背景
常常在做像注册,条件搜索会做表单提交,但发请求前会做各种验证,要把规则验证完才能提交。
分析
大多数会在一个验证的方法里写很多if判断语句,判断不通过就return false, 判断通过就return true,让代码显得逻辑很乱。比如说这样:
function check(form){
// 时间需要满足的条件
if(form.date){}
// 地区需要满足的条件
if(form.area){}
// 还有不同规则组合需要满足的条件
if(form.rules1 && form.rules2){}
}
整个看下来这个方法非常臃肿,当然这个时候会改进一下,把不同规则的验证单独写一个方法,但还是会有一个不好的地方,那就是不能在某个规则不通过的条件下能及时退出这个方法,否则就只有在每个单独验证规则的方法后面再写一个判断是false还是true。
解决
这个时候可以考虑引入职责链模式,网上讨论职责链模式的文章有很多,比如说这篇
那现在换成职责链模式的做法
class Chain{
constructor(fn) {
this.fn = fn;
this.successor = null;
}
setNext(successor) {
return (this.successor = successor);
}
passRequest() {
const res = this.fn.apply(this, arguments);
if(res === 'nextSuccesor'){
return this.successor && this.successor.passRequest.apply(this.successor, arguments);
}
return res;
}
}
let checkDate = function(form) {
if(pass){
return true;
}else {
return 'nextSuccesor';
}
}
let checkArea = function(form) {
if(pass){
return true;
}else {
return 'nextSuccesor';
}
}
// 记得最后一个规则要返回true或者false
let checkRules1AndRules2 = function(form) {
if(pass){
return true;
}else {
return 'nextSuccesor';
}
}
let checkDateChain = new Chain(checkDate);
let checkAreaChain = new Chain(checkArea);
let checkRules1AndRules2Chain = new Chain(checkRules1AndRules2);
// 按顺序验证规则
checkDateChain.setNext(checkAreaChain).setNext(checkRules1AndRules2Chain);
return checkDateChain.passRequest();
按这样写的方式就实现了低耦合,还可以按顺序,比如说有些规则是只要填了日期,其他的都不需要验证了,就可以放在最前面。脑子里也会有更清晰的顺序。