BaseResponsibilityChainHandler.java 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. package cn.nosum.support.chain;
  2. import lombok.Data;
  3. import lombok.extern.slf4j.Slf4j;
  4. import org.springframework.util.StopWatch;
  5. import java.util.UUID;
  6. import java.util.function.Predicate;
  7. /**
  8. * 链的处理节点处理器。
  9. *
  10. * @author Young
  11. */
  12. @Data
  13. @Slf4j
  14. public class BaseResponsibilityChainHandler<T extends Processor> {
  15. public BaseResponsibilityChainHandler(String name, Predicate<T> hitPredicate,
  16. Predicate<T> handleAction, BaseResponsibilityChainHandler<T> next) {
  17. this.name = name;
  18. this.hitPredicate = hitPredicate;
  19. this.handleAction = handleAction;
  20. this.next = next;
  21. }
  22. /**
  23. * 节点ID
  24. */
  25. private UUID id = UUID.randomUUID();
  26. /**
  27. * 节点的名称
  28. */
  29. private String name;
  30. /**
  31. * 提供给外部注册的判断是否命中当前责任链节点的逻辑块
  32. */
  33. private Predicate<T> hitPredicate;
  34. /**
  35. * 提供给外部注册的责任链上下文处理的逻辑块, 返回值为true时,将会继续执行下一个节点
  36. */
  37. private Predicate<T> handleAction;
  38. /**
  39. * 下一个处理节点
  40. */
  41. private BaseResponsibilityChainHandler<T> next;
  42. /**
  43. * 节点排序
  44. */
  45. private int sort;
  46. /**
  47. * 责任链上下文处理
  48. *
  49. * @param context 当前处理的上下文信息
  50. */
  51. public boolean handle(T context) {
  52. try {
  53. if (!hit(context)) {
  54. if (next != null) {
  55. // 如果当前节点不执行,则重置isCurrentExecuteNode;否则下面的节点都不会执行
  56. context.setExecuteNextNode(true);
  57. log.info("未命中节点:{} 执行下一个节点:{}.", name, next.name);
  58. return next.handle(context);
  59. }
  60. log.info("未命中节点并且不存在下一个节点:{} ",name);
  61. return false;
  62. }
  63. log.info("命中节点: {}", name);
  64. if (handleAction != null) {
  65. // 执行逻辑
  66. if (handleAction.test(context)) {
  67. if (next != null) {
  68. log.info("命中节点:{} 执行下一个节点:{}", name, next.name);
  69. context.addNodeLog(name);
  70. return next.handle(context);
  71. }
  72. log.info("命中节点:{} 不存在下一个节点", name);
  73. } else {
  74. log.info("命中节点:{} 中断后续节点执行", name);
  75. }
  76. }
  77. StopWatch stopWatch = context.getStopWatch();
  78. if (stopWatch.getTaskCount() > 0) {
  79. log.info("\n"+context.getStopWatch().prettyPrint());
  80. }
  81. context.addNodeLog(name);
  82. log.info("当前执行的节点为: [{}]", context.prettyPrint());
  83. return true;
  84. } catch (ResponsibilityChainException e) {
  85. throw e;
  86. } catch (Exception e) {
  87. throw new ResponsibilityChainException(name, e);
  88. }
  89. }
  90. /**
  91. * 判断是否命中当前责任链节点
  92. *
  93. * @param context {@link BaseContext} 当前处理的上下文信息
  94. */
  95. public boolean hit(T context) {
  96. if (hitPredicate != null) {
  97. return hitPredicate.test(context);
  98. }
  99. return true;
  100. }
  101. public int getSort() {
  102. return sort;
  103. }
  104. }