当前位置: 首页 > 后端技术 > Java

【设计模式系列】之这才是责任链模式的优雅使用方式

时间:2023-04-02 00:38:48 Java

【设计模式系列】责任链模式的优雅使用方式。公共类成员{私有字符串登录名;私人字符串登录密码;私有字符串角色名;publicMember(StringloginName,StringloginPass){this.loginName=loginName;this.loginPass=登录密码;StringgetLoginPass(){返回登录密码;}publicStringgetRoleName(){返回角色名;}publicvoidsetRoleName(StringroleName){this.roleName=roleName;}@OverridepublicStringtoString(){return"Member{"+"loginName='"+loginName+'\''+",loginPass='"+loginPass+'\''+'}';然后我们来看一段我们经常写的代码。publicclassMemberService{publicvoidlogin(StringloginName,StringloginPass){if(StringUtils.isEmpty(loginName)||StringUtils.isEmpty(loginPass)){System.out.println("用户名密码验证成功,可以下去执行");返回;}System.out.println("用户名和密码不为空,可以继续执行");会员member=checkExists(loginName,loginPass);如果(null==成员){System.out。println("用户不存在");返回;}System.out.println("登录成功!");if(!"Administrator".equals(member.getRoleName())){System.out.println("您不是管理员,没有操作权限");返回;}System.out.println("允许运行");}privateMembercheckExists(StringloginName,StringloginPass){Membermember=newMember(loginName,loginPass);成员.setRoleName("管理员");回归会员;}publicstaticvoidmain(String[]args){MemberServiceservice=newMemberSe服务();service.login("tom","666");}}上面的代码中主要做了登录前的数据校验,判断逻辑是时序的。先进行非空判断,再检查账号是否有效,最后获取用户角色。根据用户角色拥有的权限匹配是否有操作权限。那么这样的检查代码一般是少不了的,但是写在具体的业务代码中就很臃肿了。因此,我们可以在不影响代码美观的情况下,使用责任链模型将这些检查步骤串联起来,可以让我们在编码时更加专注于某个特定的业务逻辑处理。接下来,使用责任链模式优化代码,首先创建一个Handler类。公共抽象类处理程序{受保护的处理程序链;publicvoidnext(Handlerhandler){this.chain=handler;}publicabstractvoiddoHandle(成员成员);}然后创建非空校验ValidateHandler类,登录校验LoginHandler类和权限校验AuthHandler类。ValidateHandler类的代码如下。publicclassValidateHandlerextendsHandler{publicvoiddoHandle(Membermember){if(StringUtils.isEmpty(member.getLoginName())||StringUtils.isEmpty(member.getLoginPass())){System.out.println("用户名或密码为空");返回;}System.out.println("用户名密码验证成功,可以继续执行");chain.doHandle(成员);}}LoginHandler类的代码如下。publicclassLoginHandlerextendsHandler{publicvoiddoHandle(Membermember){System.out.println("登录成功!");member.setRoleName("管理员");chain.doHandle(成员);}}AuthHandler类代码如下。publicclassAuthHandlerextendsHandler{publicvoiddoHandle(Membermember){if(!"Administrator".equals(member.getRoleName())){System.out.println("您不是管理员,没有权限操作");返回;}System.out.println("你是管理员,你可以操作");接下来修改MemberService中的代码。其实只需要将之前定义的Handlers按照业务需求连接起来就可以形成一条链。能。publicclassMemberService{publicvoidlogin(StringloginName,StringloginPass){HandlervalidateHandler=newValidateHandler();处理程序loginHandler=newLoginHandler();处理程序authHandler=newAuthHandler();validateHandler.next(loginHandler);授权处理程序);validateHandler.doHandle(新成员(登录名,登录密码));}}最后,编写客户端调用代码。公共类测试{publicstaticvoidmain(String[]args){MemberServiceservice=newMemberService();service.login("tom","666");}}运行结果如下图所示。其实我们平时使用的很多权限验证框架都是利用了这个原理。将各个维度的权限处理解耦后,串联起来,只处理各自的职责。如果责任与你无关,就丢给链条中的下一个Handler,俗称“踢球”。2 责任链模式和建造者模式结合使用是因为责任链模式具有链式结构,而在上面的代码中,负责组装链式结构的角色是MemberService。当链式结构较长时,MemberService的工作会很繁琐,而且MemberService的代码比较臃肿,而且后续改变处理器或消息类型时,必须在MemberService中修改,不符合开闭原则。出现这些问题的原因是链条结构的装配过于复杂。对于复杂结构的创建,我们自然会想到建造者模式。使用构建器模式,可以自动链接MemberService指定的处理节点对象。客户只需要指定处理节点对象,其他不需要关心,而且客户指定的处理节点对象顺序不同,构建的链结构也不同。我们来修改一下,先修改Handler的代码。公共抽象类Handler{受保护的处理程序链;publicvoidnext(Handlerhandler){this.chain=handler;}publicabstractvoiddoHandle(成员成员);publicstaticclassBuilder{privateHandlerhead;私人处理程序尾部;publicBuilderaddHandler(Handlerhandler){if(this.head==null){this.head=this.tail=handler;归还这个;}这个尾巴。下一个(处理程序);this.tail=处理程序;归还这个;}publicHandlerbuild(){returnthis.head;}}}然后修改MemberService的代码。publicclassMemberService{publicvoidlogin(StringloginName,StringloginPass){Handler.Builderbuilder=newHandler.Builder();builder.addHandler(newValidateHandler()).addHandler(newLoginHandler()).addHandler(newAuthHandler());builder.build().doHandle(新成员(loginName,loginPass));因为builder模式构建的是nodehandlers,所以我们使用Builder作为Handler的静态内部类,并且因为客户端不需要链式组装,所以也可以将链式组装方法next()方法设置为private,使处理程序更高度聚合。代码如下。公共抽象类Handler{受保护的处理程序链;privatevoidnext(Handlerhandler){this.chain=handler;}...}通过这个案例,大家应该已经感受到responsibilitychain和builderup相结合的本质了。如果本文对您有帮助,请关注并点赞;有什么建议也可以留言或私信。您的支持是我坚持创作的动力。如果您需要设计模式、源码等相关学习资料,可以在这里免费获取资料,后续我们会持续更新设计模式系列。欢迎关注~~~