首页 > 其他分享 >说说设计模式~管道模式(pipeline)

说说设计模式~管道模式(pipeline)

时间:2023-06-30 15:56:16浏览次数:32  
标签:pipeline handlerModels class public 管道 handler new 设计模式 AbstractHandler

说明

复合的责任链,类似于管道模式,只要符合条件,说会向下传递,不会终止

算法说明

  • 按最高优先级去使用,符合就用,不符合就走下一个策略
  • 具体链条,有点像pipeline管道模式
    • BlackHandler ip=172.17.0.11
    • RateLimitHandler header=is-black
    • WriteBlackHandler header=real-black

继承抽象类

  • AbstractHandler 抽象的责任处理者
    • 抽象方法action,需要各个子类【具体的责任处理者】自己去实现
    • final修饰的方法,封装了实现细节,子类不能重写
    • setNextHandler方法,设置下一个链条的【责任处理者】
  • HandlerFactory 责任工厂
    • 通过一个责任处理列表,返回一个责任链条
    • 责任链条可以持久化到数据库里

责任链如果没有终止条件,就类似于pipeline管道了

graph TD Request[post body]-->A[BlackHandler] A --> B[RateLimitHandler] B --> C[WriteBlackHandler] C --> D[EndHandler]

测试代码

抽象处理者

public abstract class AbstractHandler<T> {

	private AbstractHandler nextHandler;

	public final void setNextHandler(AbstractHandler nextHandler) {
		this.nextHandler = nextHandler;
	}

	protected abstract void action(T body);

	// final表示不允许子类重写
	public final void handleRequest(T body) {
		action(body);

		if (this.nextHandler != null)
			this.nextHandler.handleRequest(body);
	}

}

具体处理者

public class BlackHandler extends AbstractHandler<Request> {

	private static final Logger logger = LoggerFactory.getLogger(CouponHandler.class);

	@Override
	public void action(Request body) {
		logger.info("BlackHandler 处理");
	}

}
public class RateLimitHandler extends AbstractHandler<Request> {

	private static final Logger logger = LoggerFactory.getLogger(CouponHandler.class);

	@Override
	protected void action(Request body) {
		logger.info("RateLimitHandler 处理");

	}

}
public class WriteBlackHandler extends AbstractHandler<Request> {

	private static final Logger logger = LoggerFactory.getLogger(CouponHandler.class);

	@Override
	protected void action(Request body) {
		logger.info("WriteBlackHandler 处理");

	}

}
public class EndHandler extends AbstractHandler<Request> {

	private static final Logger logger = LoggerFactory.getLogger(CouponHandler.class);

	@Override
	protected void action(Request body) {
		logger.info("EndHandler 处理");

	}

}

处理者工厂和请求数据体

public class HandlerFactory {

	public static <T extends Request> AbstractHandler<T> createHandler(List<AbstractHandler<T>> handlerModels) {
		AbstractHandler<T> handler = null;
		AbstractHandler<T> previousHandler = null;

		for (AbstractHandler<T> currentHandler : handlerModels.stream().collect(Collectors.toList())) {

			if (previousHandler != null) {
				previousHandler.setNextHandler(currentHandler);
			}
			else {
				handler = currentHandler;
			}
			previousHandler = currentHandler;

		}

		return handler;
	}

}
@AllArgsConstructor
@NoArgsConstructor
@Data
public class Request {

	private String ip;

	private String userId;

}

测试用例

 public static void main(String[] args) {
		List<AbstractHandler<Request>> abstractHandlers = Arrays.asList(new RateLimitHandler(), new BlackHandler(),
				new WriteBlackHandler(),new EndHandler());
		AbstractHandler<Request> abstractHandler = HandlerFactory.createHandler(abstractHandlers);
		abstractHandler.handleRequest(new Request("1", "user1"));
	}

如果希望将你的责任链处理存储到数据库中,那个在handleFactory里,就需要接口className了,例如下面的代码:

public static Handler handlerFactory() {
		List<HandlerModel> handlerModels = new ArrayList<>();
		handlerModels
				.add(new HandlerModel("CouponHandler", "com.lind.common.pattern.chinaorder.handler.CouponHandler", 1));
		handlerModels.add(
				new HandlerModel("DiscountHandler", "com.lind.common.pattern.chinaorder.handler.DiscountHandler", 2));
		handlerModels.add(
				new HandlerModel("BigGiftHandler", "com.lind.common.pattern.chinaorder.handler.BigGiftHandler", 3));
		handlerModels.add(new HandlerModel("VipHandler", "com.lind.common.pattern.chinaorder.handler.VipHandler", 4));
		return createHandler(handlerModels);
	}

	private static Handler createHandler(List<HandlerModel> handlerModels) {
		Handler handler = null;
		Handler previousHandler = null;

		for (HandlerModel handlerModel : handlerModels.stream().sorted().collect(Collectors.toList())) {
			try {
				Handler currentHandler = (Handler) Class.forName(handlerModel.getClassPath()).newInstance();
				if (previousHandler != null) {
					previousHandler.setNextHandler(currentHandler);
				}
				else {
					handler = currentHandler;
				}
				previousHandler = currentHandler;
			}
			catch (InstantiationException | IllegalAccessException | ClassNotFoundException e) {
				throw new RuntimeException(e);
			}
		}

		return handler;
	}

标签:pipeline,handlerModels,class,public,管道,handler,new,设计模式,AbstractHandler
From: https://www.cnblogs.com/lori/p/17516975.html

相关文章

  • Java 设计模式实战系列—工厂模式
    在Java开发中,对象的创建是一个常见的场景,如果对象的创建和使用都写在一起,代码的耦合度高,也不利于后期的维护。我们可以使用工厂模式来解决这个问题,工厂模式是一个创建型模式,将对象的创建和使用分离开来,降低代码的耦合度,提高程序的可维护性和扩展性。工厂模式应用场景调用方......
  • 什么是设计模式?
    普遍认同的2种软件模式:设计模式和架构模式。重构模式模式的定义:每个模式都描述了一个问题,这个问题在我们的环境中一遍一遍出现。且模式还给出了这个问题的核心解决方案,这个方案可以被一次次地重用,而无需每次都从头开始。  ......
  • redis之管道(事物)
    redis-py默认在执行每次请求都会创建(连接池申请连接)和断开(归还连接池)一次连接操作,如果想要在一次请求中指定多个命令,则可以使用pipline实现一次请求指定多个命令,并且默认情况下一次pipline是原子性操作。使用管道也就是相当于开启了事物,要么都执行成功,要么都执行失败importred......
  • 设计模式之单例模式
    很重要的一个设计模式!!介绍:它和工厂模式一样,都属于创建型模式,用于类进行初始化。单例模式保证一个类只会被实例化一次。1.线程安全的懒汉单例模式publicclassSingletonTwo{privatevolatilestaticSingletonTwosingletonTwo;privateSingletonTwo(){}......
  • 10redis列表操作,其他操作,redis管道,django中使用redis,django缓存,序列化json和pickle,cel
    字符串和字节转换的两种方式#字符串和字节转换的两种方式 -decode,encode-直接类型转换-bytes格式的16进制,2进制,10进制的显示#字符串需要用encode,bytes格式需要用decode,但是有时候忘了#可以直接进行强转b1=bytes(s,encoding='utf-8') print(......
  • 深入浅出设计模式 - 中介者模式
    博主介绍:✌博主从事应用安全和大数据领域,有8年研发经验,5年面试官经验,Java技术专家✌Java知识图谱点击链接:体系化学习Java(Java面试专题)......
  • 精选Android中高级面试题:性能优化,JNI,设计模式
    性能优化1、图片的三级缓存中,图片加载到内存中,如果内存快爆了,会发生什么?怎么处理?参考回答:首先我们要清楚图片的三级缓存是如何的:如果内存足够时不回收。内存不够时就回收软引用对象2、内存中如果加载一张500*500的png高清图片。应该是占用多少的内存?不考虑屏幕比的话:占用内存......
  • 说说设计模式~责任链模式
    回到目录责任链模式它是一种设计模块,主要将操作流程与具体操作解耦,让每个操作都可以设置自己的操作流程,这对于工作流应用是一个不错的选择!下面是官方标准的定义:责任链模式是一种设计模式。在责任链模式里,很多对象由每一个对象对其下家的引用而连接起来形成一条链。请求在这个链......
  • 你用过哪些设计模式(一)?
    什么是设计模式?一些经验总结的最佳实践!是不是必须要用?并不是,但是既然已经说是最佳实践了,该用的地方,你不用,就有些违背常理了。一、单例这个或许是最最最常见,也是最最最常用的了。为什么要用单例模式?因为只需要一个对象就够了(有时候只能有一个,有时候是不需要有多个)。对象的......
  • 设计模式--适配器模式 Adapter
    设计模式 适配器模式Adapter 定义一个规则--->和尚吃斋念经打坐撞钟习武 缺省适配器模式 鲁智深鲁达形态丑陋面貌凶顽 此人上应天星心地刚直虽时下凶顽命中驳杂久后却得清净证果非凡汝等皆不及他 就是在一个接口跟正常子......