Dagor —— 一个高性能 DAG 算子执行框架,开箱即用!

Dagor 是一个高性能DAG算子执行框架,专为高并发在线服务设计。它将复杂的业务逻辑解耦为独立的算子,通过DAG进行灵活编排,自动处理并行调度与数据注入。

GitHub 项目地址:
github.com/wwz16/dagor

中文 README:
github.com/wwz16/dagor...


一、背景:复杂在线逻辑,真的只能写 if-else 吗?

复杂业务的在线系统中,我们经常会遇到这样的业务形态:

  • 请求链路长
  • 逻辑复杂、阶段多
  • 不同模块之间存在明确的数据依赖
  • 希望尽可能 并行执行,降低整体 latency

最初的实现通常是这样:

css 复制代码
a := stepA()
b := stepB(a)
c := stepC(a)
d := stepD(b, c)

随着业务增长,很快就会变成:

  • 强耦合
  • 难以重构
  • 不好做并行
  • 难以配置化、AB 实验成本高

在字节 / 阿里 / 腾讯内部,这类问题几乎都会收敛到一个解法

用 DAG(有向无环图)来描述业务执行流程

于是我在业余时间,把这一类"内部 DAG 执行引擎"的设计思想,抽象并实现成了一个 Go 语言开源项目 ------ Dagor


二、Dagor 是什么?

Dagor 是一个基于 DAG 的算子执行框架(Operator-based DAG Engine)

它的核心思想是:

  • 把业务逻辑拆成 Operator(算子)

  • DAG 描述算子之间的数据依赖

  • 由引擎自动完成:

    • 任务调度
    • 并行执行
    • 数据注入
    • 数据传递

一句话总结:

Dagor 让你用「配置」描述业务拓扑,用「代码」实现单点业务逻辑。


三、核心设计理念

1️⃣ 数据驱动,而不是流程驱动

在 Dagor 中,你不需要写「谁先执行谁」:

css 复制代码
"inputs": {
  "a": "n1",
  "b": "n2"
}

只要声明 数据从哪里来,引擎就会自动推导依赖关系。


2️⃣ 字段级依赖,而不是节点级依赖

Dagor 的依赖粒度是 字段(field) ,而不是整节点:

  • 一个算子可以产出多个字段
  • 不同下游节点可以依赖不同字段
  • 并行度最大化

3️⃣ Operator 池化可复用

  • 算子支持 池化(operator pooling)
  • 参数在运行期绑定
  • 自动 Reset,安全复用
  • 大幅降低 GC 压力

四、核心概念速览

概念 说明
Operator 独立的业务计算单元
Vertex 图中的节点,对应一个 Operator
Edge 数据依赖关系
Graph 业务拓扑(DAG)
Engine 图的运行时,负责任务调度

关系示意图:


五、一个最简单但有代表性的示例

1️⃣ 定义算子

go 复制代码
type AddOp struct {
    a   *int `dag:"input"`
    b   *int `dag:"input"`
    sum int  `dag:"output"`
}

func (op *AddOp) Run(ctx context.Context) error {
    op.sum = *op.a + *op.b
    return nil
}

无需手动接线,输入输出由框架自动注入。


2️⃣ 用 JSON 描述业务 DAG

css 复制代码
{
  "name": "math_demo",
  "vertices": {
    "const10": {
      "op": "ConstOp",
      "params": { "in": 10 },
      "outputs": { "out": "n1" }
    },
    "const20": {
      "op": "ConstOp",
      "params": { "in": 20 },
      "outputs": { "out": "n2" }
    },
    "add": {
      "op": "AddOp",
      "inputs": {
        "a": "n1",
        "b": "n2"
      },
      "outputs": {
        "sum": "answer"
      }
    }
  }
}

3️⃣ 运行 DAG

css 复制代码
eng, _ := dagor.NewEngine(graph, pool)
_ = eng.Run(ctx)

v, _ := eng.GetOutput("answer")
fmt.Println(*v.(*int))

六、为什么不用现成的 Workflow / Airflow?

Dagor 的定位很明确:

❌ 不做离线

❌ 不做大而全

❌ 不做跨系统编排

它专注解决的是:

高并发在线请求内的复杂逻辑调度问题

和很多公司内部推荐 / 搜索 / 广告 DAG 引擎的定位是一致的。


七、还有哪些工程化能力?

  • ✅ Operator 自动代码生成,减少手动代码编写
  • ✅ 算子参数 Params开箱即用,无需提前定义结构体,支持路径访问(a.b.c.0
  • ✅ 并行调度 + goroutine pool
  • ✅ 图的超时控制
  • ✅ 图可视化工具

八、适合哪些人?

如果你是:

  • Go 后端工程师
  • 复杂业务流程编排
  • 搜索 / 推荐 / 广告方向
  • 对架构、执行引擎、Infra 感兴趣
  • 想看 "字节/阿里/腾讯内部系统的简化版实现"

那这个项目可能对你有参考价值。


九、项目地址 & 结语

👉 GitHub:
github.com/wwz16/dagor

👉 中文 README:
github.com/wwz16/dagor...

如果你对 DAG / 执行引擎 / 推荐系统架构 感兴趣,也欢迎在评论区交流 👋

相关推荐
mtngt1116 小时前
AI DDD重构实践
go
Grassto2 天前
12 go.sum 是如何保证依赖安全的?校验机制源码解析
安全·golang·go·哈希算法·go module
Grassto4 天前
11 Go Module 缓存机制详解
开发语言·缓存·golang·go·go module
程序设计实验室5 天前
2025年的最后一天,分享我使用go语言开发的电子书转换工具网站
go
我的golang之路果然有问题5 天前
使用 Hugo + GitHub Pages + PaperMod 主题 + Obsidian 搭建开发博客
golang·go·github·博客·个人开发·个人博客·hugo
啊汉7 天前
古文观芷App搜索方案深度解析:打造极致性能的古文搜索引擎
go·软件随想
asaotomo7 天前
一款 AI 驱动的新一代安全运维代理 —— DeepSentry(深哨)
运维·人工智能·安全·ai·go
码界奇点8 天前
基于Gin与GORM的若依后台管理系统设计与实现
论文阅读·go·毕业设计·gin·源代码管理
迷迭香与樱花8 天前
Gin 框架
go·gin
只是懒得想了8 天前
用Go通道实现并发安全队列:从基础到最佳实践
开发语言·数据库·golang·go·并发安全