diff --git a/src/utils/validate.js b/src/utils/validate.js index 659aad00..af21be38 100644 --- a/src/utils/validate.js +++ b/src/utils/validate.js @@ -198,52 +198,81 @@ export function validateNewPassword(rule, value, callback) { callback() // 验证成功 } -function containsConsecutiveCharacters(password, maxConsecutive) { - let count = 1 // 初始化计数器 - let previousChar = '' // 保存上一个字符 - maxConsecutive = maxConsecutive + 1 - for (let i = 0; i < password.length; i++) { - // 检查当前字符与前一个字符是否相同 - if (password[i] === previousChar) { - count++ // 计数器加1 - } else { - count = 1 // 如果字符不同,重置计数器 - } - - // 检查是否超过最大连续字符数 - if (count > maxConsecutive) { - return true - } - - // 检查当前字符是否是数字 - if (/\d/.test(password[i])) { - // 检查是否有超过指定数量的连续数字 - if (i > 0 && password[i] === password[i - 1]) { - count++ // 计数器加1 - if (count > maxConsecutive) { - return true - } - } else { - count = 1 // 重置计数器 +/** + * 检查密码中是否包含超过 n 个连续相同字符、连续递增/递减的数字或字母(不区分大小写) + */ +function containsConsecutiveCharacters(password, n) { + // 检查连续相同字符 + n = n + 1; // 允许最多 n 个连续字符 + for (let i = 0; i <= password.length - n; i++) { + let consecutiveSameChar = true; + for (let j = 1; j < n; j++) { + if (password[i + j] !== password[i]) { + consecutiveSameChar = false; + break; } } - - // 检查当前字符是否是字母 - if (/[a-zA-Z]/.test(password[i])) { - // 检查是否有超过指定数量的连续字母 - if (i > 0 && password[i] === password[i - 1]) { - count++ // 计数器加1 - if (count > maxConsecutive) { - return true - } - } else { - count = 1 // 重置计数器 - } + if (consecutiveSameChar) { + return true; // 包含超过 n 个连续相同字符 } - - previousChar = password[i] // 更新上一个字符 } - return false // 如果没有找到问题,则返回符合要求的提示 + // 检查连续递增或递减的数字 + for (let i = 0; i <= password.length - n; i++) { + let consecutiveIncreasing = true; + let consecutiveDecreasing = true; + for (let j = 1; j < n; j++) { + const currentChar = password[i]; + const nextChar = password[i + j]; + + // 检查数字递增或递减 + if (/\d/.test(currentChar) && /\d/.test(nextChar)) { + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) + j) { + consecutiveIncreasing = false; + } + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) - j) { + consecutiveDecreasing = false; + } + } else { + consecutiveIncreasing = false; + consecutiveDecreasing = false; + break; + } + } + if (consecutiveIncreasing || consecutiveDecreasing) { + return true; // 包含超过 n 个递增或递减的连续数字 + } + } + + // 检查连续递增或递减的字母(不区分大小写) + for (let i = 0; i <= password.length - n; i++) { + let consecutiveIncreasing = true; + let consecutiveDecreasing = true; + for (let j = 1; j < n; j++) { + const currentChar = password[i].toLowerCase(); // 转为小写 + const nextChar = password[i + j].toLowerCase(); // 转为小写 + + // 检查字母递增或递减 + if (/[a-zA-Z]/.test(currentChar) && /[a-zA-Z]/.test(nextChar)) { + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) + j) { + consecutiveIncreasing = false; + } + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) - j) { + consecutiveDecreasing = false; + } + } else { + consecutiveIncreasing = false; + consecutiveDecreasing = false; + break; + } + } + if (consecutiveIncreasing || consecutiveDecreasing) { + return true; // 包含超过 n 个递增或递减的连续字母 + } + } + + // 不包含连续相同字符、数字或字母序列 + return false; } + diff --git a/src/views/system/user/index.vue b/src/views/system/user/index.vue index c31512fe..e9b56d24 100644 --- a/src/views/system/user/index.vue +++ b/src/views/system/user/index.vue @@ -743,53 +743,81 @@ export default { // 6. 新密码通过所有校验,返回空表示通过校验 return null }, - containsConsecutiveCharacters(password, maxConsecutive) { - let count = 1 // 初始化计数器 - let previousChar = '' // 保存上一个字符 - maxConsecutive = maxConsecutive + 1 - for (let i = 0; i < password.length; i++) { - // 检查当前字符与前一个字符是否相同 - if (password[i] === previousChar) { - count++ // 计数器加1 - } else { - count = 1 // 如果字符不同,重置计数器 - } - - // 检查是否超过最大连续字符数 - if (count > maxConsecutive) { - return true - } - - // 检查当前字符是否是数字 - if (/\d/.test(password[i])) { - // 检查是否有超过指定数量的连续数字 - if (i > 0 && password[i] === password[i - 1]) { - count++ // 计数器加1 - if (count > maxConsecutive) { - return true - } - } else { - count = 1 // 重置计数器 + /** + * 检查密码中是否包含超过 n 个连续相同字符、连续递增/递减的数字或字母(不区分大小写) + */ + containsConsecutiveCharacters(password, n) { + // 检查连续相同字符 + n = n + 1 // 允许最多 n 个连续字符 + for (let i = 0; i <= password.length - n; i++) { + let consecutiveSameChar = true + for (let j = 1; j < n; j++) { + if (password[i + j] !== password[i]) { + consecutiveSameChar = false + break } } - - // 检查当前字符是否是字母 - if (/[a-zA-Z]/.test(password[i])) { - // 检查是否有超过指定数量的连续字母 - if (i > 0 && password[i] === password[i - 1]) { - count++ // 计数器加1 - if (count > maxConsecutive) { - return true - } - } else { - count = 1 // 重置计数器 - } + if (consecutiveSameChar) { + return true // 包含超过 n 个连续相同字符 } - - previousChar = password[i] // 更新上一个字符 } - return false // 如果没有找到问题,则返回符合要求的提示 + // 检查连续递增或递减的数字 + for (let i = 0; i <= password.length - n; i++) { + let consecutiveIncreasing = true + let consecutiveDecreasing = true + for (let j = 1; j < n; j++) { + const currentChar = password[i] + const nextChar = password[i + j] + + // 检查数字递增或递减 + if (/\d/.test(currentChar) && /\d/.test(nextChar)) { + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) + j) { + consecutiveIncreasing = false + } + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) - j) { + consecutiveDecreasing = false + } + } else { + consecutiveIncreasing = false + consecutiveDecreasing = false + break + } + } + if (consecutiveIncreasing || consecutiveDecreasing) { + return true // 包含超过 n 个递增或递减的连续数字 + } + } + + // 检查连续递增或递减的字母(不区分大小写) + for (let i = 0; i <= password.length - n; i++) { + let consecutiveIncreasing = true + let consecutiveDecreasing = true + for (let j = 1; j < n; j++) { + const currentChar = password[i].toLowerCase() // 转为小写 + const nextChar = password[i + j].toLowerCase() // 转为小写 + + // 检查字母递增或递减 + if (/[a-zA-Z]/.test(currentChar) && /[a-zA-Z]/.test(nextChar)) { + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) + j) { + consecutiveIncreasing = false + } + if (nextChar.charCodeAt(0) !== currentChar.charCodeAt(0) - j) { + consecutiveDecreasing = false + } + } else { + consecutiveIncreasing = false + consecutiveDecreasing = false + break + } + } + if (consecutiveIncreasing || consecutiveDecreasing) { + return true // 包含超过 n 个递增或递减的连续字母 + } + } + + // 不包含连续相同字符、数字或字母序列 + return false } } }