0
点赞
收藏
分享

微信扫一扫

【设计模式】责任链3-横刀植入


紧接着上一篇的开始:
我们来说说普遍的解决方案,我们用一个类来模拟:
这个类模拟一个够过滤器链条:

package cn.edu.hpu.responsibility;


import java.util.List;
import java.util.ArrayList;


public class FilterChain {
List<Filter> filters=new ArrayList<Filter>();

//返回值是FilterChain只为了在Main中满足链条式的编程
public FilterChain addFilter(Filter f) {
this.filters.add(f);
return this;
}
}


可以添加过滤器。


我们如果把这个过滤器链条类看成一个“黑盒子”的话,它也算是一个巨大的过滤器。


于是它也应该有这个方法:


public String doFilter(String str) {
String r=str;
for(Filter f:filters){
r=f.doFilter(r);
}

return r;
}

也就是:


package cn.edu.hpu.responsibility;

import java.util.List;
import java.util.ArrayList;


public class FilterChain {
List<Filter> filters=new ArrayList<Filter>();

//返回值是FilterChain只为了在Main中满足链条式的编程
public FilterChain addFilter(Filter f) {
this.filters.add(f);
return this;
}

public String doFilter(String str) {
String r=str;
for(Filter f:filters){
r=f.doFilter(r);
}

return r;
}
}


当我们有FilterChain这个类的时候,MsgProcessor就会有些变化:


package cn.edu.hpu.responsibility;

public class MsgProcessor {
private String msg;

//把众多的过滤规则(不同的过滤器)整合在一起
//Filter[] filters={new HTMLFilter(),new SesitiveFilter()};
FilterChain fc;

public String getMsg() {
return msg;
}


public void setMsg(String msg) {
this.msg = msg;
}

public FilterChain getFc() {
return fc;
}


public void setFc(FilterChain fc) {
this.fc = fc;
}


public String process(){
//处理脚本语句和敏感字眼
return fc.doFilter(msg);
}
}


在Main中就应该这么写了:


package cn.edu.hpu.responsibility;


public class Main {
public static void main(String[] args) {
String msg="大家好:),<script>,偷盗,抢劫,我们要把设计模式学好";
MsgProcessor mp=new MsgProcessor();
mp.setMsg(msg);
FilterChain fc=new FilterChain();
fc.addFilter(new HTMLFilter())
.addFilter(new SesitiveFilter());//链条式写法
mp.setFc(fc);
String result=mp.process();
System.out.println(result);
}
}

运行结果:


大家好:),[script],和谐,帮助,我们要把设计模式学好




然后你不想要那个过滤规则了,就把.addFilter(new XxxxxFilter())去掉。或者写在配置文件里,直接改写配置文件就可以了。




过程解析图(FilterChain结构图):


【设计模式】责任链3-横刀植入_责任链



接下来问题就是,我如何在原来的FilterChain中加入另外一个FilterChain呢?


很简单,让FilterChain去实现Filter接口:


public class FilterChain implements Filter{.......



现在我们加一个笑脸过滤器:


package cn.edu.hpu.responsibility;

public class FaceFilter implements Filter {


@Override
public String doFilter(String str) {
//笑脸过滤器
String r=str.replace(":)", "^_^");
return r;
}


}


假设笑脸处理器属于第二个过滤器链条(FilterChain),我们在Main中来组合它们:


package cn.edu.hpu.responsibility;

public class Main {
public static void main(String[] args) {
String msg="大家好:),<script>,偷盗,抢劫,我们要把设计模式学好";
MsgProcessor mp=new MsgProcessor();
mp.setMsg(msg);
FilterChain fc=new FilterChain();
fc.addFilter(new HTMLFilter())
.addFilter(new SesitiveFilter());//链条式写法

FilterChain fc2=new FilterChain();
fc2.addFilter(new FaceFilter());

fc.addFilter(fc2);
mp.setFc(fc);
String result=mp.process();
System.out.println(result);
}
}

测试结果:


大家好^_^,[script],和谐,帮助,我们要把设计模式学好



下面我们考虑是这样的,在这里我们只是消息从过滤链这头发到了过滤链那头,直白点就是从客户端发到服务器端,一般来说服务器端也会给客户端一个反馈。那么假如说我想做一个从客户端到服务器端的过滤且从服务器端到客户端的过滤的链条,可行吗?如何实现?



重新写一些过滤器倒着去过滤服务器端的信息也不是不可以,但是代码会冗余。


我们的过滤器应该既处理过去的消息,又处理回来的消息。



好了,这样的代码该如何组织呢?



思路:


我们先写两个类,一个封装请求,一个封装反馈(模拟JavaWeb):


Request和Response类


package cn.edu.hpu.filter.web;


public class Request {
private String requestStr;


public String getRequestStr() {
return requestStr;
}


public void setRequestStr(String requestStr) {
this.requestStr = requestStr;
}


}


package cn.edu.hpu.filter.web;


public class Response {
private String responseStr;


public String getResponseStr() {
return responseStr;
}


public void setResponseStr(String responseStr) {
this.responseStr = responseStr;
}

}


现在我们的想法是这样的,如果我们把Request对象和Response对象交给处理器的话,这个处理器既能把request对象处理,又能处理回来的response对象。这个事情该怎么办呢?




举报

相关推荐

0 条评论