数据库上线后不做基础安全配置,等同于把数据目录直接暴露在公网。多数中小规模项目的数据泄露、勒索删库事件,根源不是攻击手段多高明,而是默认端口、空密码、过高权限账户和未加密传输这些基础项被长期忽视。下面直接按操作顺序,把数据库从“裸奔”状态拉到可用的安全基线。

1. 删除或锁定默认账户与匿名账户

安装完成后第一件事不是建库,而是处理默认账户。MySQL、PostgreSQL、SQL Server、MongoDB 等数据库在初始化后都可能存在匿名用户、无密码的 root 或具有默认密码的超级账户。以 MySQL 为例,安装后应执行以下检查:

SELECT user, host, authentication_string FROM mysql.user;

凡是不认识的主机范围(如 host 为 %)或空密码账户,一律删除或锁定。对于必须保留的 root,应限制其只能从本地登录,并立即设置强密码。PostgreSQL 默认只允许本地 peer 认证,但也要检查 pg_hba.conf 中是否存在 trust 认证方式,任何 trust 条目都应改为 scram-sha-256 或 md5。MongoDB 在 3.x 版本以前默认无认证,如果还在用旧版本,先升级再开启认证,否则任何远程客户端都能直接读写数据。

2. 强制修改默认端口并限制监听地址

默认端口是自动化扫描的第一目标。MySQL 的 3306、PostgreSQL 的 5432、SQL Server 的 1433、Redis 的 6379、MongoDB 的 27017,这些端口上的爆破和漏洞探测流量从未停止。修改端口不能替代其他安全措施,但能过滤掉大量无差别攻击。修改后还要检查监听地址,数据库只应监听内网 IP 或 127.0.0.1,不应直接监听 0.0.0.0。如果应用服务器和数据库在同一内网,数据库监听在内网网卡即可;如果必须跨公网访问,应通过专线或跳板机,而不是把数据库端口直接映射到公网。

3. 建立最小权限账户体系

很多团队为了省事,开发、测试、报表、备份全部使用同一个 root 或 sa 账户。一旦某个应用被 SQL 注入,攻击者拿到的就是数据库的最高权限。正确做法是按业务模块拆分账户:应用运行账户只授予对应库的 SELECT、INSERT、UPDATE、DELETE 权限,不授予 DDL、DROP、GRANT 权限;备份账户只授予 SELECT 和 LOCK TABLES 权限;报表账户只授予只读权限。以 MySQL 为例:

CREATE USER 'app_user'@'10.0.0.%' IDENTIFIED BY '强密码';
GRANT SELECT, INSERT, UPDATE, DELETE ON app_db.* TO 'app_user'@'10.0.0.%';

注意主机范围不要使用通配符 %,应精确到应用服务器所在网段。权限分配后定期审查,删除离职人员账户和不再使用的临时账户。

4. 开启并强制使用加密传输

数据库默认以明文传输数据,在内网中如果存在嗅探风险,账号密码和数据内容都可能被截获。MySQL 和 PostgreSQL 都支持 TLS/SSL 加密连接。MySQL 开启 SSL 需要在配置文件中指定证书路径,并对账户设置 REQUIRE SSL:

ALTER USER 'app_user'@'10.0.0.%' REQUIRE SSL;

PostgreSQL 在 postgresql.conf 中设置 ssl = on 并配置证书,然后在 pg_hba.conf 中将认证方式改为 hostssl。对于 Redis,如果无法使用 TLS,至少应使用 requirepass 设置访问密码,并禁止危险命令。

5. 加固配置文件与数据目录权限

数据库配置文件通常包含明文密码、证书路径和网络配置,其权限应限制为仅数据库运行用户可读。Linux 下 MySQL 的 /etc/my.cnf 和 PostgreSQL 的 /var/lib/pgsql 数据目录,应确保权限为 700 或 750,属主为数据库用户。Windows 下 SQL Server 的数据目录应限制只有服务账户和系统管理员可访问。配置文件中不要写入明文密码,MySQL 可使用 mysql_config_editor 加密存储登录凭证,PostgreSQL 可使用 .pgpass 文件并设置权限为 600。

6. 禁用危险功能与远程加载

MySQL 的 LOAD DATA LOCAL INFILE 允许客户端读取本地文件,历史上多次被用于读取服务器敏感文件。应在配置文件中设置 local-infile=0 禁用。PostgreSQL 的 COPY ... FROM PROGRAM 和 MySQL 的 sys_exec 等扩展函数,如果不是业务必需,应删除或禁用。SQL Server 的 xp_cmdshell 默认关闭,不要为了调试方便随意开启。MongoDB 的 $where 和 JavaScript 执行在不需要时应禁用,防止注入后执行任意代码。

7. 配置审计日志与告警

没有审计日志,发生安全事件后无法追溯。MySQL 开启 general_log 会影响性能,建议开启 error_log 和 slow_query_log,并通过企业版审计插件或第三方工具记录 DDL 和账户变更。PostgreSQL 的 log_statement 可设置为 ddl 或 mod,记录所有数据变更。SQL Server 自带审计功能,可对敏感表的 SELECT、INSERT、UPDATE、DELETE 操作进行细粒度审计。日志应集中存储到独立的日志服务器,避免攻击者删除本地日志。

8. 制定备份与恢复演练策略

安全配置的最终目的是保证数据可用。备份不是安全配置的附属品,而是安全体系的一部分。至少做到每日全量备份加实时 binlog/WAL 归档,备份文件加密后传输到异地存储。定期进行恢复演练,验证备份可用性。很多团队在遭受勒索攻击后才发现备份文件也被加密或备份流程早已中断。备份账户应独立于业务账户,且备份文件访问权限严格控制。

9. 及时更新补丁与版本策略

数据库厂商会定期发布安全补丁,修复权限提升、远程代码执行等严重漏洞。生产环境的数据库版本不应停留在已停止维护的旧版本。升级前在测试环境验证兼容性,升级过程中做好回滚方案。对于无法立即升级的系统,应通过网络隔离、禁用受影响功能等方式缓解风险。

10. 网络层隔离与防火墙策略

数据库端口不应被办公网或公网直接访问。通过防火墙或安全组规则,只允许应用服务器网段访问数据库端口,其他流量默认拒绝。对于多租户环境,可使用 VLAN 或微隔离技术将不同业务的数据库划分到不同安全域。云环境下,数据库应放在私有子网,通过 NAT 或负载均衡对外提供服务,而不是直接分配公网 IP。

数据库基础安全配置不是一次性工作,而是需要随业务变化持续维护的基线。上述每一项操作都有明确的命令和配置项,执行成本不高,但能有效阻断绝大多数自动化攻击和内部误操作。安全配置的优先级应高于功能开发,因为数据一旦丢失或泄露,恢复成本远高于预防投入。