表单验证的规则的实现
基础实现
- 手机号码的校验
- 密码的长度的验证不小于6
表单结构
<form action="http:// xxx.com/register" id="registerForm" method="post">
请输入手机号码:<input type="text" name="phoneNumber" />
请输入密码:<input type="text" name="password" />
<button>提交</button>
</form>
代码实现
var registerForm = document.getElementById('registerForm')
registerForm.onsubmit = function () {
if (registerForm.password.value.length < 6) {
alert(`密码长度不能少于 ${registerForm.password.value.length} 位`)
return false
}
if (!/(^1[3|5|8][0-9]{9}$)/.test(registerForm.phoneNumber.value)) {
alert('手机号码不正确')
return false
}
console.log('提交成功!!!');
}
代码问题分析
* registerForm.onsubmit 函数比较庞大,包含了很多 if-else 语句,这些语句需要覆盖所有
* 的校验规则。
* registerForm.onsubmit 函数缺乏弹性,如果增加了一种新的校验规则,或者想把密码的长
* 度校验从 6 改成 8,我们都必须深入 registerForm.onsubmit 函数的内部实现,这是违反开
*放—封闭原则的。
* 算法的复用性差,如果在程序中增加了另外一个表单,这个表单也需要进行一些类似的
* 校验,那我们很可能将这些校验逻辑复制得漫天遍野。
策略模式如何优化表单的验证
策略模式的一些重要实现
1.Context :封装上下文,根据需要调用需要的策略,屏蔽外界对策略的直接调用,只对外提供一个接口,根据需要调用对应的策略;
2.Strategy :策略,含有具体的算法,其方法的外观相同,因此可以互相代替;
3.StrategyMap :所有策略的合集,供封装上下文调用;
封装我们的策略对象
var strategies = {
minLength: function (value, length, errorMsg) { // 限制最小长度
if (value.length < length) {
return errorMsg;
}
},
isMobile: function (value, errorMsg) { // 手机号码格式
if (!/(^1[3|5|8][0-9]{9}$)/.test(value)) {
return errorMsg;
}
}
};
创建Validator类
var Validator = function () {
this.cache = [] // 保存校验规则
}
Validator.prototype.add = function (dom, rule, errorMsg) {
var ary = rule.split(':') //把 strategy 和参数分开
this.cache.push(function () { // 把校验的步骤用空函数包装起来,并且放入 cache
var strategy = ary.shift() // 用户挑选的 strategy
ary.unshift(dom.value); // 把 input 的 value 添加进参数列表
ary.push(errorMsg); // 把 errorMsg 添加进参数列表
return strategies[strategy].apply(dom, ary);
})
}
Validator.prototype.start = function () {
for (var i = 0, validatorFunc; validatorFunc = this.cache[i++];) {
var msg = validatorFunc(); // 开始校验,并取得校验后的返回信息
if (msg) { // 如果有确切的返回值,说明校验没有通过
return msg;
}
}
};
Validator 类在这里作为 Context,负责接收用户的请求并委托给 strategy 对象。
完整的功能实现
<html>
<body>
<form action="http:// xxx.com/register" id="registerForm" method="post">
请输入邮箱号码:<input type="text" name="email"/>
请输入用户名:<input type="text" name="userName" />
请输入密码:<input type="text" name="password" />
请输入手机号码:<input type="text" name="phoneNumber" />
<button>提交</button>
</form>
<script>
/***********************策略对象**************************/
var strategies = {
isNonEmpty: function (value, errorMsg) {
if (value === '') {
return errorMsg;
}
},
minLength: function (value, length, errorMsg) {
if (value.length < length) {
return errorMsg;
}
},
isMobile: function (value, errorMsg) {
if (!/(^1[3|5|8][0-9]{9}$)/.test(value)) {
return errorMsg;
}
},
isEmail:function(value,errorMsg){
if(!/^[\w.\-]+@(?:[a-z0-9]+(?:-[a-z0-9]+)*\.)+[a-z]{2,3}$/.test(value)){
return errorMsg
}
}
};
/***********************Validator 类**************************/
var Validator = function () {
this.cache = [];
};
Validator.prototype.add = function (dom, rules) {
var self = this;
for (var i = 0, rule; rule = rules[i++];) {
(function (rule) {
var strategyAry = rule.strategy.split(':');
var errorMsg = rule.errorMsg;
self.cache.push(function () {
var strategy = strategyAry.shift();
strategyAry.unshift(dom.value);
strategyAry.push(errorMsg);
return strategies[strategy].apply(dom, strategyAry);
});
})(rule)
}
};
Validator.prototype.start = function () {
for (var i = 0, validatorFunc; validatorFunc = this.cache[i++];) {
var errorMsg = validatorFunc();
if (errorMsg) {
return errorMsg;
}
}
};
/***********************客户调用代码**************************/
var registerForm = document.getElementById('registerForm');
var validataFunc = function () {
var validator = new Validator();
validator.add(registerForm.userName, [{
strategy: 'isNonEmpty',
errorMsg: '用户名不能为空'
}, {
strategy: 'minLength:6',
errorMsg: '用户名长度不能小于 10 位'
}]);
validator.add(registerForm.password, [{
strategy: 'minLength:6',
errorMsg: '密码长度不能小于 6 位'
}]);
validator.add(registerForm.phoneNumber, [{
strategy: 'isMobile',
errorMsg: '手机号码格式不正确'
}]);
validator.add(registerForm.email, [{
strategy: 'isEmail',
errorMsg: '邮箱不正确'
}]);
var errorMsg = validator.start();
return errorMsg;
}
registerForm.onsubmit = function () {
var errorMsg = validataFunc();
if (errorMsg) {
alert(errorMsg);
return false;
}
};
</script>
</body>
</html>