RuleGo RuleGo
🏠Home
  • Quick Start
  • Rule Chain
  • Standard Components
  • Extension Components
  • Custom Components
  • Visualization
  • RuleGo-Server
  • RuleGo-MCP-Server
  • AOP
  • Trigger
  • Advanced Topics
  • Performance
  • Standard Components
  • Extension Components
  • Custom Components
  • Components Marketplace
  • Overview
  • Quick Start
  • Routing
  • DSL
  • API
  • Options
  • Components
🔥Editor (opens new window)
  • RuleGo Editor (opens new window)
  • RuleGo Server (opens new window)
  • Github (opens new window)
  • Gitee (opens new window)
  • Changelog (opens new window)
  • English
  • 简体中文
🏠Home
  • Quick Start
  • Rule Chain
  • Standard Components
  • Extension Components
  • Custom Components
  • Visualization
  • RuleGo-Server
  • RuleGo-MCP-Server
  • AOP
  • Trigger
  • Advanced Topics
  • Performance
  • Standard Components
  • Extension Components
  • Custom Components
  • Components Marketplace
  • Overview
  • Quick Start
  • Routing
  • DSL
  • API
  • Options
  • Components
🔥Editor (opens new window)
  • RuleGo Editor (opens new window)
  • RuleGo Server (opens new window)
  • Github (opens new window)
  • Gitee (opens new window)
  • Changelog (opens new window)
  • English
  • 简体中文

广告采用随机轮播方式显示 ❤️成为赞助商
  • Quick Start

  • Rule Chain

  • Standard Components

  • Extension Components

  • Custom Components

  • Components marketplace

  • Visualization

  • AOP

    • AOP Overview
    • Before Advice
    • After Advice
    • Around Advice
      • Interface
      • Example
    • Start Advice
    • End Advice
    • Completed Advice
    • OnChainBeforeInit Advice
    • OnNodeBeforeInit 增强点
    • OnCreated Advice
    • OnReload Advice
    • OnDestroy Advice
    • builtin aspect

  • Trigger

  • Advanced Topic

  • RuleGo-Server

  • FAQ

  • Endpoint Module

  • Support

目录

Around Advice

Node around advice (Around Advice): executes before and after the node OnMsg method. This type of advice can replace the original node logic. It can implement node failover, retry, caching and other functions.

Before, After, Around Advice execution order: Around->Before->Around

# Interface

// Order returns the execution order, the smaller the value, the higher the priority
Order() int
// New creates a new instance
New() Aspect
// PointCut declares a cut-in point, used to determine whether to execute the advice
//For example: specify some component types or relationType to execute the aspect logic;return ctx.Self().Type()=="mqttClient"
PointCut(ctx RuleContext, msg RuleMsg, relationType string) bool
//Around is the advice that executes around the node OnMsg method. 
//If the return is false: the engine will not call the current node's OnMsg method,
//it needs to be manually triggered by Aspect, such as: ctx.Self().OnMsg (ctx, msg), or skip the current node's logic: ctx.TellNext .
//If it returns true: the engine will call the current node's OnMsg method.
Around(ctx RuleContext, msg RuleMsg, relationType string) (RuleMsg, bool)
1
2
3
4
5
6
7
8
9
10
11
12

The return value of the Around msg cannot affect the parameters of the next node; please use the before aspect or control it through ctx.TellNext(msg, relationType).

# Example

type AroundAspect struct {
	Name string
}

func (aspect *AroundAspect) Order() int {
	return 5
}

func (aspect *AroundAspect) New() types.Aspect {
	return &AroundAspect{}
}

func (aspect *AroundAspect) PointCut(ctx types.RuleContext, msg types.RuleMsg, relationType string) bool {
	return true
}

func (aspect *AroundAspect) Around(ctx types.RuleContext, msg types.RuleMsg, relationType string) (types.RuleMsg, bool) {
	fmt.Printf("debug Around before ruleChainId:%s,flowType:%s,nodeId:%s,msg:%+v,relationType:%s \n", ctx.RuleChain().GetNodeId().Id, "Around", ctx.Self().GetNodeId().Id, msg, relationType)
	msg.Metadata.PutValue(ctx.GetSelfId()+"_before", ctx.GetSelfId()+"_before")
	// Execute the current node logic
	ctx.Self().OnMsg(ctx, msg)
    //get out result
    //ctx.GetOut()
    fmt.Printf("debug Around after ruleChainId:%s,flowType:%s,nodeId:%s,msg:%+v,relationType:%s \n", ctx.RuleChain().GetNodeId().Id, "Around", ctx.Self().GetNodeId().Id, msg, relationType)
	//Return false,do not repeatedly execute this node logic outside of the framework.
	return msg, false
}

func TestAroundAspect(t *testing.T) {
var chain = `
{
  "ruleChain": {
    "id": "rule8848",
    "name": "test",
    "root": true
  },
  "metadata": {
    "nodes": [
      {
        "id": "s1",
        "type": "jsFilter",
        "name": "过滤",
        "debugMode": true,
        "configuration": {
          "jsScript": "return msg.role=='admin';"
        }
      },
      {
        "id": "s2",
        "type": "jsTransform",
        "name": "转换",
        "debugMode": true,
        "configuration": {
          "jsScript": "msg.userName=msg.userName+'NO-1';\n return {'msg':msg,'metadata':metadata,'msgType':msgType};"
        }
      }
    ],
    "connections": [
         {
        "fromId": "s1",
        "toId": "s2",
        "type": "False"
      }
    ]
  }
}
`
chainId := "test_around_aspect"

config := NewConfig()

ruleEngine, err := DefaultPool.New(chainId, []byte(chain), WithConfig(config), types.WithAspects(
&AroundAspect{Name: "AroundAspect1"},
))
if err != nil {
t.Error(err)
}
metaData := types.NewMetadata()
metaData.PutValue("productType", "test01")
msg := types.NewMsg(0, "TEST_MSG_TYPE1", types.JSON, metaData, "{\"temperature\":41}")

ruleEngine.OnMsg(msg)
time.Sleep(time.Millisecond * 200)
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
Edit this page on GitHub (opens new window)
Last Updated: 2025/04/02, 01:29:50
After Advice
Start Advice

← After Advice Start Advice→

Theme by Vdoing | Copyright © 2023-2025 RuleGo Team | Apache 2.0 License

  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式