Go运行Grule引擎实现计费规则管理

Go运行Grule引擎实现计费规则管理

  • github位置: https://github.com/hyperjumptech/grule-rule-engine
shell 复制代码
# 安装grule模块
go get -u github.com/hyperjumptech/grule-rule-engine

Grule的示例代码

  • 示例位置: https://github.com/hyperjumptech/grule-rule-engine/tree/master/examples

    • 使用 go test 运行
    shell 复制代码
    cd examples
    $ go test NumberExponentExample_test.go 
    ok      command-line-arguments  0.011s
  • Grule规则

    • rule {} 表示规则
    • salience 10 表示优先级为10
      • 优先级高的先执行
go 复制代码
type ExponentData struct {
	Check float64
	Set   float64
}

/*
    条件部分 (when):
    当ExponentData 结构体中的 Check 等于 6.67428e-11 时,规则会触发
    动作部分 (then):
    当条件满足时,将 ExponentData 结构体中的 Set 设置为 .12345E+5
    然後,使用 Retract("ExponentCheck") 將這個规则從工作记忆中移除,
    以防止它再次被觸發。
*/

const ExponentRule = `
rule  ExponentCheck  "User Related Rule"  salience 10 {
	when 
		ExponentData.Check == 6.67428e-11
	Then
		ExponentData.Set = .12345E+5;
		Retract("ExponentCheck");
}
`
// 往下是 运行"github.com/stretchr/testify/assert"的测试代码, 忽略
func TestEvaluateAndAssignExponentNumber(t *testing.T) {
	exponent := &ExponentData{
		Check: 6.67428e-11,
		Set:   0,
	}
	...
}
  • 总结:Grule规则使用 when 判断条件, 当条件满足时执行 then

编写计费规则代码

  • 仿照示例代码,编写计费规则代码

    • 对云服务器 cpu 计费, 每小时 0.05元 * 核数
    • 对云服务器 内存 计费, 每小时 0.01元 * GB
    go 复制代码
    const (
      rule = `
      rule CalculateCost "Calculate the total cost based on CPU and Memory usage" {
        when 
            CloudResource.CPU > 0 &&
            CloudResource.Memory > 0
        then
            costPerCPUHour = 0.05;
            costPerGBMemoryHour = 0.01;
            cpuCost = CloudResource.CPU * costPerCPUHour;
            memoryCost = CloudResource.Memory * costPerGBMemoryHour;
            CloudResource.TotalCost = cpuCost + memoryCost;
            Retract("CalculateCost");
      }
      `
    )
    • cpu 内存 总费用 封装为结构体
    go 复制代码
    type CloudResource struct {
        CPU       float64
        Memory    float64
        TotalCost float64
    }
  • 使用 go test 执行完整代码

go 复制代码
package example

import (
    "testing"

    "github.com/hyperjumptech/grule-rule-engine/ast"
    "github.com/hyperjumptech/grule-rule-engine/builder"
    "github.com/hyperjumptech/grule-rule-engine/engine"
    "github.com/hyperjumptech/grule-rule-engine/pkg"
    "github.com/stretchr/testify/assert"
)

const (
    rule = `
rule CalculateCost "Calculate the total cost based on CPU and Memory usage" {
    when 
        CloudResource.CPU > 0 &&
        CloudResource.Memory > 0
    then
        costPerCPUHour = 0.05;
        costPerGBMemoryHour = 0.01;
        cpuCost = CloudResource.CPU * costPerCPUHour;
        memoryCost = CloudResource.Memory * costPerGBMemoryHour;
        CloudResource.TotalCost = cpuCost + memoryCost;
        Retract("CalculateCost");
}
`
)

type CloudResource struct {
    CPU       float64
    Memory    float64
    TotalCost float64
}

func TestCloudResource(t *testing.T) {
    myResource := &CloudResource{
        CPU:    2,
        Memory: 4,
    }
    dataContext := ast.NewDataContext()
    err := dataContext.Add("CloudResource", myResource)
    if err != nil {
        t.Fatal(err)
    }
    lib := ast.NewKnowledgeLibrary()
    ruleBuilder := builder.NewRuleBuilder(lib)
    err = ruleBuilder.BuildRuleFromResource("Test", "0.1.1", pkg.NewBytesResource([]byte(rule)))
    assert.NoError(t, err)
    kb, err := lib.NewKnowledgeBaseInstance("Test", "0.1.1")
    assert.NoError(t, err)
    eng1 := &engine.GruleEngine{MaxCycle: 1}
    err = eng1.Execute(dataContext, kb)
    assert.NoError(t, err)

    // 檢查計算出的總成本
    expectedTotalCost := (2 * 0.05) + (4 * 0.01)
    assert.Equal(t, expectedTotalCost, myResource.TotalCost)
}
  • 总结: 使用 assert.Equal 校验 expectedTotalCost ,最后得出结果
shell 复制代码
$ go test
PASS
ok      grule_study/example/test        0.007s
相关推荐
每天进步一点_JL21 小时前
JVM 类加载:双亲委派机制
java·后端
用户2986985301421 小时前
Java HTML 转 Word 完整指南
java·后端
J2K1 天前
JDK都25了,你还没用过ZGC?那真得补补课了
java·jvm·后端
EMQX1 天前
ESP32 + MCP over MQTT:通过大模型控制智能硬件设备
后端·mcp
郭京京1 天前
go框架gin(中)
后端·go
郭京京1 天前
go框架gin(下)
后端·go
林树的编程频道1 天前
单例模式的推导
后端
就是帅我不改1 天前
揭秘Netty高性能HTTP客户端:NIO编程的艺术与实践
后端·面试·github
Ray661 天前
SugLucene索引构建
后端
舒一笑1 天前
Saga分布式事务框架执行逻辑
后端·程序员·设计