MySQL 安全最佳实践

MySQLBeginner
立即练习

介绍

在本实验中,你将学习如何增强 MySQL 数据库的安全性。我们将涵盖重要的安全最佳实践,包括为 root 用户设置密码,根据最小权限原则创建专用用户,管理用户权限以及删除匿名账户。完成本实验后,你将更深入地了解如何保护你的 MySQL 服务器免受常见漏洞的侵害。

这是一个实验(Guided Lab),提供逐步指导来帮助你学习和实践。请仔细按照说明完成每个步骤,获得实际操作经验。根据历史数据,这是一个 初级 级别的实验,完成率为 94%。获得了学习者 89% 的好评率。

保护 Root 账户

默认的 MySQL 安装通常允许 root 用户从本地机器连接而无需密码。保护 MySQL 的第一步是为 root 账户设置一个强密码。

首先,从你的桌面打开终端。

root 用户身份连接到 MySQL 服务器。在本实验环境中,你可以使用 sudo 来连接而无需密码。

sudo mysql -u root

连接成功后,你将看到 MySQL 提示符 (mysql>)。

现在,为 root 用户设置密码。ALTER USER 语句用于修改用户账户。将 YourStrongPassword! 替换为你选择的密码。

ALTER USER 'root'@'localhost' IDENTIFIED BY 'YourStrongPassword!';

此命令为从 localhost 连接的 root 用户设置密码。你应该看到以下输出,确认命令已成功执行:

Query OK, 0 rows affected (0.01 sec)

接下来,使用 FLUSH PRIVILEGES 命令立即应用权限更改。

FLUSH PRIVILEGES;

输出将是:

Query OK, 0 rows affected (0.00 sec)

你现在已成功为 root 用户设置了密码。虽然你仍然可以使用 sudo mysql -u root 进行连接,但任何直接使用 mysql -u root -p 的连接尝试现在都需要你刚刚设置的密码。这是保护你的数据库的关键第一步。

创建专用用户和数据库

为应用程序使用 root 账户存在安全风险,因为它拥有无限权限。最佳实践是为每个应用程序创建具有有限权限的专用用户。在此步骤中,你将创建一个新数据库和一个仅对该数据库拥有访问权限的用户。

现在,为你的应用程序创建一个新数据库。我们将其命名为 app_db

CREATE DATABASE app_db;

你应该看到此确认信息:

Query OK, 1 row affected (0.01 sec)

接下来,创建一个应用程序将用于连接数据库的新用户。我们将此用户命名为 app_user 并为其分配密码。

CREATE USER 'app_user'@'localhost' IDENTIFIED BY 'UserPassword123';

输出将是:

Query OK, 0 rows affected (0.01 sec)

现在,授予 app_user 所需的权限。在此示例中,我们将授予对 app_db 数据库中所有表的 SELECTINSERT 权限。这遵循了最小权限原则,只赋予用户其所需的权限。

GRANT SELECT, INSERT ON app_db.* TO 'app_user'@'localhost';

通过刷新权限来应用更改。

FLUSH PRIVILEGES;

你可以通过运行以下命令来验证你刚刚授予的权限:

SHOW GRANTS FOR 'app_user'@'localhost';

输出将显示 app_user 的确切权限:

+------------------------------------------------------------------+
| Grants for app_user@localhost                                    |
+------------------------------------------------------------------+
| GRANT USAGE ON *.* TO `app_user`@`localhost`                     |
| GRANT SELECT, INSERT ON `app_db`.* TO `app_user`@`localhost`     |
+------------------------------------------------------------------+
2 rows in set (0.00 sec)

你已成功创建了一个具有适当权限的专用数据库和用户。

管理用户权限

应用程序的需求可能会发生变化,你可能需要相应地调整用户权限。在此步骤中,你将通过撤销 app_user 的现有权限来练习修改权限。

假设 app_user 现在只能读取数据 (SELECT) 而不能添加新数据 (INSERT)。你需要撤销 INSERT 权限。

使用 REVOKE 语句从 app_db 数据库上的 app_user 撤销 INSERT 权限。

REVOKE INSERT ON app_db.* FROM 'app_user'@'localhost';

你将看到以下确认信息:

Query OK, 0 rows affected (0.00 sec)

通过刷新权限来应用更改。

FLUSH PRIVILEGES;

现在,通过再次检查用户的权限来验证权限是否已被撤销。

SHOW GRANTS FOR 'app_user'@'localhost';

输出现在应该显示 app_user 只对 app_db 拥有 SELECT 权限。INSERT 权限已移除。

+--------------------------------------------------------------+
| Grants for app_user@localhost                                |
+--------------------------------------------------------------+
| GRANT USAGE ON *.* TO `app_user`@`localhost`                 |
| GRANT SELECT ON `app_db`.* TO `app_user`@`localhost`         |
+--------------------------------------------------------------+
2 rows in set (0.00 sec)

这演示了如何有效地管理用户权限以适应不断变化的安全需求。

移除匿名用户账户

默认情况下,某些 MySQL 安装会创建匿名用户账户,这些账户的用户名是空的。这些账户会带来安全风险,因为它们可能允许未经授权的访问。检查并删除它们(如果存在)是一项关键的安全实践。

你可以通过查询 mysql.user 表来识别匿名用户,查找用户名为空的条目。

SELECT User, Host FROM mysql.user WHERE User = '';

如果存在匿名用户,此查询将列出它们。Ubuntu 上的全新安装可能包含一个,但较新版本的 MySQL/MariaDB 默认通常没有匿名用户。

如果你看到类似以下的结果:

+------+-----------+
| User | Host      |
+------+-----------+
|      | localhost |
+------+-----------+
1 row in set (0.00 sec)

那么你应该使用 DROP USER 语句删除匿名用户,同时指定用户名(即空字符串 '')和主机:

DROP USER ''@'localhost';

你应该看到此确认信息:

Query OK, 0 rows affected (0.01 sec)

但是,如果你的查询返回一个空集,如下所示:

Empty set (0.00 sec)

这意味着你的数据库中没有匿名用户,这已经很安全了。在这种情况下,如果你尝试删除一个不存在的匿名用户,你将收到一个错误:

ERROR 1396 (HY000): Operation DROP USER failed for ''@'localhost'

如果不存在匿名用户,此错误是正常的,你可以安全地继续操作。

在检查匿名用户并根据需要删除它们之后,刷新权限以确保所有更改都已应用:

FLUSH PRIVILEGES;

通过再次运行 SELECT 查询来验证是否没有匿名用户剩余:

SELECT User, Host FROM mysql.user WHERE User = '';

此查询应返回一个空集,确认没有匿名用户存在:

Empty set (0.00 sec)

你已成功检查并解决了服务器上潜在的安全漏洞。现在你可以退出 MySQL shell。

exit;

总结

在此次实验中,你学习并应用了多项重要的 MySQL 安全最佳实践。你成功地为 root 账户设置了密码,根据最小权限原则创建了一个具有有限权限的专用应用程序用户,通过撤销权限管理了用户访问,并检查和处理了潜在的匿名用户账户。

通过实施这些基本的安全措施,你可以显著提高 MySQL 数据库的安全级别,并保护其免受未经授权的访问和潜在威胁。