docs: 记录 Aipod 多上游模型路由
Pipelines as Code CI / agentrun-nc01-v02-ci-af6791d6aea4b91bed6ffd066f5fa53fd0f036d0 Success

This commit is contained in:
AgentRun Codex
2026-07-14 19:12:36 +02:00
parent 624654f74d
commit af6791d6ae
+57 -4
View File
@@ -1,6 +1,15 @@
# v0.1 AipodSpec 规格 # v0.1 AipodSpec 规格
`AipodSpec` 是 AgentRun `v0.1` 的声明式 agent 装配规格。它把已有的 `imageRef``backendProfile``executionPolicy.secretScope``ResourceBundleRef.kind="gitbundle"`、Queue task 和 Session send 装配入口集中到 YAML 文件中,避免把某个 agent 的 work-ready env image、模型、SecretRef、gitbundle、skill 或 tool 写死在 manager、runner 或 CLI 源码里。 `AipodSpec` 是 AgentRun `v0.1` 的声明式 agent 装配规格。它把以下装配事实集中到 YAML 文件中:
- `imageRef`
- 单 upstream `backendProfile`
- 多 upstream `upstreams`/`modelRouting`
- `executionPolicy.secretScope`
- `ResourceBundleRef.kind="gitbundle"`
- Queue task 和 Session send 装配入口。
这些声明避免把某个 agent 的 work-ready env image、模型、SecretRef、gitbundle、skill 或 tool 写死在 manager、runner 或 CLI 源码里。
## 设计边界 ## 设计边界
@@ -55,6 +64,29 @@ spec:
- `spec.backendProfile` 使用 AgentRun 已注册或动态的 Codex-compatible profile slug,例如 `codex``deepseek``minimax-m3``dsflash-go``sub2api` - `spec.backendProfile` 使用 AgentRun 已注册或动态的 Codex-compatible profile slug,例如 `codex``deepseek``minimax-m3``dsflash-go``sub2api`
- `spec.model.model` 会展开为 command payload 的 `model` 字段;完整 `spec.model` 同时进入 `payload.modelConfig`,用于保留 `reasoningEffort` 等声明但不作为 Secret 输出。 - `spec.model.model` 会展开为 command payload 的 `model` 字段;完整 `spec.model` 同时进入 `payload.modelConfig`,用于保留 `reasoningEffort` 等声明但不作为 Secret 输出。
- `spec.executionPolicy` 复用 run 的执行策略校验,且必须恰好包含一个匹配 `backendProfile` 的 provider credential SecretRef。 - `spec.executionPolicy` 复用 run 的执行策略校验,且必须恰好包含一个匹配 `backendProfile` 的 provider credential SecretRef。
- 单 upstream 模式:
- 继续使用 `spec.backendProfile``spec.model`
- provider credential 继续来自 `spec.executionPolicy.secretScope.providerCredentials`
- 保持既有 AipodSpec 兼容。
- 多 upstream 模式:
- 必须同时声明 `spec.upstreams``spec.modelRouting`
- 不得同时声明顶层 `backendProfile``model`
- 不得在 `executionPolicy.secretScope.providerCredentials` 重复声明 provider credential。
- `spec.upstreams.<id>`
- 为每个 upstream 声明唯一 `backendProfile`
- 声明对应的 provider credential SecretRef
- SecretRef 必须显式包含该 profile 所需的全部 key。
- `spec.modelRouting.default` 声明默认 upstream、默认模型和可选 reasoning effort。
- `spec.modelRouting.exact.<model>` 把精确模型 id 映射到特定 upstream 和可选 reasoning effort。
- render 输入显式传入模型时:
- 先查 `exact`
- 命中后选择对应 upstream
- 未命中则保留请求模型并走 `default.upstream`
- 显式 reasoning effort 始终覆盖路由默认值。
- render 后:
- Queue task 只携带命中 upstream 的一个 provider credential
- metadata、`payload.modelConfig``modelResolution` 保存 requested model、upstream id、匹配方式与路由哈希;
- 重试复用该持久化 task,不重新读取当前 YAML 做隐式切换。
- `spec.resourceBundleRef` 复用 RuntimeAssembly 的 gitbundle 规则,可为 `null`,但需要注入 skill/tool 时必须使用 gitbundle。 - `spec.resourceBundleRef` 复用 RuntimeAssembly 的 gitbundle 规则,可为 `null`,但需要注入 skill/tool 时必须使用 gitbundle。
- `spec.payloadDefaults` 与 CLI render 输入合并;用户 prompt 通过 `--prompt``--prompt-file``--prompt-stdin` 覆盖或补充。 - `spec.payloadDefaults` 与 CLI render 输入合并;用户 prompt 通过 `--prompt``--prompt-file``--prompt-stdin` 覆盖或补充。
@@ -87,9 +119,20 @@ imageRef:
仓库内置 `config/aipods/artificer.yaml`,名称为 `Artificer`。它的长期目标是承接 UniDesk 分布式开发任务: 仓库内置 `config/aipods/artificer.yaml`,名称为 `Artificer`。它的长期目标是承接 UniDesk 分布式开发任务:
- `backendProfile``credential.profile``model``reasoningEffort` 的唯一可调事实来自 `config/aipods/artificer.yaml`;本 SPEC 不复制默认值。任务级显式 override 只允许改变 `model``reasoningEffort`,不得改变 provider、credential profile 或 SecretRef。 - Artificer 的可调事实来自 `config/aipods/artificer.yaml`
- upstream 与模型路由;
- `backendProfile` 与 provider SecretRef
- 默认模型与 `reasoningEffort`
- 本 SPEC 不复制默认值。
- 调用方只允许显式选择 `model``reasoningEffort`
- provider、credential profile 和 SecretRef 必须由模型路由派生,不能由调用方直接覆盖。
- 通过 `imageRef` 引用 AgentRun `v0.1` env image Dockerfile source;当前默认值是 `repoUrl=git@github.com:pikasTech/agentrun.git``commitId=6601b4afb4870ecec62f14459e14202e5ccca7ec``dockerfilePath=deploy/container/Containerfile`。启动时必须复用已物化的 digest-pinned env image,不能把依赖安装留给任务运行时。 - 通过 `imageRef` 引用 AgentRun `v0.1` env image Dockerfile source;当前默认值是 `repoUrl=git@github.com:pikasTech/agentrun.git``commitId=6601b4afb4870ecec62f14459e14202e5ccca7ec``dockerfilePath=deploy/container/Containerfile`。启动时必须复用已物化的 digest-pinned env image,不能把依赖安装留给任务运行时。
- provider SecretRef 只读取 `config/aipods/artificer.yaml` 的声明,用于获取 `auth.json``config.toml`;本 SPEC 不复制 SecretRef 名称。 - provider SecretRef
- 只读取 `config/aipods/artificer.yaml` 对各 upstream 的声明;
- 用于获取各自的 `auth.json``config.toml`
- 本 SPEC 不复制 SecretRef 名称;
- 单次任务只投影命中 upstream 的 SecretRef
- 不把所有 provider credential 一起注入 runner。
- 通过 `toolCredentials` 获取 GitHub Issue/PR 写入 token`agentrun-v01-tool-github-pr` -> env `GH_TOKEN` - 通过 `toolCredentials` 获取 GitHub Issue/PR 写入 token`agentrun-v01-tool-github-pr` -> env `GH_TOKEN`
- 通过 `toolCredentials` 获取 UniDesk SSH 透传 token`agentrun-v01-tool-unidesk-ssh` -> env `UNIDESK_SSH_CLIENT_TOKEN` - 通过 `toolCredentials` 获取 UniDesk SSH 透传 token`agentrun-v01-tool-unidesk-ssh` -> env `UNIDESK_SSH_CLIENT_TOKEN`
- 通过 `toolCredentials` 获取 GitHub SSH 凭据:`agentrun-v01-tool-github-ssh` -> volume `/home/agentrun/.ssh` - 通过 `toolCredentials` 获取 GitHub SSH 凭据:`agentrun-v01-tool-github-ssh` -> volume `/home/agentrun/.ssh`
@@ -163,7 +206,17 @@ CLI
## 测试规格 ## 测试规格
- A1`config/aipods/artificer.yaml` 能被 manager list/show/renderrender 结果中的 `backendProfile``credential.profile``model``reasoningEffort` 与 provider SecretRef 必须逐项等于 owning YAML;显式 model/reasoning override 只改变对应两项。结果还必须包含 `imageRef.kind=env-image-dockerfile``repoUrl``commitId``dockerfilePath`、GitHub PR token env projection、UniDesk SSH env projection、GitHub SSH volume projection、无 `resourceBundleRef.gitMirror` 字段、AgentRun runner tools gitbundle 和 gitbundle requiredSkills。 - A1`config/aipods/artificer.yaml` 能被 manager list/show/render
- 默认模型走默认 upstream
- 精确模型规则切到对应 upstream;
- 未知模型保留请求模型并走默认 upstream;
- `backendProfile``credential.profile``model``reasoningEffort` 与 provider SecretRef 逐项等于路由结果;
- execution policy 只包含命中的一个 provider credential
- 结果包含路由快照;
- 结果包含 `imageRef.kind=env-image-dockerfile``repoUrl``commitId``dockerfilePath`
- 结果包含 GitHub PR token env projection、UniDesk SSH env projection、GitHub SSH volume projection
- 结果不包含 `resourceBundleRef.gitMirror` 字段;
- 结果包含 AgentRun runner tools gitbundle 和 gitbundle requiredSkills。
- A2`queue submit --aipod Artificer --dry-run` 输出标准 `queue-submit-plan`,且 `idempotencyKey`、prompt 与 metadata 被保留。 - A2`queue submit --aipod Artificer --dry-run` 输出标准 `queue-submit-plan`,且 `idempotencyKey`、prompt 与 metadata 被保留。
- A2b`queue submit --aipod Artificer --dry-run``render Artificer` 在没有显式 `sessionRef` 时必须输出默认 `sessionRef.sessionId` / `conversationId`;显式传入 `sessionRef` 时不得覆盖。 - A2b`queue submit --aipod Artificer --dry-run``render Artificer` 在没有显式 `sessionRef` 时必须输出默认 `sessionRef.sessionId` / `conversationId`;显式传入 `sessionRef` 时不得覆盖。
- A3Artificer 规格只声明 GitHub URL,不声明 `gitMirror`runner 默认把 GitHub URL 改写到 mirror base URL,非 GitHub URL 不改写。请求体显式携带 `resourceBundleRef.gitMirror` 必须 schema-invalid,避免把基础设施策略下放到 AipodSpec。 - A3Artificer 规格只声明 GitHub URL,不声明 `gitMirror`runner 默认把 GitHub URL 改写到 mirror base URL,非 GitHub URL 不改写。请求体显式携带 `resourceBundleRef.gitMirror` 必须 schema-invalid,避免把基础设施策略下放到 AipodSpec。