一、责任链定义
为了避免请求发送者与多个请求处理者耦合在一起,于是将所有请求的处理者通过前一对象记住其下一个对象的引用而连成一条链;当有请求发生时,可将请求沿着这条链传递,直到有对象处理它为止。
二、逐步引入
1.情景引入
- 在论坛中发表文章
- 后台要经过信息处理才可以发表或者进入数据库
所以在这里面会有过滤链,去看看文章有没有敏感词或黑客代码这些东西,然后进行过滤,接下来我们对其模拟情景
2.情景编写代码
2.1 初步代码
public class Main {
public static void main(String[] args) {
Msg msg = new Msg();
msg.setMsg("大家好:),<script>,欢迎访问baidu.com,520这个世界");
// 处理msg
String r = msg.getMsg();
r = r.replace('<','[');
r = r.replace('>',']');
msg.setMsg(r);
r = r.replaceAll("520","188");
System.out.println(r);
}
}
class Msg{
String name;
String msg;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
@Override
public String toString() {
return "Msg{" +
"name='" + name + '\'' +
", msg='" + msg + '\'' +
'}';
}
}
2.2 引入过滤器
在上面的写法,在功能比较复杂的时候,代码会非常乱,而且添加新功能是非常麻烦的,可拓展性是不好的,所以采取拓展性比较好的方案,例如使用过滤器
public class Main {
public static void main(String[] args) {
Msg msg = new Msg();
msg.setMsg("大家好:),<script>,欢迎访问baidu.com,520这个世界");
new HTMLFilter().doFilter(msg);
new SensitiveFilter().doFilter(msg);
System.out.println(msg);
}
}
class Msg{
String name;
String msg;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
@Override
public String toString() {
return "Msg{" +
"name='" + name + '\'' +
", msg='" + msg + '\'' +
'}';
}
}
interface Filter{
void doFilter(Msg m);
}
class HTMLFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replace('<','[');
r = r.replace('>',']');
m.setMsg(r);
}
}
class SensitiveFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replaceAll("520","188");
m.setMsg(r);
}
}
2.3 把过滤器串联起来成过滤链
2.3.1 使用ArrayList
public class Main {
public static void main(String[] args) {
Msg msg = new Msg();
msg.setMsg("大家好:),<script>,欢迎访问baidu.com,520这个世界");
List<Filter> filters = new ArrayList<>();
filters.add(new HTMLFilter());
filters.add(new SensitiveFilter());
for (Filter f : filters) {
f.doFilter(msg);
}
System.out.println(msg);
}
}
class Msg{
String name;
String msg;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
@Override
public String toString() {
return "Msg{" +
"name='" + name + '\'' +
", msg='" + msg + '\'' +
'}';
}
}
interface Filter{
void doFilter(Msg m);
}
class HTMLFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replace('<','[');
r = r.replace('>',']');
m.setMsg(r);
}
}
class SensitiveFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replaceAll("520","188");
m.setMsg(r);
}
}
2.3.2 把它们穿成链条
public class Main {
public static void main(String[] args) {
Msg msg = new Msg();
msg.setMsg("大家好:),<script>,欢迎访问baidu.com,520这个世界");
FilterChain fc = new FilterChain();
fc.add(new HTMLFilter());
fc.add(new SensitiveFilter());
fc.doFilter(msg);
System.out.println(msg);
}
}
class Msg{
String name;
String msg;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
@Override
public String toString() {
return "Msg{" +
"name='" + name + '\'' +
", msg='" + msg + '\'' +
'}';
}
}
interface Filter{
void doFilter(Msg m);
}
class HTMLFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replace('<','[');
r = r.replace('>',']');
m.setMsg(r);
}
}
class SensitiveFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replaceAll("520","188");
m.setMsg(r);
}
}
class FilterChain{
List<Filter> filters = new ArrayList<>();
public void add(Filter f){
filters.add(f);
}
public void doFilter(Msg msg){
for (Filter f : filters) {
f.doFilter(msg);
}
}
}
2.3.3 两者的区别
其实每个FilterChain可以和别的FilterChain连在一起的,若想过滤链合并,就让过滤链实现Filter的接口
public class Main {
public static void main(String[] args) {
Msg msg = new Msg();
msg.setMsg("大家好:),<script>,欢迎访问baidu.com,520这个世界");
FilterChain fc = new FilterChain();
fc.add(new HTMLFilter()).add(new SensitiveFilter());
FilterChain fc2 = new FilterChain();
fc2.add(new FaceFilter()).add(new URLFilter());
//过滤链合并
fc.add(fc2);
fc.doFilter(msg);
System.out.println(msg);
}
}
class Msg{
String name;
String msg;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
@Override
public String toString() {
return "Msg{" +
"name='" + name + '\'' +
", msg='" + msg + '\'' +
'}';
}
}
interface Filter{
void doFilter(Msg m);
}
class HTMLFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replace('<','[');
r = r.replace('>',']');
m.setMsg(r);
}
}
class SensitiveFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replaceAll("520","188");
m.setMsg(r);
}
}
class FaceFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replace(":)","~_~");
m.setMsg(r);
}
}
class URLFilter implements Filter{
@Override
public void doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replaceAll("baidu.com","www.baidu.com");
m.setMsg(r);
}
}
// 若想过滤链合并,就让过滤链实现Filter的接口
class FilterChain implements Filter{
List<Filter> filters = new ArrayList<>();
public FilterChain add(Filter f){
filters.add(f);
return this;
}
public void doFilter(Msg msg){
for (Filter f : filters) {
f.doFilter(msg);
}
}
}
3.由FilterChian中的某一个Filter决定Filter决定是否继续
public class Main {
public static void main(String[] args) {
Msg msg = new Msg();
msg.setMsg("大家好:),<script>,欢迎访问baidu.com,520这个世界");
FilterChain fc = new FilterChain();
fc.add(new HTMLFilter()).add(new SensitiveFilter());
FilterChain fc2 = new FilterChain();
fc2.add(new FaceFilter()).add(new URLFilter());
//过滤链合并
fc.add(fc2);
fc.doFilter(msg);
System.out.println(msg);
}
}
class Msg{
String name;
String msg;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
@Override
public String toString() {
return "Msg{" +
"name='" + name + '\'' +
", msg='" + msg + '\'' +
'}';
}
}
// 若想其中一个Filter中止返回,则应该在Filter中让doFilter返回boolean类型
interface Filter{
boolean doFilter(Msg m);
}
class HTMLFilter implements Filter{
@Override
public boolean doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replace('<','[');
r = r.replace('>',']');
m.setMsg(r);
return true;
}
}
class SensitiveFilter implements Filter{
@Override
public boolean doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replaceAll("520","188");
m.setMsg(r);
return false;
}
}
class FaceFilter implements Filter{
@Override
public boolean doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replace(":)","~_~");
m.setMsg(r);
return true;
}
}
class URLFilter implements Filter{
@Override
public boolean doFilter(Msg m) {
// 处理msg
String r = m.getMsg();
r = r.replaceAll("baidu.com","www.baidu.com");
m.setMsg(r);
return true;
}
}
// 若想过滤链合并,就让过滤链实现Filter的接口
class FilterChain implements Filter{
List<Filter> filters = new ArrayList<>();
public FilterChain add(Filter f){
filters.add(f);
return this;
}
public boolean doFilter(Msg msg){
for (Filter f : filters) {
if (!f.doFilter(msg))
return false;
}
return true;
}
}