Skip to content

TiDB 密码策略

密码复杂度要求

配置密码复杂度

TiDB 通过系统变量控制密码复杂度要求,支持以下参数:

系统变量类型默认值描述
validate_password_lengthint8密码最小长度
validate_password_mixed_case_countint0密码至少包含的大小写字母数量
validate_password_number_countint0密码至少包含的数字数量
validate_password_special_char_countint0密码至少包含的特殊字符数量
validate_password_policystring"MEDIUM"密码策略级别,可选值:LOW, MEDIUM, STRONG

密码策略级别

LOW 级别

  • 仅检查密码长度
  • 要求密码长度不小于 validate_password_length

MEDIUM 级别

  • 检查密码长度
  • 要求密码包含至少一个大写字母和一个小写字母
  • 要求密码包含至少一个数字

STRONG 级别

  • 检查密码长度
  • 要求密码包含至少一个大写字母和一个小写字母
  • 要求密码包含至少一个数字
  • 要求密码包含至少一个特殊字符

示例配置

sql
-- 设置密码最小长度为 12
SET GLOBAL validate_password_length = 12;

-- 设置密码至少包含 1 个大写字母和 1 个小写字母
SET GLOBAL validate_password_mixed_case_count = 1;

-- 设置密码至少包含 1 个数字
SET GLOBAL validate_password_number_count = 1;

-- 设置密码至少包含 1 个特殊字符
SET GLOBAL validate_password_special_char_count = 1;

-- 设置密码策略为 STRONG
SET GLOBAL validate_password_policy = 'STRONG';

密码过期设置

配置密码过期时间

sql
-- 设置密码过期时间为 90 天
SET GLOBAL default_password_lifetime = 90;

查看密码过期时间

sql
-- 查看全局密码过期设置
SELECT @@GLOBAL.default_password_lifetime;

-- 查看用户的密码过期时间
SELECT user, host, password_expired, password_last_changed, password_lifetime FROM mysql.user;

为特定用户设置密码过期时间

sql
-- 创建用户时设置密码过期时间
CREATE USER 'test'@'%' IDENTIFIED BY 'Password@123' PASSWORD EXPIRE INTERVAL 30 DAY;

-- 修改现有用户的密码过期时间
ALTER USER 'test'@'%' PASSWORD EXPIRE INTERVAL 30 DAY;

-- 禁用特定用户的密码过期
ALTER USER 'test'@'%' PASSWORD EXPIRE NEVER;

-- 使用全局密码过期设置
ALTER USER 'test'@'%' PASSWORD EXPIRE DEFAULT;

密码历史记录

配置密码历史记录

密码历史记录用于防止用户重复使用最近使用过的密码。

sql
-- 设置密码历史记录为 5 条,即用户不能重复使用最近 5 次的密码
SET GLOBAL password_history = 5;

查看密码历史记录

sql
-- 查看全局密码历史设置
SELECT @@GLOBAL.password_history;

-- 查看用户的密码历史记录
SELECT * FROM mysql.password_history WHERE user = 'test';

登录失败锁定

配置登录失败锁定

登录失败锁定功能可以防止暴力破解密码。

系统变量类型默认值描述
max_connect_errorsint100允许的最大连接错误数
connect_timeoutint10连接超时时间(秒)

查看和解锁锁定的用户

sql
-- 查看锁定的用户
SELECT user, host, account_locked FROM mysql.user;

-- 解锁用户
ALTER USER 'test'@'%' ACCOUNT UNLOCK;

密码验证插件

TiDB 支持多种密码验证插件,用于增强密码安全性。

内置密码验证插件

  • mysql_native_password:MySQL 原生密码验证插件
  • caching_sha2_password:SHA-256 密码验证插件,提供更强的安全性

设置密码验证插件

sql
-- 创建用户时指定密码验证插件
CREATE USER 'test'@'%' IDENTIFIED WITH caching_sha2_password BY 'Password@123';

-- 修改现有用户的密码验证插件
ALTER USER 'test'@'%' IDENTIFIED WITH caching_sha2_password BY 'Password@123';

密码管理最佳实践

1. 制定严格的密码策略

  • 采用 STRONG 级别密码策略
  • 设置合理的密码长度(至少 12 位)
  • 要求密码包含多种字符类型

2. 定期更换密码

  • 设置密码过期时间(建议 90 天)
  • 定期提醒用户更换密码
  • 管理员密码应更频繁更换

3. 启用密码历史记录

  • 设置至少保存 5 条密码历史
  • 防止用户重复使用旧密码

4. 配置登录失败锁定

  • 设置合理的登录失败次数限制
  • 及时解锁误锁定的用户

5. 使用强密码验证插件

  • 优先使用 caching_sha2_password 插件
  • 确保所有用户都使用安全的密码验证方式

6. 定期审计密码策略

  • 检查密码策略配置是否符合安全要求
  • 审计用户密码使用情况
  • 及时调整密码策略以适应新的安全威胁

常见问题(FAQ)

Q1: 如何查看当前的密码策略配置?

A1: 使用以下命令查看当前密码策略配置:

sql
SHOW VARIABLES LIKE 'validate_password%';
SHOW VARIABLES LIKE 'default_password_lifetime';
SHOW VARIABLES LIKE 'password_history';

Q2: 如何修改用户密码?

A2: 使用以下命令修改用户密码:

sql
-- 修改当前用户密码
ALTER USER USER() IDENTIFIED BY 'NewPassword@123';

-- 修改其他用户密码
ALTER USER 'test'@'%' IDENTIFIED BY 'NewPassword@123';

Q3: 如何重置忘记的 root 密码?

A3: 重置 root 密码步骤:

  1. 停止 TiDB 服务
  2. 使用 --skip-grant-tables 选项启动 TiDB
  3. 登录 TiDB 并修改 root 密码
  4. 重启 TiDB 服务

Q4: 密码策略修改后是否立即生效?

A4: 全局密码策略修改后,对新创建的用户和密码立即生效,但对现有用户密码不会自动生效。现有用户需要重新设置密码才能应用新的密码策略。

Q5: 如何禁用密码复杂度检查?

A5: 将密码策略级别设置为 LOW,并将复杂度要求参数设置为 0:

sql
SET GLOBAL validate_password_policy = 'LOW';
SET GLOBAL validate_password_mixed_case_count = 0;
SET GLOBAL validate_password_number_count = 0;
SET GLOBAL validate_password_special_char_count = 0;

Q6: 如何配置密码永不过期?

A6: 设置全局密码过期时间为 0:

sql
SET GLOBAL default_password_lifetime = 0;

Q7: 如何查看用户的密码过期时间?

A7: 使用以下命令查看用户的密码过期时间:

sql
SELECT user, host, password_expired, password_last_changed, 
       CASE WHEN password_lifetime IS NULL THEN 'DEFAULT' 
            WHEN password_lifetime = 0 THEN 'NEVER' 
            ELSE CONCAT(password_lifetime, ' DAYS') END AS password_lifetime
FROM mysql.user;

Q8: 密码包含哪些特殊字符?

A8: TiDB 认为以下字符为特殊字符:

!"#$%&'()*+,-./:;<=>?@[\]^_`{|}~

Q9: 如何解锁被锁定的用户?

A9: 使用以下命令解锁被锁定的用户:

sql
ALTER USER 'test'@'%' ACCOUNT UNLOCK;

Q10: 如何批量修改用户的密码策略?

A10: 可以使用存储过程或脚本来批量修改用户的密码策略:

sql
-- 示例:批量修改所有用户的密码过期时间为 90 天
DELIMITER //
CREATE PROCEDURE batch_update_password_lifetime()
BEGIN
    DECLARE done INT DEFAULT FALSE;
    DECLARE user_name VARCHAR(100);
    DECLARE host_name VARCHAR(100);
    DECLARE cur CURSOR FOR SELECT user, host FROM mysql.user;
    DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = TRUE;
    
    OPEN cur;
    
    read_loop: LOOP
        FETCH cur INTO user_name, host_name;
        IF done THEN
            LEAVE read_loop;
        END IF;
        
        SET @sql = CONCAT('ALTER USER ''', user_name, '''@''', host_name, ''' PASSWORD EXPIRE INTERVAL 90 DAY;');
        PREPARE stmt FROM @sql;
        EXECUTE stmt;
        DEALLOCATE PREPARE stmt;
    END LOOP;
    
    CLOSE cur;
END//
DELIMITER ;

-- 执行存储过程
CALL batch_update_password_lifetime();

Q11: 如何审计密码策略的合规性?

A11: 可以使用以下方法审计密码策略的合规性:

  1. 定期检查密码策略配置
  2. 审计用户密码是否符合策略要求
  3. 检查密码过期情况
  4. 检查密码历史记录
  5. 检查登录失败锁定情况

Q12: 密码策略对性能有影响吗?

A12: 密码策略主要在用户创建、密码修改和登录验证时生效,对数据库的正常运行性能影响很小。