32 KiB
Skill Action Manifest(匠厂宿主)
本文件说明 assets/actions.json 与 scripts/main.py CLI 的对应关系,供 Agent 编排与宿主 Skill Action Runtime 使用。这是 Agent 侧关于 Action / 任务中心的主契约;实现细节与开发规范见 ../development/SKILL_ACTION_RUNTIME.md。
边界: 用户市场四 Tab 见根目录 README.md / TUTORIAL.md / DEMO.md / CHANGELOG.md;CLI 参数见 CLI.md。
Agent 何时用 Action(与 CLI 的分工)
| 场景 | 做法 |
|---|---|
| 短查询 / 只读 / 秒级 | bash + 共享 Python CLI(见 CLI.md);不必强行走 Action |
| 数据管理按钮 / 定时任务 / 技能详情按钮 | 必须在 actions.json 声明对应 Action |
| 长耗时 / RPA / 需要进度与取消 | 必须 run_skill_action;对应 Action 一般为 executionProfile: "async" |
已声明的 sync Action |
run_skill_action 当场返回结果,不进任务中心 |
已声明的 async Action |
run_skill_action 立即返回 jobId,进入任务中心 |
进不进任务中心只取决于该 Action 的 executionProfile,与从数据管理、定时任务还是 Agent 触发无关。
禁止对长任务 exec/bash + process poll 干等 CLI。禁止 uv run python 跑技能脚本。
async 副作用 Action 最小组合(复制验收 checklist)
对每个「会开浏览器 / 长耗时 / 需进度或取消」的 Action,声明时建议同时满足:
executionProfile: "async"(进入任务中心)- 若要让 Agent 触发:
placements含agent - 有可感知副作用时:提供
confirmation.message - 需要用户/Agent 入参时:简单
inputSchema+ entrypoint 中的{{fieldName}} SKILL.md「用户意图路由表」与CLI.md「Action 强制黑名单」出现同一 action id / 命令
默认模板 assets/actions.json 仅含诊断类 sync Action,不要为通过本 checklist 而塞假业务 Action;业务技能按需添加。完整字段见下文 Phase 1。
可选:域前缀 CLI(嵌套子命令)
小技能可继续扁平:entrypoint.command = "run"。
命令变多时,可采用域前缀:command 为域(如 <domain>),业务动词与参数放在 args 数组(如 ["<verb>", "--flag", "{{field}}"])。与扁平入口等价,须仍指向同一 domain service。
模板严格规范 vs 宿主向后兼容
| 角色 | 定位 |
|---|---|
| skill-template | 新技能推荐的严格规范:必填字段、明确类型、additionalProperties: false |
| 宿主运行时 | 向后兼容的历史 manifest 解析器:可能接受部分缺省字段(如 description、placements、entrypoint.args、缺失的 bind.tables) |
新技能不应依赖宿主缺省行为。 复制模板后按 assets/schemas/skill-actions.schema.json 与本文完整填写 manifest。
JSON Schema 使用 additionalProperties: false 表达模板严格边界;这与宿主共享类型中的可选字段并不矛盾——宿主为兼容旧技能可能更宽松,模板为防漂移要求更严。
Action 是否必需
Action 是可选能力:
- 没有宿主直接操作需求的技能,可以不提供
actions.json。 - 需要出现在数据管理按钮、技能详情、定时任务或 Agent 直接调用中的技能,必须提供
assets/actions.json。 - 含浏览器 RPA / 长耗时任务的技能:必须提供至少一条
executionProfile: "async"且placements含agent的 action(见POLICY-SKILL-ACTION-001)。
文件位置
{skill_root}/assets/actions.json
宿主扫描路径示例:
~/.openclaw/skills/your-skill-slug/assets/actions.json
顶层结构
| 字段 | 必填 | 说明 |
|---|---|---|
schemaVersion |
是 | 当前固定为 1 |
skill |
是 | 必须与 SKILL.md 的 metadata.openclaw.slug 一致 |
actions |
是 | Action 数组,每项 id 唯一;数组相对顺序决定数据管理 toolbar / row / batch 技能按钮的展示顺序(见下节) |
模板最小示例见 assets/actions.json;JSON Schema 见 assets/schemas/skill-actions.schema.json。可选 Data Policy 见 POLICY.md 与 assets/schemas/skill-policy-snapshot.schema.json。可选单元格呈现见 CELL_PRESENTATION.md 与 assets/schemas/skill-cell-presentation.schema.json。
六职责正交(必读)
| 字段 / 层 | 只决定什么 | 不决定什么 |
|---|---|---|
placements |
Action 出现在哪里(toolbar / row / batch / cron / agent / skill-detail;row=行级入口,壳由宿主呈现) |
不决定 sync/async,不决定点了是否弹窗,不决定行级用操作列还是右键,不决定谁能点 |
replaces |
可选:接管数据管理默认「新增 / 编辑 / 删除」 | 不强制;无配置时宿主仍直写 SQLite |
bind.tables |
数据管理里出现在哪些业务表 | 不决定业务实现 |
executionProfile |
宿主是同步等待还是异步 Job | 不限制可展示入口,不决定是否弹窗 |
interaction |
可点击入口(数据管理 toolbar/row/batch、默认 CRUD 接管、未来 skill-detail)点了怎么交互 | 不决定 sync/async;cron 触发与 agent 忽略 |
hostEffects / steps |
可选:数据管理交互跑完前后,宿主要不要刷新表 / 清选区 / 级联删等 | 不决定业务写什么;省略 = 宿主不额外改 UI(≥2.8.5 起不再硬编码 mutation 后刷新);cron/agent 忽略 |
cellPresentation |
可选:某表某行某列的语义标色/强调(tone + 说明) | 不替代业务列;不下发 CSS;用途不限(超时、预警、驳回等);见 CELL_PRESENTATION.md |
policy / Snapshot |
可选:当前身份在数据管理下允许哪些 Action / 宿主内置能力 / 行列范围 | 不替代 placements;不替代 domain 写路径鉴权;多数技能不配 = L0 全开 |
entrypoint |
实际执行哪个 CLI 命令与参数 | 不写业务逻辑 |
| domain service | 真正完成什么业务 | 不感知 toolbar / cron / agent 来源 |
一个业务能力通常只定义一个 Action,用 placements 同时挂到多个入口。不要拆成 sync-records-toolbar / sync-records-cron 等副本,除非语义确实不同;即便拆分,也必须调用同一个领域业务内核。需要按用户/角色藏按钮或滤行时,不要按角色复制 Action,应启用顶层 policy 并由技能算出 Snapshot(见 POLICY.md)。
Phase 1 当前稳定支持(新技能应只使用这些)
| 层级 | 稳定字段 / 能力 |
|---|---|
| 顶层 | schemaVersion、skill、actions;可选 policy(Data Policy 启用块);可选 cellPresentation(单元格呈现启用块) |
| action | id、label、description、placements、entrypoint、executionProfile(必填);可选 inputSchema、confirmation、interaction、interactionByPlacement、bind、replaces、hostEffects、steps、authz(仅文档提示) |
| entrypoint | type = cli、command、args(必填 JSON 数组,项为 string / number / boolean) |
| placements | toolbar、row、batch、skill-detail、agent、cron;仅 replaces 时可为空数组 |
| replaces | 可选 "create" | "update" | "delete" — 接管默认新增/编辑/删除(须 bind.tables) |
| bind | { "tables": ["business_table"] };可选 inputMapping(行内/批量预填,见下节) |
| policy | 可选;enabled + entrypoint(推荐 policy CLI);见 POLICY.md。未启用 = L0 |
| cellPresentation | 可选;{ "enabled": true } 时宿主应加载单元格呈现;见 CELL_PRESENTATION.md。未启用 = P0 |
| inputSchema | 根 type: object;properties 使用 string / number / boolean;支持 enum、default、required、sensitive、readOnly |
| confirmation | { "message": "..." } — 风险文案(confirm/form 弹窗黄条;agent 元数据);不是「要不要弹窗」的开关 |
| executionProfile | "sync" | "async"(必须显式写出,禁止依赖缺省) |
| interaction | "auto" | "direct" | "confirm" | "form"(可选;省略≈auto) |
| interactionByPlacement | 可选;按 placement 覆盖为 direct/confirm/form(不可写 auto) |
| hostEffects | 可选;onSuccess / onFailure → reloadTable | refreshCatalog | clearSelection(匠厂宿主 ≥2.8.5) |
| steps | 可选;有序 { when, do, table?, fk? },when=before|afterSuccess|afterFailure;新技能优先(≥2.8.5) |
bind.tables(表级绑定)
{
"bind": {
"tables": ["business_table"]
}
}
规则:
bind为 object,additionalProperties: false;当前允许tables(必填键当存在 bind 时)与可选inputMapping。tables非空数组、元素唯一、英文 snake_case、不得为空字符串。placements含toolbar时必须显式声明非空bind.tables(模板 Schemaif/then+ 自动测试强制)。row/batch建议同样声明bind.tables,避免在无关表上露出按钮;未声明时宿主可能按兼容逻辑在更多表上展示。- 表名须真实存在于技能 SQLite 与
_jiangchang_tables。 - 希望出现在多张表时,显式列出所有表;不要依赖「无 bind 则全表展示」——那是宿主对旧技能的兼容,不是新技能标准。
inputMapping(可选):把行/勾选映射到inputSchema字段,例如"leadId": "$row.$pk"、"ids": "$selection.ids"。适合row/batch。宿主仍会提交这些字段;可用inputSchema.properties.*.readOnly: true在表单中只读展示。concurrency/locks仍未稳定,不要写入新技能 manifest。
replaces(可选:接管默认新增 / 编辑 / 删除)
有领域副作用的表(建目录、加密、级联清理)不要依赖宿主直写 SQLite。此时可为该表声明:
{
"id": "account-add-web",
"label": "新增账号",
"description": "登记网页账号并初始化 profile 目录。",
"replaces": "create",
"placements": [],
"executionProfile": "sync",
"interaction": "form",
"bind": { "tables": ["accounts"] },
"inputSchema": {
"type": "object",
"required": ["platform_key", "account_label"],
"properties": {
"platform_key": { "type": "string", "title": "平台" },
"account_label": { "type": "string", "title": "账号名称" }
}
},
"entrypoint": {
"type": "cli",
"command": "account",
"args": ["add-web", "--platform", "{{platform_key}}", "--label", "{{account_label}}"]
}
}
规则:
- 全可选:无
replaces时,宿主默认按钮仍直写库,行为与以前一致。 - 取值:
create(新增)/update(编辑)/delete(删除)。 - 必须非空
bind.tables;同一技能同一表同一replaces至多一个 Action。 - 与
placements正交:可只接管默认按钮(placements: []),不必再挂 toolbar「第二个新增」。 - 点默认按钮时走该 Action 的
interaction(create/update 常用form;delete 常用confirm)。 update/delete可用inputMapping($row.$pk、$selection.ids)预填主键。- 宿主导入仍直写:有
replaces:create的表慎用宿主导入,或另做 import Action。 - 整表
_jiangchang_tables.readonly=1时仍隐藏写按钮(优先于replaces)。 - 列元数据复用(lookup):create/update 抽屉可将
inputSchema字段对齐业务列,复用中文名与 lookup 下拉:- 优先让属性名 = 物理列名(如
platform_key); - 或
bind.columnMapping:{ "platform": "platform_key" }; - 或字段上写
"column": "platform_key"。 - 不要在 actions.json 里写死会过期的全量平台
enum。
- 优先让属性名 = 物理列名(如
interaction(点击交互方式)
与 executionProfile 正交:一个 Action 可以是 async + direct(一点就进任务中心),也可以是 sync + form(填参后当场返回)。
| 值 | 数据管理体验 | 典型场景 |
|---|---|---|
direct |
一点即跑,无弹窗 | 打开文件位置、无参只读、行内主键已映射 |
confirm |
轻量确认弹窗(无参数区;文案优先 confirmation.message) |
打开浏览器、有副作用但无可编辑入参 |
form |
完整参数表单(现状默认路径) | 导入、查询条件、需用户改写的字段 |
auto / 省略 |
宿主推断:有可编辑参数 → form;仅有 confirmation → confirm;否则 → direct |
旧技能兼容;新技能建议显式写出 |
{
"id": "reveal-profile",
"label": "打开文件位置",
"description": "在资源管理器中打开 Profile 目录。",
"placements": ["row"],
"executionProfile": "sync",
"interaction": "direct",
"bind": {
"tables": ["accounts"],
"inputMapping": { "accountId": "$row.$pk" }
},
"inputSchema": {
"type": "object",
"required": ["accountId"],
"properties": {
"accountId": { "type": "number", "title": "账号 ID", "readOnly": true }
}
},
"entrypoint": {
"type": "cli",
"command": "account",
"args": ["reveal-profile", "{{accountId}}"]
}
}
{
"id": "open-browser",
"label": "打开浏览器",
"placements": ["row"],
"executionProfile": "async",
"interaction": "confirm",
"confirmation": { "message": "将用该账号 Profile 打开浏览器,仅供查看。" },
"bind": {
"tables": ["accounts"],
"inputMapping": { "accountId": "$row.$pk" }
},
"inputSchema": {
"type": "object",
"required": ["accountId"],
"properties": {
"accountId": { "type": "number", "readOnly": true }
}
},
"entrypoint": {
"type": "cli",
"command": "account",
"args": ["open", "{{accountId}}"]
}
}
可选 interactionByPlacement:同一 Action 在不同入口用不同交互(例如 row: "direct"、toolbar: "form")。值只能是 direct/confirm/form,不能写 auto。
边界:
- cron 配置:仍展示可编辑参数;
confirmation.message可作为配置页风险提示(由宿主决定)。 - cron 触发 / agent:忽略
interaction(无人值守 / 模型填参);confirmation对 agent 仍作requiresConfirmation元数据。 - 不要用
interaction: "direct"掩盖需要用户填写的可编辑字段——宿主在auto下会因可编辑参数回落到form;显式direct+ 可编辑字段时参数取 default/预填,作者须自觉。
hostEffects / steps(执行前后宿主编排,≥2.8.5)
与 placements / executionProfile / interaction 正交。决定的是:数据管理里点完 Action 之后(或之前),宿主要不要刷新当前表、刷新目录、清空多选、级联删子表等。
- 省略 / 空 ⇒ 宿主不额外改 UI(≥2.8.5 起不再对 mutation 硬编码刷新)。本地库若已由技能写新,界面仍可能旧,直到用户点内置「刷新」或本 Action 声明了
reloadTable。 - 仅数据管理交互路径生效(toolbar / row / batch / skill-detail /
replaces);cron 与 agent 忽略(与interaction相同)。 - 需匠厂宿主 ≥ 2.8.5;更旧宿主会忽略未知字段(若未做严格 Schema 校验)。
- 新技能优先写
steps;hostEffects仍可作为「只刷 UI」的简写。两者可并存;同一 UI 效果若两边都声明,宿主可能各跑一次。
hostEffects(UI 副作用简写)
{
"hostEffects": {
"onSuccess": ["reloadTable"],
"onFailure": ["clearSelection"]
}
}
| 字段 | 触发时机 |
|---|---|
onSuccess |
sync 退出码 0;或 async 任务已被任务中心接收(不是 Job 跑完) |
onFailure |
sync 失败;或 async 启动被拒 |
闭集 effect id:reloadTable(重载当前表 + 常伴随 Data Policy 再拉)、refreshCatalog(刷新技能目录)、clearSelection(清空多选)。未知 id 丢弃。
async 注意:sync-data 一类长同步若写 onSuccess: ["reloadTable"],会在入队成功时就刷表,可能仍是旧数据;更适合 sync 的新建/登记,或等 Job 真正完成后再刷(若宿主后续扩展完成回调)。
steps(有序编排,推荐)
{
"steps": [
{ "when": "before", "do": "deleteByFk", "table": "child_rows", "fk": "parent_id" },
{ "when": "afterSuccess", "do": "reloadTable" },
{ "when": "afterFailure", "do": "clearSelection" }
]
}
when |
含义 |
|---|---|
before |
调用 CLI 之前 |
afterSuccess |
同 hostEffects.onSuccess |
afterFailure |
同 hostEffects.onFailure |
do |
说明 |
|---|---|
reloadTable / refreshCatalog / clearSelection |
同 hostEffects |
deleteByFk |
按外键批量删子表;须 table + fk;行按钮会把当前行主键当父键 |
deleteRows |
删指定表行;须 table |
规则:单次最多 8 步;未知步骤丢弃;deleteByFk / deleteRows 仅走 Skill Action steps 路径时可删 metadata_readonly 投影表(人工 CRUD 仍守只读)。整库只读 / 视图仍禁止写。
典型:业务表「新建 / 登记 / 更新」成功后加 { "when": "afterSuccess", "do": "reloadTable" },避免用户傻等旧表格。
{
"id": "register-one",
"label": "登记本行",
"description": "更新当前行业务字段。",
"placements": ["row"],
"executionProfile": "sync",
"interaction": "form",
"bind": {
"tables": ["business_records"],
"inputMapping": { "recordId": "$row.$pk" }
},
"steps": [{ "when": "afterSuccess", "do": "reloadTable" }],
"entrypoint": {
"type": "cli",
"command": "register",
"args": ["--id", "{{recordId}}"]
}
}
默认模板 actions.json 仅含 health / version / config-path,不放在 toolbar/row/batch,故无需 bind 示例污染默认 manifest。业务示例:
{
"id": "sync-records",
"label": "同步记录",
"description": "从外部来源同步到技能本地数据库,不生成导出文件。",
"placements": ["toolbar", "cron", "agent", "skill-detail"],
"executionProfile": "async",
"bind": { "tables": ["business_records"] },
"entrypoint": { "type": "cli", "command": "sync-records", "args": [] }
}
行内示例:
{
"id": "retry-one",
"label": "重试本行",
"description": "对当前行执行一次业务重试。",
"placements": ["row"],
"executionProfile": "async",
"bind": {
"tables": ["business_records"],
"inputMapping": { "recordId": "$row.$pk" }
},
"inputSchema": {
"type": "object",
"required": ["recordId"],
"properties": {
"recordId": { "type": "string", "title": "记录 ID", "readOnly": true }
}
},
"entrypoint": {
"type": "cli",
"command": "retry",
"args": ["--id", "{{recordId}}"]
}
}
预留能力(当前不可当作已实现能力)
| 类别 | 预留项 | 说明 |
|---|---|---|
| action 字段 | concurrency、locks |
并发与锁控制,未稳定开放 |
| inputSchema | array、nested object、oneOf 等 |
复杂表单,不属于当前推荐范围 |
bind、row、batch 不是保留能力;已按匠厂宿主正式支持写入本规范。
执行模型
宿主将 action 转为 argv,再用共享 Python(用户数据目录下 python-runtime/.venv)执行:
python {skill_root}/scripts/main.py <command> <args...>
entrypoint.type当前只支持clientrypoint.command→ CLI 子命令(须真实存在)entrypoint.args→ 子命令参数(必须为 JSON 数组){{fieldName}}→ 来自inputSchema用户输入的简单模板替换
完整子命令定义见 scripts/cli/app.py。
executionProfile(仅 sync / async)
心智:多数 Action 按 sync(短调用、不进任务中心);只有长耗时 / RPA / 需进度控制时才标 async。匠厂宿主若省略该字段,按 sync 处理;模板与新技能仍要求每个 Action 显式写出 sync 或 async,禁止发明 auto / background / deferred,也禁止赌省略行为。
| 值 | 宿主行为 | 任务中心 |
|---|---|---|
sync(或省略时的宿主缺省) |
调用方等待结束,直接返回结构化结果或结构化错误;不创建后台 Job | 不进 |
async(须显式声明) |
宿主创建后台 Job,立即返回 jobId;用 emit / checkpoint / finish 报告进度与终态 |
进入 |
合法组合(全部允许):sync|async × toolbar|row|batch|cron|agent|skill-detail。
经验建议(不是 placement 硬限制):耗时不可预测、需要暂停/停止/进度展示的任务,用 async;其余默认写 sync。
直接执行短 CLI 时,终端自然等待进程结束。宿主通过 Action 调用同一 CLI 时,再按 executionProfile 决定同步等待还是建 Job。技能不得自行实现第二套任务中心或后台队列。
CLI 输出契约
技能 CLI 必须:
- 使用稳定的退出码
- 成功时输出可解析的结构化结果
- 失败时输出稳定错误信息
- 对可预期错误提供稳定错误码
- 对用户可处理的问题提供
HINT - 不依赖 Agent 连续对话才能完成
- 不自行实现宿主任务中心
- 不在 CLI 中硬编码宿主安装目录
- 不直接依赖某个具体 UI 页面
建议错误输出格式:
ERROR:<CODE>: <message>
HINT: <next step>
placements(入口位置)
| 值 | 含义 |
|---|---|
toolbar |
数据管理表顶栏技能按钮(须配合 bind.tables) |
row |
数据管理行级入口(建议 bind.tables + inputMapping;表需有主键)。技能声明后,由宿主呈现为操作列链接、行右键菜单和/或行内「⋯」等壳;不新增 row-context-menu 等 placement |
batch |
数据管理批量操作(需勾选行;无勾选时宿主禁用按钮) |
skill-detail |
技能详情页直调(与安装/四 Tab 同属技能市场详情;已声明则须自测) |
agent |
Agent 可直接调用(run_skill_action) |
cron |
定时任务「技能直调」 |
行级入口 row(宿主呈现契约)
- 技能决定有什么:
placements含"row"(且通过bind.tables/ policy 等过滤)的 Action,构成该表行的技能菜单项集合;配什么就出现什么。 - 宿主决定怎么摆:可用操作列、行右键、行内「⋯」等呈现同一批 Action;点击均走同一
launch(placement: "row"),interaction/executionProfile与壳无关。 - 顺序:各壳内技能项顺序 = 下方「数据管理技能按钮顺序」契约(
actions数组相对顺序)。 - 宿主内置项:查看 / 编辑 / 删除由宿主提供,不是技能
actions.json配置出来的;若出现在行右键,须与技能项分组(例如分隔线后),且不得要求技能再配一份菜单 DSL。 - 禁止:为右键单独发明 placement、菜单注册表或第二套 Action 列表。
数据管理技能按钮顺序(宿主正式契约)
宿主没有单独的 sortOrder / uiOrder 字段。同一 placement(toolbar / row / batch)下,技能按钮的展示顺序 = actions 数组中匹配该项 placement(且通过 bind.tables 过滤)的相对先后。
规则:
- 想调整顺序 → 调整
actions数组先后(不必改id/label)。 - 无关 placement 的 Action(如仅
skill-detail的health)夹在中间不影响 toolbar/row 的相对顺序;宿主按匹配子集保序渲染。 - 同一 Action 可同时挂多个 placement;它在各入口的位置,分别是该入口匹配子集里的相对位置。
- 宿主内置按钮不参与本契约、位置固定:
- 表顶栏右侧:删除(有勾选时)/ 刷新 / 新增 / 导入 / 导出 —— 技能 toolbar/batch 按钮在左侧,不能与右侧内置按钮混排。
- 行级:技能
row项按本顺序出现在操作列 / 行右键(及可选「⋯」)中;宿主「查看」→(非只读)「编辑」→「删除」为内置项,位置由宿主固定(操作列常在技能项之后;右键中可与技能项分组)。
- 表顶栏全部直接展示,无「更多操作」溢出菜单:匹配到的 toolbar/batch 技能按钮一律渲染(顺序仍按本契约)。行级不以「顶栏溢出菜单」模型截断;行右键是
row的正式呈现壳之一,不是 toolbar 式「更多操作」截断。 - 表顶栏宽窄布局(宿主行为,技能无需配置):
- 够宽:左右各横排一行(左技能按钮 + 右宿主工具)。
- 不够宽:保持左右分栏,栏内按钮上下竖排(左栏技能、右栏刷新/导出等)。
禁止:
- 臆造
sortOrder/order/priority等字段指望宿主排序(模板 SchemaadditionalProperties: false会拒收)。 - 依赖或宣传表顶栏「更多操作」溢出菜单(宿主已取消该能力)。
- 把「表格行数据默认排序」与按钮顺序混淆——行排序见
SCHEMA.md的default_sort_json。 - 新增
row-context-menu等 placement,或要求技能再维护一份与row平行的菜单清单。
Action 类型 × placements(常见示例,不是限制)
下表只表示常见用法示例。实际 placements 以 manifest 配置为准;sync / async 不影响展示入口。已声明的入口都要在宿主自测,不要只测其中一条。
| Action 类型 | 常见 executionProfile | 常见 placements | confirmation |
|---|---|---|---|
| health / version / config-path | sync | skill-detail, agent | 无 |
| 统计 / 只读查询 | sync | skill-detail, agent | 无 |
| 数据同步(外源 → 本地库) | sync 或 async | toolbar + cron + agent + skill-detail(按需) | 可选 |
| 单行重试 / 行内处理 | sync 或 async | row(可加 agent) | 可选 |
| 批量处理勾选行 | sync 或 async | batch(可加 toolbar/cron) | 可选 |
| 导入 / 重置 | sync 或 async | skill-detail, agent | 可选 |
| 单条副作用 RPA | async(建议) | agent, skill-detail | 建议 |
| 批量顺序 pick RPA | async(建议) | toolbar, cron, agent | 建议 |
同步数据 vs 导出当前表 vs 特殊业务报告
不要混用「导出」一词:
| 能力 | 语义 | 谁负责 |
|---|---|---|
| 同步数据(sync / refresh / collect) | 外部来源 → 技能本地数据库 | 技能 Action / domain service |
| 导出当前数据表 | 技能本地数据库 → CSV/Excel 等 | 数据管理页宿主统一导出 |
| 生成特殊业务报告 | 多表合并、特殊排版或附加计算 | 仅当系统导出无法满足时,才提供独立 export-* Action |
同步型 Action 默认:读外部数据、写技能自己的库、不生成 CSV/Excel/JSON 文件、不重复实现宿主表导出。兼容旧 export 命令若需要刷新数据,必须调用同一个 sync 业务内核。通用同步语义见 SCHEMA.md 与 ../development/SKILL_ACTION_RUNTIME.md。
inputSchema 与参数表单
当前宿主稳定支持:
object/string/number/booleanenum/default/required/sensitive/readOnly- 属性级
description(表单标签下方灰字说明) - 简单模板替换(
{{fieldName}})
与数据管理「新增 / 编辑」表单的分工(勿混用配置入口):
| 表单 | 短标题 | 说明灰字 | 默认值 |
|---|---|---|---|
| Skill Action 弹窗 | inputSchema.title |
inputSchema.description |
inputSchema.default |
| 数据管理新增/编辑 | _jiangchang_columns.display_name |
_jiangchang_columns.description |
物理列 SQLite DEFAULT |
CRUD 侧宿主义务与禁止事项见 SCHEMA.md「新增/编辑表单:字段说明与默认值(宿主支持)」。同一业务含义两边文案应对齐,但分别配置。
示例:
{
"inputSchema": {
"type": "object",
"required": ["query"],
"properties": {
"query": {
"type": "string",
"title": "查询条件",
"description": "支持关键词或完整业务编号"
},
"limit": {
"type": "number",
"title": "返回数量",
"description": "最多返回多少条;填 0 表示不限制(若业务支持)",
"default": 50
}
}
}
}
批量 pick 参数约定(有队列表时):
{
"pickCount": {
"type": "number",
"title": "处理数量",
"description": "从队列选取 pending 记录条数",
"default": 1,
"minimum": 1
}
}
约定:
boolean在宿主中渲染为开关enum在宿主中渲染为选择框required字段在提交前校验sensitive字段不得出现在低信任入口readOnly: true时数据管理表单只读展示该字段(仍随提交传入);适合行内/勾选预填的主键、编号列表placements含batch的动作在数据管理表顶常驻,无勾选时禁用(与表删除一致)- 需要确认的副作用操作使用
confirmation.message - 模板参数使用
{{fieldName}},且必须在inputSchema.properties中声明 entrypoint.args项当前只允许string、number、boolean;不允许对象或null- 不要在当前模板中宣传
nested object、oneOf、复杂数组等尚未稳定支持的能力
风险与入口配置
- 查询、诊断、版本检查可以放到
skill-detail或agent - 低风险、常用动作才考虑放
toolbar(须bind.tables;executionProfile 按耗时自选) - 会修改本地数据、访问外部系统、执行长时间任务的动作必须谨慎配置
- 有副作用的动作应添加
confirmation.message - 高风险动作不应默认出现在
toolbar - 含
sensitive参数的 action 不应放入toolbar或cron,除非有明确安全设计 - 不要为了「按钮多」而暴露所有 CLI 子命令
- 一个 CLI 命令可以拆成多个语义清晰的 action,但每个 action 必须有明确语义,并复用同一业务内核
- Agent 必须用
run_skill_action,禁止exec直跑长任务 CLI(见SKILL_ACTION_RUNTIME.md) - 禁止按
source=toolbar/cron/agent/skill-detail在业务代码中分叉业务行为
模板示例 action 一览
| id | CLI | executionProfile | placements | 说明 |
|---|---|---|---|---|
health |
health |
sync | skill-detail, agent | 运行环境检查 |
version |
version |
sync | skill-detail | 版本 JSON |
config-path |
config-path |
sync | skill-detail | 配置路径 JSON |
业务技能复制后,按需增加例如:
| 模式 | id 示例 | executionProfile | placements | bind |
|---|---|---|---|---|
| 数据同步 | sync-records |
async 或 sync | toolbar, cron, agent, skill-detail | 必填 tables |
| 单条 RPA | your-run |
async(建议) | agent, skill-detail | 按需 |
| 队列 pick | your-run-pick |
async(建议) | toolbar, cron, agent | 有 toolbar 则必填 |
| 统计 | your-stats |
sync | skill-detail, agent | 无 |
不需要宿主入口时可删除整个 actions.json(无 RPA 长任务时)。
与宿主 API(参考)
| 宿主 API | 用途 |
|---|---|
GET /api/skill-actions/{skillSlug} |
读取 manifest |
POST /api/skill-actions/run |
{ skillSlug, actionId, input?, source? } |
GET /api/skill-actions/jobs |
任务中心 |
具体路径与字段以宿主实现为准;技能侧只需保证 manifest 与 CLI 契约稳定。