责任链模式

顾名思义,责任链模式(Chain of Responsibility Pattern)为请求创建了一个接收者对象的链。这种模式给予请求的类型,对请求的发送者和接收者进行解耦。这种类型的设计模式属于行为型模式。

在这种模式中,通常每个接收者都包含对另一个接收者的引用。如果一个对象不能处理该请求,那么它会把相同的请求传给下一个接收者,依此类推。

这样,请求发送者与接收者耦合在一起,让多个对象都有可能接收请求,将这些对象连接成一条链,并且沿着这条链传递请求。

e.g.

实现一个消息通知,例如某个告警通知,要通过各种方式(短信,邮件等)通知。

首先抽象NotifyChain

public abstract class NotifyChain<T> {

    private NotifyChain nextHandler;

    /**
     * 控制方法。
     * 这里不对结果R进行校验,直接有下一个处理器,就处理。即走完所有的通知方式
     * 
     * @param notifyDTO
     * @return
     */
    public R<T> handle(NotifyDTO notifyDTO) {
        R<T> notifyResultDTO = this.doNotify(notifyDTO);
        if (Objects.nonNull(nextHandler)) {
            return this.nextHandler.handle(notifyDTO);
        }
        return notifyResultDTO;
    }

    /**
     * 实际的通知方法
     *
     * @param notifyDTO
     * @return NotifyResultDTO
     */
    public abstract R<T> doNotify(NotifyDTO notifyDTO);

}

各个通知方式继承该类即可,例如

WorkWeiXinNotifyHandler     // 企业微信
SmsNotifyHandler            // 短信
EmailNotifyHandler          // 邮件
//...

编排各个handler的链式关系

如果是Spring项目,可以配合@Order注解进行各个处理器的链式关系

public class NotifyManager {

    private final List<NotifyChain> notifyChainList;

    @Bean("notifyChain")
    public NotifyChain notifyChain() {
        int size = notifyChainList.size();
        for (int i = 0; i < size; i++) {
            if (i == size - 1) {
                notifyChainList.get(i).setNextHandler(null);
            } else {
                notifyChainList.get(i).setNextHandler(notifyChainList.get(i + 1));
            }
        }
        return notifyChainList.get(0);
    }
}

调用

// 通知
NotifyDTO notifyDTO = NotifyDTO.builder()
    .title(title)
    .content(content)
    .build();
notifyChain.handle(notifyDTO);