增加密码校验

This commit is contained in:
BianLzhaoMin 2026-01-04 10:21:30 +08:00
parent a93308d5dd
commit 8521290ee4
3 changed files with 144 additions and 70 deletions

View File

@ -5,7 +5,10 @@
* @returns {Boolean}
*/
export function isPathMatch(pattern, path) {
const regexPattern = pattern.replace(/\//g, '\\/').replace(/\*\*/g, '.*').replace(/\*/g, '[^\\/]*')
const regexPattern = pattern
.replace(/\//g, '\\/')
.replace(/\*\*/g, '.*')
.replace(/\*/g, '[^\\/]*')
const regex = new RegExp(`^${regexPattern}$`)
return regex.test(path)
}
@ -16,7 +19,7 @@ export function isPathMatch(pattern, path) {
* @returns {Boolean}
*/
export function isEmpty(value) {
if (value == null || value == "" || value == undefined || value == "undefined") {
if (value == null || value == '' || value == undefined || value == 'undefined') {
return true
}
return false
@ -54,7 +57,8 @@ export function validUsername(str) {
* @returns {Boolean}
*/
export function validURL(url) {
const reg = /^(https?|ftp):\/\/([a-zA-Z0-9.-]+(:[a-zA-Z0-9.&%$-]+)*@)*((25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9][0-9]?)(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3}|([a-zA-Z0-9-]+\.)*[a-zA-Z0-9-]+\.(com|edu|gov|int|mil|net|org|biz|arpa|info|name|pro|aero|coop|museum|[a-zA-Z]{2}))(:[0-9]+)*(\/($|[a-zA-Z0-9.,?'\\+&%$#=~_-]+))*$/
const reg =
/^(https?|ftp):\/\/([a-zA-Z0-9.-]+(:[a-zA-Z0-9.&%$-]+)*@)*((25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9][0-9]?)(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3}|([a-zA-Z0-9-]+\.)*[a-zA-Z0-9-]+\.(com|edu|gov|int|mil|net|org|biz|arpa|info|name|pro|aero|coop|museum|[a-zA-Z]{2}))(:[0-9]+)*(\/($|[a-zA-Z0-9.,?'\\+&%$#=~_-]+))*$/
return reg.test(url)
}
@ -90,7 +94,8 @@ export function validAlphabets(str) {
* @returns {Boolean}
*/
export function validEmail(email) {
const reg = /^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/
const reg =
/^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/
return reg.test(email)
}
@ -112,3 +117,55 @@ export function isArray(arg) {
}
return Array.isArray(arg)
}
/**
* 验证新密码用于 Element UI 表单验证规则
* @param {Object} rule 验证规则对象
* @param {string} value 密码值
* @param {Function} callback 回调函数
*/
export function validateNewPassword(rule, value, callback) {
if (!value) {
callback(new Error('密码不能为空'))
return
}
// 1. 检查密码长度
if (value.length < 8 || value.length > 16) {
callback(new Error('密码长度应为8至16位且必须包含大小写字母及数字及特殊字符'))
return
}
// 2. 检查密码复杂度
const hasUpperCase = /[A-Z]/.test(value)
const hasLowerCase = /[a-z]/.test(value)
const hasDigit = /\d/.test(value)
const hasSpecialChar = /[!@#$%^&*(),.?":{}|<>]/.test(value)
if (!hasUpperCase || !hasLowerCase || !hasDigit || !hasSpecialChar) {
callback(new Error('密码长度应为8至16位且必须包含大小写字母及数字及特殊字符'))
return
}
callback() // 验证成功
}
/**
* 同步验证新密码用于 $prompt inputValidator 等场景
* @param {string} value 密码值
* @returns {string|boolean} 返回错误信息字符串或 true验证通过
*/
export function validateNewPasswordSync(value) {
if (!value) {
return '密码不能为空'
}
// 1. 检查密码长度
if (value.length < 8 || value.length > 16) {
return '密码长度应为8至16位且必须包含大小写字母及数字及特殊字符'
}
// 2. 检查密码复杂度
const hasUpperCase = /[A-Z]/.test(value)
const hasLowerCase = /[a-z]/.test(value)
const hasDigit = /\d/.test(value)
const hasSpecialChar = /[!@#$%^&*(),.?":{}|<>]/.test(value)
if (!hasUpperCase || !hasLowerCase || !hasDigit || !hasSpecialChar) {
return '密码长度应为8至16位且必须包含大小写字母及数字及特殊字符'
}
return true
}

View File

@ -531,6 +531,7 @@ import 'splitpanes/dist/splitpanes.css'
import CryptoUtil from '../../../api/crypto.js'
import ComDialog from '@/components/ComDialog/index.vue'
import ComButton from '@/components/ComButton/index.vue'
import { validateNewPasswordSync } from '@/utils/validate'
const router = useRouter()
const appStore = useAppStore()
@ -769,13 +770,7 @@ function handleResetPwd(row) {
confirmButtonText: '确定',
cancelButtonText: '取消',
closeOnClickModal: false,
inputPattern: /^.{5,20}$/,
inputErrorMessage: '用户密码长度必须介于 5 和 20 之间',
inputValidator: (value) => {
if (/<|>|"|'|\||\\/.test(value)) {
return '不能包含非法字符:< > " \' \\\ |'
}
},
inputValidator: validateNewPasswordSync,
})
.then(({ value }) => {
resetUserPwd(row.userId, value).then((response) => {

View File

@ -1,13 +1,28 @@
<template>
<el-form ref="pwdRef" :model="user" :rules="rules" label-width="80px">
<el-form-item label="旧密码" prop="oldPassword">
<el-input v-model="user.oldPassword" placeholder="请输入旧密码" type="password" show-password />
<el-input
v-model="user.oldPassword"
placeholder="请输入旧密码"
type="password"
show-password
/>
</el-form-item>
<el-form-item label="新密码" prop="newPassword">
<el-input v-model="user.newPassword" placeholder="请输入新密码" type="password" show-password />
<el-input
v-model="user.newPassword"
placeholder="请输入新密码"
type="password"
show-password
/>
</el-form-item>
<el-form-item label="确认密码" prop="confirmPassword">
<el-input v-model="user.confirmPassword" placeholder="请确认新密码" type="password" show-password/>
<el-input
v-model="user.confirmPassword"
placeholder="请确认新密码"
type="password"
show-password
/>
</el-form-item>
<el-form-item>
<el-button type="primary" @click="submit">保存</el-button>
@ -17,36 +32,43 @@
</template>
<script setup>
import { updateUserPwd } from "@/api/system/user"
import { updateUserPwd } from '@/api/system/user'
import { validateNewPassword } from '@/utils/validate'
const { proxy } = getCurrentInstance()
const user = reactive({
oldPassword: undefined,
newPassword: undefined,
confirmPassword: undefined
confirmPassword: undefined,
})
const equalToPassword = (rule, value, callback) => {
if (user.newPassword !== value) {
callback(new Error("两次输入的密码不一致"))
callback(new Error('两次输入的密码不一致'))
} else {
callback()
}
}
const rules = ref({
oldPassword: [{ required: true, message: "旧密码不能为空", trigger: "blur" }],
newPassword: [{ required: true, message: "新密码不能为空", trigger: "blur" }, { min: 6, max: 20, message: "长度在 6 到 20 个字符", trigger: "blur" }, { pattern: /^[^<>"'|\\]+$/, message: "不能包含非法字符:< > \" ' \\\ |", trigger: "blur" }],
confirmPassword: [{ required: true, message: "确认密码不能为空", trigger: "blur" }, { required: true, validator: equalToPassword, trigger: "blur" }]
oldPassword: [{ required: true, message: '旧密码不能为空', trigger: 'blur' }],
newPassword: [
{ required: true, message: '新密码不能为空', trigger: 'blur' },
{ validator: validateNewPassword, trigger: 'blur' },
],
confirmPassword: [
{ required: true, message: '确认密码不能为空', trigger: 'blur' },
{ validator: equalToPassword, trigger: 'blur' },
],
})
/** 提交按钮 */
function submit() {
proxy.$refs.pwdRef.validate(valid => {
proxy.$refs.pwdRef.validate((valid) => {
if (valid) {
updateUserPwd(user.oldPassword, user.newPassword).then(response => {
proxy.$modal.msgSuccess("修改成功")
updateUserPwd(user.oldPassword, user.newPassword).then((response) => {
proxy.$modal.msgSuccess('修改成功')
})
}
})