密码复杂度检查
密码复杂度检查

密码复杂度检查

密码复杂度检查方案(标准可落地版)

适用场景:账号注册、密码重置、运维系统、LDAP/Radius、Web 后台;可直接翻译成伪代码、Python/C++ 实现。 设计思路:分层校验(基础规则 + 强度评分 + 黑名单),支持灵活开关规则,输出结构化结果(是否通过、强度等级、不满足项)。

一、核心定义

字符分类

  1. 大写字母 A-Z
  2. 小写字母 a-z
  3. 数字 0-9
  4. 特殊符号:!@#$%^&*()_+-=[]{}|;:,.<>?(可自定义,建议排除易混淆、命令注入风险字符如 " ' \)

注意:中文、全角字符默认归为其他字符,不计入 4 类字符集,但可计入长度。

二、规则集(推荐企业标准,可分【基础版】【严格版】)

✅ 基础版(内网普通业务,最低安全)

  1. 长度 ≥8
  2. 至少包含 2 种 上面 4 类字符
  3. 不能包含用户名 / 账号名(大小写不敏感)
  4. 不能包含连续 3 位相同字符(aaa、111)
  5. 不能包含连续升序 / 降序 3 位(123、321、abc、cba)

✅ 严格版(管理员账号、VPN、Radius、LDAP、核心业务,推荐)

  1. 长度 ≥12
  2. 至少包含 3 种 上面 4 类字符
  3. 不能包含用户名 / 账号名(大小写不敏感)
  4. 禁止连续 3 位相同字符(aaa)
  5. 禁止连续升序 / 降序 3 位(123/cba)
  6. 禁止常见弱密码黑名单匹配(字典)
  7. 禁止密码是账号名反转
  8. 禁止密码包含手机号、生日片段(可选增强)

可选增强项:禁止重复使用历史 N 次密码(如最近 5 次密码不可复用)

三、密码强度评分算法(0~100 分)

用于前端展示弱 / 中 / 强,不替代硬性规则:硬性规则不满足直接拒绝,分数仅做参考。

  1. 基础分:长度 × 4
  2. 字符种类加分:
    • 2 类:+10
    • 3 类:+20
    • 4 类:+30
  3. 额外加分:含特殊字符额外 + 5
  4. 扣分项:
    • 连续 3 相同字符:-15
    • 连续 3 顺序字符:-15
    • 包含用户名:-20
    • 在弱密码黑名单:直接置 0

强度等级映射

  • 0~39:弱(禁止)
  • 40~69:中(基础业务可放行,管理员账号禁止)
  • 70~100:强(推荐)

四、伪代码(可直接转 C++/Python/JS)

// 输入:password(待检测密码), username(账号名), mode="strict" / "basic"
// 输出结构体:
// {
//    pass: bool,
//    score: int,
//    level: string, // weak/medium/strong
//    msg_list: array<string> // 不满足原因
// }
Function CheckPasswordComplexity(password, username, mode):
    msg_list = empty array
    score = 0
    // 1. 长度校验
    min_len = 8
    if mode == "strict":
        min_len = 12
    if length(password) < min_len:
        add msg_list, "密码长度不足,最少要求"+min_len+"位"
    
    // 2. 判断4类字符是否存在
    has_upper = RegexMatch(password, "[A-Z]")
    has_lower = RegexMatch(password, "[a-z]")
    has_digit = RegexMatch(password, "[0-9]")
    has_special = RegexMatch(password, "[!@#$%^&*()_+\-=\[\]{}|;:,.<>?]")
    type_count = count_true(has_upper, has_lower, has_digit, has_special)
    
    require_type = 2
    if mode == "strict":
        require_type =3
    if type_count < require_type:
        add msg_list, "字符种类不足,至少需要"+require_type+"种字符(大写/小写/数字/符号)"
    
    // 3. 检测连续3相同字符
    if RegexMatch(password, "(.)\1\1"):
        add msg_list, "禁止3个连续相同字符"
    
    // 4. 检测连续升序/降序
    if HasSeq3(password):
        add msg_list, "禁止3位连续顺序字符(如123、abc)"
    
    // 5. 账号名检测(大小写不敏感)
    low_pwd = ToLower(password)
    low_user = ToLower(username)
    if low_user != "" and low_pwd contains low_user:
        add msg_list, "密码不能包含账号名称"
    
    // 6. 弱密码黑名单校验
    if IsInWeakDict(low_pwd):
        add msg_list, "该密码属于常见弱密码,禁止使用"

    // 强度评分计算
    score = length(password)*4
    if type_count ==2: score +=10
    if type_count ==3: score +=20
    if type_count ==4: score +=30
    if has_special: score +=5
    if RegexMatch(password, "(.)\1\1"): score -=15
    if HasSeq3(password): score -=15
    if low_user != "" and low_pwd contains low_user: score -=20
    if IsInWeakDict(low_pwd): score =0

    // 分数边界裁剪
    score = Clamp(score, 0, 100)
    
    // 等级
    if score <40: level="weak"
    else if score <70: level="medium"
    else: level="strong"
    
    // 是否通过:无错误消息即通过
    pass = (length(msg_list)==0)
    
    return {pass, score, level, msg_list}

// 辅助函数:检测连续3位顺序字符 123/321/abc/cba
Function HasSeq3(s):
    for i from 0 to len(s)-3:
        c1 = s[i], c2=s[i+1], c3=s[i+2]
        // 升序 c2=c1+1 && c3=c2+1
        if (Ord(c2)==Ord(c1)+1 && Ord(c3)==Ord(c2)+1):
            return true
        // 降序 c2=c1-1 && c3=c2-1
        if (Ord(c2)==Ord(c1)-1 && Ord(c3)==Ord(c2)-1):
            return true
    return false

// 辅助函数:弱密码字典匹配(读取弱密码列表,大小写不敏感)
Function IsInWeakDict(lower_pwd):
    return lower_pwd in WeakPasswordSet

五、弱密码字典建议

来源:常见 top 弱密码集合

  • 123456、password、qwerty、admin123、111111、abc123

生产环境建议加载 10 万 + 弱密码库;可定期更新。

六、边界注意事项

  1. 前后空格:建议自动 trim,或者直接判定首尾空格非法(看业务)
  2. Unicode 字符:中文、emoji 等,若业务允许,只计入长度,不计入 4 类字符集,防止绕过规则
  3. 正则引擎:特殊符号正则记得转义,避免注入
  4. 不要在前端单独校验!前端仅做提示,后端必须重复完整校验(前端可被绕过)
  5. 密码不要明文存储,校验时仅接收明文用于复杂度判断,判断完成立刻丢弃明文

七、输出示例

示例 1:密码 Abc12345,基础模式

  • 长度 8;大小写 + 数字,3 类;包含连续顺序abc、123
  • 结果:pass=false,提示:禁止 3 位连续顺序字符

示例 2:密码 K9s@P27q,严格模式

  • 长度 8 <12;不通过;提示长度不足

示例 3:密码 Mk7$s92pRz!5,严格模式

  • 长度 13;大小写、数字、符号(4 类);无连续重复 / 顺序;不含用户名;不在黑名单
  • pass=true,score=88 level=strong

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

错误: Content is protected !!