责任链设计模式
责任链设计模式的典型场景:
- 一个对象或请求,需要验证一系列的判断,依次执行,顺序不限;核心目的:用于解耦发送方和处理方
带优先级的责任链设计模式:
某些情况下,责任链Handler需要有先后顺序执行
实现
-
ConcreteHandler嵌套BaseHandler,间接实现 BaseHandler的 方法SetNext、HandleNext、Priority
-
同时ConcreteHandler实现业务Handle方法
-
ByPriority,实现了sort方法的所有方法,实现sort.Sort接口要求
go
type Handler interface {
SetNext(handler Handler)
Handle(currentValue, PreviousValue float64) (handled bool)
Priority() int
}
type BaseHandler struct {
next Handler
priority int // 处理器的优先级
}
func (h *BaseHandler) SetNext(handler Handler) {
h.next = handler
}
func (h *BaseHandler) HandleNext(currentValue, PreviousValue float64) (handled bool) {
if h.next != nil {
return h.next.Handle(currentValue, PreviousValue)
}
return false
}
func (h *BaseHandler) Priority() int {
return h.priority
}
type ConcreteHandler struct {
BaseHandler
handleFunc func(currentValue, PreviousValue float64) bool // 处理函数
}
func (h *ConcreteHandler) Handle(currentValue, PreviousValue float64) (handled bool) {
// 如果 handleFunc 处理请求的结果为(返回 true),则停止处理
if h.handleFunc(currentValue, PreviousValue) {
return false
}
// 否则,传递给下一个处理器
return h.HandleNext(currentValue, PreviousValue)
}
func NewConcreteHandler(priority int, handleFunc func(currentValue, PreviousValue float64) bool) Handler {
return &ConcreteHandler{
BaseHandler: BaseHandler{priority: priority},
handleFunc: handleFunc,
}
}
type ByPriority []Handler
func (a ByPriority) Len() int { return len(a) }
func (a ByPriority) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
// 1==>优先级最大
func (a ByPriority) Less(i, j int) bool { return a[i].Priority() < a[j].Priority() }
业务逻辑,实现Handler
- 通过NewConcreteHandler,构建业务Handler,返回业务处理结果;true则不再往下执行
go
handlers := []Handler{
NewConcreteHandler(1, func(_currentValue, _PreviousValue float64) bool {
pRule := ConstructExpression(PriorityRules)
expr, _ := govaluate.NewEvaluableExpression(pRule)
con := make(map[string]interface{})
con[ExpressionCurrentKey] = _currentValue
con[ExpressionPreviousValueKey] = _PreviousValue
result, _ := expr.Evaluate(con)
if result.(bool) {
fmt.Printf("当前值%v 前值%v 结果%v 触发表达式:%v\n",
con[ExpressionCurrentKey], con[ExpressionPreviousValueKey], result, pRule)
}
return result.(bool)
}),
NewConcreteHandler(2, func(_currentValue, _PreviousValue float64) bool {
rule := ConstructExpression(Rules)
expr, _ := govaluate.NewEvaluableExpression(rule)
con := make(map[string]interface{})
con[ExpressionCurrentKey] = _currentValue
con[ExpressionPreviousValueKey] = _PreviousValue
result, _ := expr.Evaluate(con)
if result.(bool) {
fmt.Printf("当前值%v 前值%v 结果%v 触发表达式:%v\n",
con[ExpressionCurrentKey], con[ExpressionPreviousValueKey], result, rule)
}
return result.(bool)
}),
}
构建链以及调用
- 根据场景,可以构建多个Handler,并根据优先级执行排序并依次执行SetNext方法,使得对象可以经由多个逻辑依次处理,直至处理结束,实现责任链的执行。
go
sort.Sort(ByPriority(handlers))
for i := 0; i < len(handlers)-1; i++ {
handlers[i].SetNext(handlers[i+1])
}
for _, handler := range handlers {
if !handler.Handle(currentValue.Value, *alertRule.PreviousValue) {
// break
return true, nil
}
}
return false, nil