深入浅出Agent: Harness最全调研与原理解析(持续更新中)

内容提纲

  • 为什么要谈 Harness:Prompt、Context、Harness 三个时代的演进
  • Agent Loop:所有 Harness 框架共享的 ReAct 内核
  • 常见 Harness 框架横向对比:Claude Code、Codex、OpenClaw、Hermes、OpenHuman
  • Loop Engineering:人从写 Prompt 转向定义状态和循环
  • Harness 的核心抽象层:Tool Call、MCP、Skill、SubAgent、Memory、Hook、Plugin、Goal 八种抽象
    • Skill 的实现原理
    • SubAgent 的实现原理
  • 前沿特性速览
    • Agent Team:多实例自由通信
    • Goal:对抗 Agentic Laziness
    • Humanize:用 Stop Hook 逼 Agent 继续干
    • Dynamic Workflows:把编排写成代码
    • Auto Dream:给记忆做整理巩固
    • OpenHuman 记忆系统:层次化加多路检索
    • Hermes 自我进化:边干边重构自己
  • 更新日志与思考

Harness 时代

过去几年,业界对大模型的关注点经历了三次转移。这三次转移可以用三个词概括:Prompt、Context、Harness。

阶段 时间 问题 一句话
Prompt Engineering 2020 至 2024 模型还不够听话,怎么让它按指定格式输出 控制模型输出什么
Context Engineering 2024 至今 模型的上下文学习和多轮能力变强,怎么组织上下文、补充知识 控制模型看什么
Harness Engineering 2026 至今 模型本身已具备强多轮能力,怎么搭一个约束模型行为、组织模型能力的环境 控制模型生产什么

Prompt / Context / Harness Engineering

Prompt 时代解决的是单次输出的可控性,Context 时代解决的是知识注入,而 Harness 时代解决的是行为约束与能力编排。模型越强,外层环境的设计就越重要,因为强模型需要是一个能让它自由发挥又不脱轨的运行框架。

Agent Loop:所有 Harness 的核心

现今所有 Harness 框架的核心都是同一个 Loop,也就是 ReAct 范式:模型思考,调用工具,拿回结果,再思考,直到任务完成。所有其他设施都是围绕这个 Loop 搭建的,包括 Skill、Memory、SubAgent 等。

围绕 Loop 的三类基础设施:

  1. 消息平台。负责承载对话,可以是独立 App、CLI,也可以是开放接口
  2. 内置工具。读写文件、跑命令等原子能力
  3. 记忆系统。跨会话保存偏好、经验和失败教训

Skill 和 SubAgent 则建在这套基础之上,作为更高层的能力封装。理解一个 Harness 框架,本质上就是理解它如何组织这个 Loop 的上下文,以及它在 Loop 周围挂了哪些设施。

Agent Loop 架构

可以通过 Claude 官方设计的交互组件了解 Claude Code 的 Prompt 具体如何组织:code.claude.com/docs/zh-CN/...

参考:Dive into Claude Code: The Design Space of Today's and Future AI Agent Systems, arxiv.org/abs/2604.14...

常见 Harness 框架横向对比

目前一线的 Harness 框架可以分为两类定位:一类是生产级、主要面向编程场景的,另一类是 Feature 多但 Bug 也多、面向个人助手场景的。

维度 Claude Code Codex OpenClaw Hermes OpenHuman
开源
GitHub Stars 暂无 92.6k 370k 60k 27k
编程语言 TypeScript Rust TypeScript Python Rust + TS
代码行数 512k 731k 2,362k 261k 806k
消息平台 独立 App / CLI 独立 App / CLI 开放 开放 开放
内置工具数 15 至 20 25 33 34 190
记忆系统 轻量 Auto Memory 暂无 MEMORY.md Markdown + SQLite,26k 行,层次化加向量,极复杂
自我改进 Auto Dream dreaming 自动整理记忆 fork 自我复盘写 Skill Subconscious 循环

几点值得注意的趋势:

  • 代码行数和工具数量整体在膨胀。OpenHuman 的 190 个内置工具和 26k 行记忆系统代表了功能堆叠路线的极端
  • 几乎每个框架都在做某种形式的自我改进,名字各异,但思路一致:让 Agent 在跑完任务后回头整理自己的记忆或能力
  • 生产级框架(Claude Code、Codex)倾向克制,工具数和记忆系统都偏轻量,稳定性优先。个人助手场景的框架则倾向激进堆功能

Loop Engineering:人只定义状态

Loop Engineering 是一个建在 Harness 之上的概念。它的核心主张是:人不再关注 Agent 具体怎么运行,只负责定义状态。

具体来说,人定义三样东西:任务、验证环境、验收标准。当 Agent 无法达到验收标准时,会有一个外层脚本不断调用 Agent,持续执行任务,直到达标。换句话说,人写的不再是 Prompt,而是 Loop 本身。

这个理念在 2026 年 6 月被两位一线人物先后点破。Claude Code 负责人 Boris Cherny 在公开演讲中表达的意思是,他已经不再直接给模型写 Prompt,而是运行循环,由循环来给模型写 Prompt、决定下一步做什么,他的工作是写循环。OpenClaw 作者 Peter Steinberger(已加入 OpenAI)也发推表达了同样的观点,认为不应该再给编码 Agent 写 Prompt,而应该去设计能给 Agent 写 Prompt 的循环。

Loop Engineering 把人的角色从指令的发出者,变成了状态机的设计者。后文的 Goal、Humanize、Dynamic Workflows 都可以看作这个理念的具体落地。

Prompting vs Looping

四类可以无人值守运行的 Loop

参考:x.com/sairahul1/s...

Harness 的核心抽象层

理解 Harness 的关键,是搞清楚它提供了哪些抽象,以及这些抽象各自解决什么问题、由谁触发、占不占主上下文、活多久。下面这张表把当前主流的八种抽象一次说清。

抽象 一句话定义 解决什么 谁触发 / 谁定义 上下文 持久性 层级
Tool Call Agent 调一个函数并拿回结果 读写文件、跑命令等原子操作 模型决定调,harness 执行 占用主上下文 单次调用 最底层原子能力,其余能力最终都落到 tool call
MCP 一套接入外部工具和数据源的协议 统一外部服务接口 外部 server 提供,模型当 tool 调 工具结果进主上下文 配置级 Tool Call 的外部供给来源
Skill 把可复用工作流封装成含文本与工具说明书的包 固化重复流程 模型按需加载和调用 加载时才进上下文,渐进披露 跨会话长期 建在 tool call 之上的能力封装
SubAgent 在独立上下文里调一个独立 Agent 上下文隔离,并行化 主 Agent 调用 独立上下文 任务级 作为 tool 调用
Memory 跨会话保存偏好、经验、失败教训 不用每次重新解释背景 harness 自动写,启动时注入 启动时注入主上下文 跨会话长期 持久化层
Hook 在固定生命周期点触发的确定性脚本 用代码强制约束行为 事件触发,非模型决定 通常不进上下文,外部执行 配置级常驻 凌驾于模型之上
Plugin 把 Skill、Hook、SubAgent、MCP 打包分发 一整套能力 用户安装注册 取决于内含组件 配置级 打包分发层
Goal / Plan 把完成条件变成持久状态,让 Agent 长程无人值守推进 跨越几十上百轮、断线重连仍朝目标收敛 用户设目标,Agent 自驱循环 计划状态持久存储,每轮读取 目标级长期 凌驾于模型之上,每轮注入上下文

读这张表有三个角度:

第一个角度是上下文成本。Tool Call 和 MCP 的结果直接进主上下文,调多了会撑爆窗口;Skill 用渐进披露,只在被调用时才加载;SubAgent 干脆开一个独立上下文,把无关上下文隔离在外

第二个角度是谁说了算。Tool Call、MCP、Skill、SubAgent 都是模型自己决定要不要用;Hook 和 Goal 则不是,它们由事件或外层脚本触发,凌驾于模型之上,模型无法绕过。这正是 Loop Engineering 的抓手所在

第三个角度是活多久。Tool Call 是单次的,SubAgent 是任务级的,Skill 和 Memory 是跨会话长期的,Goal 是目标级长期的。越往下越接近持久状态,越能支撑长程无人值守的运行

下面以一张图直观理解这几个概念:

以做 PPT 为例直观理解八种抽象

Skill 的实现原理

Skill 听起来高级,源码层面其实很朴素。

格式约定:

  • Skill 必须放在特定位置,例如 .agents/skills/***/SKILL.md
  • SKILL.md 顶部需要一段 YAML frontmatter,写明这个 Skill 的描述和触发条件。

System Prompt 末尾的 Skill 列表

运行机制分两步:

  1. 每次对话开始时,Harness 程序扫描所有 Skill,把每个 Skill 的名称和描述组织成一份列表,放在 System Prompt 的最后。
  2. 对话进行中,当 Agent 判断需要某个 Skill,就去读对应位置的 SKILL.md。这一步是渐进式加载,正文只有在真正需要时才进上下文。

一个直接的工程约束由此而来:Skill 不能太多。因为所有 Skill 的名称和描述都常驻在 System Prompt 里,Skill 一多,System Prompt 就会膨胀甚至爆掉。这也是为什么后文 Hermes 要专门做 Skill 的后台合并与归档。

SubAgent 的实现原理

SubAgent 指在自己的独立上下文窗口中运行的 Agent,它有自定义的系统提示、特定的工具访问权限和独立的权限边界。

什么时候用:当一个辅助任务会用搜索结果、日志或大段文件内容塞满主对话,而你之后不会再引用这些中间内容时,就该把它丢进 SubAgent。主 Agent 只拿回最终结论,中间噪音留在 SubAgent 的上下文里,跟着任务一起结束。

三个可控特性:

  • 可以指定 SubAgent 用其他模型,比如让便宜的小模型干粗活
  • 可以控制 SubAgent 能用哪些工具,收窄它的权限面
  • 可以控制它是否继承主上下文

SubAgent 的本质价值是上下文隔离加并行化。它在主 Agent 眼里就是一次 tool call,调用完返回一个结果,但背后是一整段独立的推理过程。

调用 SubAgent 有两种方式,行为上略有差别:fork 继承完整的对话历史,命名 subagent 则拿一份只带你传入提示的新鲜上下文。

分叉 vs 命名 subagent

前沿特性速览

下面这些是当前各框架在 SubAgent 和 Memory 之上探索出的新玩法,可以看作 Harness 时代正在成形的新范式。

Agent Team:多实例自由通信

Agent Team 指多个独立的 Agent 实例像团队一样并行协作,关键在于 SubAgent 之间可以自由通信,而不只是各自向主 Agent 汇报。这种横向通信提升了探索的自由度,让多个 Agent 能就同一问题交换中间发现,而不必每条信息都绕回主 Agent 的上下文。

Subagents vs Agent Teams

二者的区别在于通信和协调方式。Subagent 只向主 Agent 汇报结果,由主 Agent 统一管理;Agent Team 则共享一份任务列表,队员之间直接收发消息、自我协调,代价是每个队员都是一个独立的 Claude 实例,令牌成本更高。只需要结果的专注任务用 subagent,需要讨论和相互质疑的复杂工作用 agent team。

Subagents 与 Agent teams 对比

Goal:对抗 Agentic Laziness

动机来自一个真实问题,叫 Agentic Laziness。当 Agent 处理一个特别复杂、需要分多步完成的任务时,它常常在完成一部分后就宣布任务已完成。这让它很难长期无人值守地运行,典型场景比如算子优化这种需要反复迭代的任务。

方法:

  • Harness 暴露三个工具:get_goalcreate_goalupdate_goal
  • 创建 goal 之后,每一轮 harness 都会把 goal 作为上下文放进 Prompt
  • 只有当 Agent 主动调用 update_goal({ "status": "complete" }),goal 才会被标记为已完成

换句话说,完成与否不再由模型随口宣布,而是要它显式地、主动地去改一个持久状态,这就堵住了提前收工的退路。

Goal 驱动的外层循环

Humanize:用 Stop Hook 逼 Agent 继续干

Humanize 是一个插件,灵魂是一个 2221 行的 Stop hook,文件名是 loop-codex-stop-hook.sh,它在 Claude 想要结束时触发。

Humanize 的 Stop hook 流程

完整流程:

  1. Claude 实现完计划,写一份 round-N-summary.md,尝试退出。
  2. Stop hook 拦截这次退出,把 summary 喂给 Codex review。
  3. 如果 Codex 没有输出 COMPLETE,就阻止 Claude 退出,把审查意见作为新指令喂回去,逼它继续干。

两个有意思的特性:

  • 记忆系统的 bitlesson。每轮执行前,bitlesson-selector 子 Agent 为当前任务挑出适用的教训。如果一个问题花了多轮才解决,就把它沉淀成一条新教训写进 bitlesson.md
  • 人类闸门。在循环启动前,插件用一个子 Agent 出两道关于计划的选择题,考察人类是否真读懂了即将自动执行的计划。这是无人值守流程里给人类留的一道确认关卡。

Dynamic Workflows:把编排写成代码

Dynamic Workflows 发布于 2026 年 5 月 28 日。最直观的战绩是 Bun 作者 Jarred Sumner 用它把整个 Bun 运行时从 Zig 迁移到 Rust,11 天迁移了 75 万行代码。

它要解决的瓶颈,是现有几层能力的共同短板。Claude Code 现有的协作能力有三层:

  1. 单个 Agent 实例从头干到尾,串行处理。
  2. SubAgent,派生若干小弟去搜文件、读代码、跑命令,干完汇报回来。
  3. Agent Team,多个独立实例并行协作,队员之间还能互相通信。

这三层有一个共同瓶颈:编排者始终是 Claude 本身。它逐轮决策下一步派谁去干什么,而每个 SubAgent 的返回结果都要先回到 Claude 的上下文窗口,它读完才能决定下一步。一旦要协调几十上百个并行任务,上下文窗口根本装不下这么多中间结果。

Dynamic Workflows 的思路是把编排从模型的上下文里搬出来。Claude 不再亲自逐轮调度,而是先把整个编排过程写成一段 JavaScript 脚本,循环、分支、中间结果的收集全部固化在代码里,再交给一个独立运行时去执行。模型只负责生成编排逻辑,运行时负责执行,中间结果不再占用模型上下文。

一段 workflow 脚本的样子如下,顶部用 meta 声明名称、描述和 phase 列表,下面是真正的调度逻辑:

Dynamic Workflows 脚本示例

JavaScript 脚本原语

原语 作用 关键点
agent(prompt, opts) spawn 一个 SubAgent 不带 schema 返回字符串;带 schema 时按 JSON Schema 返回结构化结果
pipeline(items, s1, s2, ...) 每个 item 独立走完所有 stage 默认选择,无屏障;item A 可以在 stage3 而 B 还在 stage1
parallel(thunks) 并发跑一批任务 有屏障,等全部完成;传的是函数数组 () => agent(...),不是 promise
phase(title) 进度分组 后续 agent 归到这一组
log(msg) 给用户发一行进度 显示在进度树上方
workflow(name, args) 内联调一个子 workflow 只能嵌一层
args / budget 外部参数 / token 预算 控制输入与成本

其中 agent() 是最核心的一个,单个调用就能指定模型、隔离方式和返回 schema;parallelpipeline 则负责把它批量组合起来:

agent 原语与 parallel / pipeline 组合

这几个原语能够完成表达所有 Agent 编排的范式:

六种工作流编排范式

几个关键约束

  • JS 只能调度。所有文件修改或 shell 命令必须由 SubAgent 执行,脚本本身不碰文件系统。
  • 并发上限。最多 16 个 SubAgent 并行,单次运行最多 1000 个 SubAgent。
  • 可恢复。没改动的 agent() 调用直接命中缓存,只有改动及其之后的部分才重新跑。这让长流程在中途失败后可以低成本续跑。

Zig 迁移 Rust 的三阶段

  1. 生命周期映射。给 Zig 代码库里每一个 struct field 算出它对应的、正确的 Rust lifetime。
  2. 并行文件移植。把每个 .zig 文件移植成行为等价的 .rs 文件,数百个 Agent 同时开工,每个文件还配两个 reviewer 做交叉审查。
  3. 编译与测试的 fix loop。驱动整个 build 和 test 套件,循环修复,直到两者都干净跑过。

Bun 从 Zig 到 Rust 的三阶段

Auto Dream:给记忆做整理巩固

动机来自记忆腐烂。Memory 让 Claude 边干活边记笔记,但跑了 20 多个 session 后,笔记会烂掉,具体有四种表现:

  1. 矛盾堆积。三个 session 对同一个 API 错误记了三条互相打架的内容。
  2. 相对日期失效。昨天决定用 Redis 里的昨天,过段时间就失去了意义。
  3. 过期内容残留。指向已被删除文件的调试笔记还留着。
  4. 重复冗余。同一个构建命令的怪癖被记了好几遍。

只记不整理的 Claude,状态相当于长期信息持续涌入却从不巩固。Auto Dream 就是补上巩固这一步,分四个阶段:

阶段 名称 做什么
Phase 1 定位 Orient ls 记忆目录、读 MEMORY.md 索引、扫一遍现有主题文件,搞清楚现在知道什么、怎么组织的,避免重复建
Phase 2 收集信号 Gather Signal 在本地轨迹里找四类高价值信号:用户的纠正、明确的记住这个、跨 session 的重复主题、重要决策
Phase 3 巩固 Consolidate 相对日期转绝对日期(昨天转成 2026-03-15)、删除被推翻的事实、清理过期记忆、合并重复条目
Phase 4 修剪与索引 Prune & Index 维护 MEMORY.md 索引,保持在 200 行以内,维护链接、解决索引与内容的矛盾、按相关性和时近性重排

OpenHuman 记忆系统:层次化加多路检索

OpenHuman 的记忆系统是目前最复杂的一套,约 26k 行,核心是层次化封装加多种检索手段并行。

写入侧分两步。

后台抽取。每 20 分钟,auto-fetch 从 Gmail、Notion、Slack 拉数据。每条记录先转成一大块标准 Markdown,然后切成 chunk,chunk 按来源和时间聚类。

逐层封装。chunk 逐层向上封存成摘要,每一层有个 buffer。当某层 buffer 攒够 token,内容就封存成上一层的一个摘要节点,buffer 清空。具体地,L0 攒够 5 万 token,约 15 个以上 chunk,就封存成一个 L1 摘要节点;每 10 个 L1 摘要再折叠成一个 L2,逐层向上。

层次化摘要树

摘要节点封存后永久不可变。要更新就用 tombstone 模式:不改旧节点,而是封一个新版本,旧节点在遍历时被过滤掉。好处是写入永远是 append-only,无锁、无并发冲突。所有记忆通过 Obsidian 的双链系统组织成知识图谱。系统曾经实现过按主题聚合的 topic tree,后来被移除。

记忆知识图谱

读取侧提供四种检索:

检索方式 机制
tree-walk 从顶层摘要节点 BFS 向下探索 drill_down。LLM 先拿到高层摘要,想看细节就向下一层,L2 到 L1 再到原始 chunk。子节点按对 query 的余弦相似度 rerank,防止最相关的被截断
vector search 对文档做 embedding 相似度排序
keyword search FTS5 全文和关键词检索
param / tag search 按 chunk 元数据加标签的结构化过滤

tree-walk 是这套系统区别于普通 RAG 的地方。它不是一次性把相关 chunk 捞出来,而是让模型像读目录一样自顶向下逐层下钻,按需深入,既控制了上下文成本,又保留了全局结构。

OpenHuman 记忆检索流程

Hermes 自我进化:边干边重构自己

Hermes 把自我改进做进了运行时,分两条线:每个 turn 后的即时复盘,和后台的 Skill 治理。

每个 turn 后自我复盘:

  • 每个 turn 结束,Hermes fork 一个受限子 Agent,复盘刚才的对话。
  • 继承父上下文时命中同一个 prefix cache,省钱。
  • 运行时工具白名单 set_thread_tool_whitelist 只放行 memory 和 skills 两个 toolset,把复盘 Agent 的能力收窄到自我维护这件事上。
  • 产出是两选一:写 Memory,或者构建新 Skill。这里同样要警惕 Skill 膨胀,所以才需要下面的后台治理。

Skill 后台管理:

每个 Skill 有三个状态,active 到 stale 到 archived。30 天没用标记为 stale,90 天没用归档。

每 7 天后台开一个 Curator 合并 Skill,逻辑如下:

  1. 扫描全部 Skill,找共享首词或域关键词的 Skill 群,也就是 prefix 簇。
  2. 对每个有两个以上成员的簇,要么合并到已有的候选 Skill,要么新建一个 Skill。
  3. 把被合并的内容降级为 references、templates 或 scripts。
  4. 继续循环,直到找不到新的簇。

举个例子,五个以 pr- 开头的 Skill 共享同一个前缀,Curator 会把它们合并成一个 pr-handling Skill,原来的内容降级成它的子小节或支持文件:

Curator 合并 Skill

这套机制让 Skill 库能自我收敛,不会因为每个 turn 都可能产出新 Skill 而无限膨胀,从根上呼应了前面提到的 System Prompt 容量约束。


更新日志与思考

2026-06-28

本次整理了 Harness 时代的核心概念与一线框架的新特性,搭好了从 Agent Loop 到自我进化记忆系统的主干。后续会补充 Harness 应用实战部分,包括上下文管理(/clear 与 /compact、Fork)、Skill 编写(Skill-creator、写法与示例)以及前沿应用范式(AutoResearch、LLM Wiki)。

本次内容连起来看,Harness 时代有一条清晰的主线。

最底层是 Agent Loop,也就是 ReAct,所有框架共享同一个内核。往上是一组抽象:Tool Call 和 MCP 提供原子能力,Skill 和 SubAgent 解决上下文成本,Memory 解决跨会话记忆,Hook 和 Goal 把控制权从模型手里部分收回到外层脚本。再往上是 Loop Engineering 这一层理念,人不再写指令,而是定义状态和循环。

前沿特性几乎都在围绕两个矛盾做文章。第一个矛盾是上下文窗口装不下长程任务的全部中间结果,Dynamic Workflows 用代码编排把中间结果搬出模型上下文来解。第二个矛盾是记忆和能力会随时间腐烂膨胀,Auto Dream、OpenHuman 的层次化封装、Hermes 的 Skill 治理都在解这个问题。

一点思考:workflow 的轮回

2025 年之前,做复杂任务靠的是人手工编排 workflow。开发者用 LangChain、各种 DAG 框架,或者干脆自己写胶水代码,把每一步该调哪个模型、该走哪个分支、上一步的输出怎么喂给下一步,全部提前写死。模型在这个阶段只是流水线上一个被调用的节点,编排的智能完全在人脑和人写的代码里。

进入 Harness 时代。大家不再事先画流程图,而是把决策权交给模型。Agent 在 Loop 里自己决定下一步调什么工具、要不要派 SubAgent、什么时候算完成。编排从静态的代码变成了模型每一轮的动态判断。手工 workflow 一度被认为过时了,因为模型够强,不需要人替它规划路径。大家只需要写好 Skill 即可。

而 Dynamic Workflows 又回到了 Workflow,这是一个螺旋上升:

  • 第一阶段,编排逻辑由人写,是静态代码。
  • 第二阶段,编排逻辑由模型在运行时即兴决定,是动态判断。
  • 第三阶段,编排逻辑重新变回代码,但这段代码由模型自动生成。

为什么会绕回到代码?因为纯动态判断有一个硬约束,就是上下文窗口。模型逐轮决策的前提是每一步的中间结果都要回到它的上下文里,一旦任务规模到了几十上百个并行子任务,窗口根本装不下。代码形式的 workflow 恰好把这些中间结果挪出了上下文,让确定性的部分交给确定性的运行时,把模型的智能省下来只用在真正需要判断的地方。

如果这个判断成立,那它指向的趋势可能是:模型的角色正在从执行者上移到编译器。早期模型是流水线里被调用的算子,Harness 时代模型是亲自跑流水线的工人,而 Dynamic Workflows 之后,模型更像是把意图编译成可执行编排的那一层。人定义目标,模型把目标编译成 workflow,运行时执行 workflow,执行中再按需调起新的模型实例。Loop Engineering 讲的人只定义状态,和这里讲的模型把状态编译成循环,其实是同一件事的两端。

相关推荐
Larcher1 小时前
从回调地狱到优雅异步:Node.js 文件操作进化史
javascript·后端·架构
日月云棠1 小时前
Spring 源码深度剖析:DispatcherServlet 的自动化注册机制
java·后端
码事漫谈1 小时前
让 Codex CLI 跑上 DeepSeek:用 LiteLLM 做 Responses↔Chat 协议翻译
后端
JavaGuide1 小时前
又一个画图 Skill 开源,再见手动画 draw.io!
前端·后端·github
吾诺2 小时前
2026大直径紧固件双叠自锁垫圈怎么选型
后端
tyung2 小时前
zhenyi-base zqueue 基准测试分享
后端·go
time展天12 小时前
Dddify:给 ASP.NET Core 项目一套轻量、清晰、可落地的 DDD 基础设施
数据库·后端·asp.net
SamDeepThinking2 小时前
为什么我会主动给一个年轻程序员加薪、晋升?
java·后端·程序员
tonydf2 小时前
接入服务商模式的支付宝支付
后端·支付宝