weaver-work-cli 0.1.6 → 0.1.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +14 -9
- package/dist/cmd/skills/index.js +60 -0
- package/dist/internal/e10/auth/commands.js +44 -31
- package/dist/internal/e10/auth/session.js +44 -3
- package/dist/internal/e10/auth/xiaoe.js +363 -11
- package/dist/internal/e10/context.js +4 -2
- package/dist/internal/skills/detector.js +42 -0
- package/dist/internal/skills/install.js +50 -3
- package/dist/shortcuts/archive/render/search-format.js +12 -3
- package/dist/shortcuts/ebuilder-form/continuation.js +70 -0
- package/dist/shortcuts/ebuilder-form/errors.js +54 -0
- package/dist/shortcuts/ebuilder-form/host.js +1238 -0
- package/dist/shortcuts/ebuilder-form/index.js +108 -0
- package/dist/shortcuts/ebuilder-form/manifest.js +347 -0
- package/dist/shortcuts/ebuilder-form/operations/read.js +157 -0
- package/dist/shortcuts/ebuilder-form/operations/registry.js +56 -0
- package/dist/shortcuts/ebuilder-form/operations/shared.js +132 -0
- package/dist/shortcuts/ebuilder-form/operations/types.js +19 -0
- package/dist/shortcuts/ebuilder-form/operations/write.js +277 -0
- package/dist/shortcuts/ebuilder-form/operations.js +8 -0
- package/dist/shortcuts/ehr/operations/salary.js +2 -140
- package/dist/shortcuts/im/continuation.js +70 -0
- package/dist/shortcuts/{yimiaoban → im}/errors.js +14 -14
- package/dist/shortcuts/{yimiaoban → im}/host.js +26 -26
- package/dist/shortcuts/{yimiaoban → im}/index.js +42 -42
- package/dist/shortcuts/{yimiaoban → im}/manifest.js +7 -6
- package/dist/shortcuts/{yimiaoban → im}/operations/file-user.js +54 -41
- package/dist/shortcuts/{yimiaoban → im}/operations/group-read.js +46 -44
- package/dist/shortcuts/{yimiaoban → im}/operations/group-write.js +113 -66
- package/dist/shortcuts/{yimiaoban → im}/operations/msg-sync.js +164 -141
- package/dist/shortcuts/{yimiaoban → im}/operations/msg-write.js +47 -47
- package/dist/shortcuts/{yimiaoban → im}/operations/person.js +10 -10
- package/dist/shortcuts/{yimiaoban → im}/operations/registry.js +10 -8
- package/dist/shortcuts/{yimiaoban → im}/operations/session.js +82 -83
- package/dist/shortcuts/im/operations/shared.js +442 -0
- package/dist/shortcuts/{yimiaoban → im}/operations/types.js +1 -1
- package/dist/shortcuts/im/operations/user-remind.js +201 -0
- package/dist/shortcuts/{yimiaoban → im}/operations/write-util.js +7 -7
- package/dist/shortcuts/{yimiaoban → im}/operations.js +3 -3
- package/dist/shortcuts/index.js +10 -2
- package/dist/shortcuts/invoice/manifest.js +113 -10
- package/dist/shortcuts/invoice/operations/import.js +39 -14
- package/dist/shortcuts/invoice/operations/reim.js +38 -18
- package/dist/shortcuts/invoice/operations/shared.js +35 -6
- package/dist/shortcuts/jiuchuanhui/manifest.js +3 -3
- package/dist/shortcuts/jiuchuanhui/operations/registry.js +2 -2
- package/dist/shortcuts/{yimiaoban → okr}/continuation.js +10 -10
- package/dist/shortcuts/okr/errors.js +70 -0
- package/dist/shortcuts/okr/host.js +169 -0
- package/dist/shortcuts/okr/index.js +155 -0
- package/dist/shortcuts/okr/manifest.js +70 -0
- package/dist/shortcuts/okr/operations/link.js +305 -0
- package/dist/shortcuts/okr/operations/read.js +481 -0
- package/dist/shortcuts/okr/operations/registry.js +31 -0
- package/dist/shortcuts/okr/operations/shared.js +381 -0
- package/dist/shortcuts/okr/operations/types.js +88 -0
- package/dist/shortcuts/okr/operations/write.js +838 -0
- package/dist/shortcuts/okr/operations.js +8 -0
- package/dist/shortcuts/project/continuation.js +70 -0
- package/dist/shortcuts/project/errors.js +53 -0
- package/dist/shortcuts/project/host.js +160 -0
- package/dist/shortcuts/project/index.js +106 -0
- package/dist/shortcuts/project/manifest.js +36 -0
- package/dist/shortcuts/project/operations/read.js +551 -0
- package/dist/shortcuts/project/operations/registry.js +31 -0
- package/dist/shortcuts/project/operations/shared.js +68 -0
- package/dist/shortcuts/project/operations/types.js +39 -0
- package/dist/shortcuts/project/operations/write.js +266 -0
- package/dist/shortcuts/project/operations.js +8 -0
- package/dist/shortcuts/workflow/continuation.js +508 -0
- package/dist/shortcuts/workflow/endpoints.js +149 -0
- package/dist/shortcuts/workflow/errors.js +112 -0
- package/dist/shortcuts/workflow/host.js +224 -0
- package/dist/shortcuts/workflow/index.js +116 -0
- package/dist/shortcuts/workflow/manifest.js +30 -0
- package/dist/shortcuts/workflow/operations/form.js +4159 -0
- package/dist/shortcuts/workflow/operations/read.js +3778 -0
- package/dist/shortcuts/workflow/operations/registry.js +33 -0
- package/dist/shortcuts/workflow/operations/shared.js +167 -0
- package/dist/shortcuts/workflow/operations/types.js +44 -0
- package/dist/shortcuts/workflow/operations/write.js +1991 -0
- package/dist/shortcuts/workflow/operations.js +119 -0
- package/dist/shortcuts/workflow/state.js +182 -0
- package/docs/SKILL.md +5 -3
- package/docs/_catalog.md +10 -1
- package/docs/agent-invoice.md +2 -2
- package/docs/agent-skill-install.md +2 -2
- package/docs/e10-auth.md +3 -1
- package/docs/ebuilder-form.md +38 -0
- package/docs/im.md +104 -0
- package/docs/invoice.md +5 -5
- package/docs/okr.md +122 -0
- package/docs/operation-manual.md +10 -7
- package/docs/project.md +69 -0
- package/docs/skill-review-2026-09-19.md +68 -0
- package/package.json +3 -2
- package/scripts/package-skill.mjs +38 -11
- package/scripts/sync-connector-skills.mjs +172 -0
- package/skill-template/business-info.json +357 -16
- package/skill-template/domains/ebuilder-form.md +5 -0
- package/skill-template/domains/okr.md +18 -0
- package/skill-template/domains/shijingran.md +3 -0
- package/skill-template/domains/skill-maker.md +4 -4
- package/skill-template/domains/workflow.md +22 -0
- package/skill-template/domains/yepiaotong.md +4 -2
- package/skill-template/domains/yimiaoban.md +13 -10
- package/skill-template/product.json +5 -0
- package/skill-template/skill-template.md +1 -0
- package/skills/weaver-e10-calendar/SKILL.md +5 -1
- package/skills/weaver-e10-calendar/references/calendar-query.md +7 -0
- package/skills/weaver-e10-calendar/references/source-manifest.json +314 -32
- package/skills/weaver-e10-ebuilder-form/SKILL.md +123 -0
- package/skills/weaver-e10-ebuilder-form/references/context-routing.md +90 -0
- package/skills/weaver-e10-ebuilder-form/references/custom-api.md +86 -0
- package/skills/weaver-e10-ebuilder-form/references/disabled-capabilities.md +50 -0
- package/skills/weaver-e10-ebuilder-form/references/fields-browser.md +100 -0
- package/skills/weaver-e10-ebuilder-form/references/list-nlist.md +91 -0
- package/skills/weaver-e10-ebuilder-form/references/openapi-read.md +74 -0
- package/skills/weaver-e10-ebuilder-form/references/openapi-write.md +86 -0
- package/skills/weaver-e10-ebuilder-form/references/source-manifest.json +107 -0
- package/skills/weaver-e10-esb/SKILL.md +1 -1
- package/skills/weaver-e10-esb/references/source-manifest.json +15 -14
- package/skills/weaver-e10-hrm/SKILL.md +1 -1
- package/skills/weaver-e10-hrm/references/source-manifest.json +357 -38
- package/skills/weaver-e10-jiuchuanhui/SKILL.md +22 -4
- package/skills/weaver-e10-jiuchuanhui/references/clue.md +4 -2
- package/skills/weaver-e10-jiuchuanhui/references/contact.md +1 -1
- package/skills/weaver-e10-jiuchuanhui/references/customer.md +3 -3
- package/skills/weaver-e10-jiuchuanhui/references/disabled-capabilities.md +1 -1
- package/skills/weaver-e10-jiuchuanhui/references/discovery-config.md +10 -10
- package/skills/weaver-e10-jiuchuanhui/references/general-helpers.md +3 -3
- package/skills/weaver-e10-jiuchuanhui/references/sale.md +7 -7
- package/skills/weaver-e10-jiuchuanhui/references/source-manifest.json +3 -3
- package/skills/weaver-e10-jucailin/SKILL.md +2 -2
- package/skills/weaver-e10-mail/SKILL.md +22 -6
- package/skills/weaver-e10-meeting/SKILL.md +22 -1
- package/skills/weaver-e10-okr/SKILL.md +139 -0
- package/skills/weaver-e10-okr/references/okr-align.md +59 -0
- package/skills/weaver-e10-okr/references/okr-keyresult.md +68 -0
- package/skills/weaver-e10-okr/references/okr-link-routing.md +67 -0
- package/skills/weaver-e10-okr/references/okr-query.md +105 -0
- package/skills/weaver-e10-okr/references/okr-write.md +94 -0
- package/skills/weaver-e10-okr/references/source-manifest.json +672 -0
- package/skills/weaver-e10-plan/SKILL.md +3 -3
- package/skills/weaver-e10-plan/references/plan-report-write.md +1 -1
- package/skills/weaver-e10-plan/references/source-manifest.json +20 -20
- package/skills/weaver-e10-qiyecheng/SKILL.md +21 -1
- package/skills/weaver-e10-qiyecheng/references/source-manifest.json +17 -17
- package/skills/weaver-e10-shared/SKILL.md +79 -11
- package/skills/weaver-e10-shared/references/e10-auth-and-session.md +41 -8
- package/skills/weaver-e10-shared/references/non-interactive-environment.md +78 -0
- package/skills/weaver-e10-shared/references/weaver-e10-installation.md +39 -0
- package/skills/weaver-e10-shijingran/SKILL.md +83 -0
- package/skills/weaver-e10-shijingran/references/field-resolution.md +105 -0
- package/skills/weaver-e10-shijingran/references/operations.md +154 -0
- package/skills/weaver-e10-shijingran/references/source-manifest.json +1380 -0
- package/skills/weaver-e10-shijingran/references/write-operations.md +90 -0
- package/skills/weaver-e10-skill-maker/SKILL.md +26 -9
- package/skills/weaver-e10-skill-maker/references/business-skill-generation.md +39 -8
- package/skills/weaver-e10-skill-maker/references/detector-validation.md +25 -8
- package/skills/weaver-e10-skill-maker/references/module-cli-generation.md +66 -5
- package/skills/weaver-e10-skill-maker/references/module-gap-audit-and-repair.md +86 -0
- package/skills/weaver-e10-skill-maker/references/source-update-detection.md +59 -5
- package/skills/weaver-e10-skill-maker/references/weaver-skill-style.md +16 -8
- package/skills/weaver-e10-wenshuding/SKILL.md +28 -4
- package/skills/weaver-e10-wenshuding/references/archive-search.md +14 -0
- package/skills/weaver-e10-wenshuding/references/source-manifest.json +27 -26
- package/skills/weaver-e10-workflow/SKILL.md +250 -0
- package/skills/weaver-e10-workflow/references/source-manifest.json +1062 -0
- package/skills/weaver-e10-workflow/references/workflow-agent-entry.md +96 -0
- package/skills/weaver-e10-workflow/references/workflow-batch.md +275 -0
- package/skills/weaver-e10-workflow/references/workflow-create.md +182 -0
- package/skills/weaver-e10-workflow/references/workflow-edit.md +106 -0
- package/skills/weaver-e10-workflow/references/workflow-memory.md +165 -0
- package/skills/weaver-e10-workflow/references/workflow-operate.md +153 -0
- package/skills/weaver-e10-workflow/references/workflow-query.md +821 -0
- package/skills/weaver-e10-workflow/references/workflow-share.md +117 -0
- package/skills/weaver-e10-workflow/references/workflow-view.md +189 -0
- package/skills/weaver-e10-yepiaotong/SKILL.md +28 -28
- package/skills/weaver-e10-yepiaotong/references/invoice-disabled-capabilities.md +11 -5
- package/skills/weaver-e10-yepiaotong/references/invoice-import.md +14 -8
- package/skills/weaver-e10-yepiaotong/references/invoice-issuing-examples.md +9 -43
- package/skills/weaver-e10-yepiaotong/references/invoice-issuing.md +8 -0
- package/skills/weaver-e10-yepiaotong/references/invoice-reim.md +13 -17
- package/skills/weaver-e10-yepiaotong/references/reim-api-reference.md +6 -7
- package/skills/weaver-e10-yepiaotong/references/reim-examples.md +2 -2
- package/skills/weaver-e10-yepiaotong/references/source-manifest.json +1155 -553
- package/skills/weaver-e10-yimiaoban/SKILL.md +56 -38
- package/skills/weaver-e10-yimiaoban/references/ding-write.md +8 -8
- package/skills/weaver-e10-yimiaoban/references/error-codes.md +16 -0
- package/skills/weaver-e10-yimiaoban/references/field-resolution.md +10 -10
- package/skills/weaver-e10-yimiaoban/references/file-user-i18n.md +12 -12
- package/skills/weaver-e10-yimiaoban/references/group-read.md +16 -16
- package/skills/weaver-e10-yimiaoban/references/group-write.md +17 -15
- package/skills/weaver-e10-yimiaoban/references/msg-read.md +21 -17
- package/skills/weaver-e10-yimiaoban/references/msg-write.md +10 -10
- package/skills/weaver-e10-yimiaoban/references/person.md +6 -6
- package/skills/weaver-e10-yimiaoban/references/safety-boundaries.md +15 -11
- package/skills/weaver-e10-yimiaoban/references/session-sysmsg.md +11 -10
- package/skills/weaver-e10-yimiaoban/references/source-manifest.json +2164 -154
- package/skills/weaver-e10-yimiaoban/references/user-remind.md +75 -0
- package/skills/weaver-e10-ziguanjia/SKILL.md +4 -2
- package/skills/weaver-e10-ziguanjia/references/source-manifest.json +99 -29
- package/tools/weaver-skill-detector-1.0.13/SKILL.md +253 -0
- package/tools/weaver-skill-detector-1.0.13/_meta.json +6 -0
- package/tools/weaver-skill-detector-1.0.13/references/checklist.md +298 -0
- package/tools/weaver-skill-detector-1.0.13/scripts/validate_skill.py +4190 -0
- package/dist/shortcuts/yimiaoban/operations/shared.js +0 -236
- package/docs/yimiaoban.md +0 -86
- package/skills/weaver-e10-calendar/product.json +0 -8
- package/skills/weaver-e10-esb/product.json +0 -8
- package/skills/weaver-e10-hrm/product.json +0 -8
- package/skills/weaver-e10-jiuchuanhui/product.json +0 -8
- package/skills/weaver-e10-jucailin/product.json +0 -8
- package/skills/weaver-e10-mail/product.json +0 -8
- package/skills/weaver-e10-meeting/product.json +0 -8
- package/skills/weaver-e10-plan/product.json +0 -8
- package/skills/weaver-e10-qiyecheng/product.json +0 -8
- package/skills/weaver-e10-skill-maker/product.json +0 -8
- package/skills/weaver-e10-wenshuding/product.json +0 -8
- package/skills/weaver-e10-yepiaotong/product.json +0 -8
- package/skills/weaver-e10-yepiaotong/references/invoice-red.md +0 -261
- package/skills/weaver-e10-yimiaoban/product.json +0 -8
- package/skills/weaver-e10-ziguanjia/product.json +0 -8
- /package/dist/shortcuts/{yimiaoban → im}/operations/msg-parse.js +0 -0
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
# Agent 入口与 Schema
|
|
2
|
+
|
|
3
|
+
## 什么时候读取
|
|
4
|
+
|
|
5
|
+
使用 `weaver-work-cli workflow` 处理流程查询、查看、打开、取日志或打开 OA 页面之前,或需要选择 operation、确认输入字段结构时,先读取本文件。
|
|
6
|
+
|
|
7
|
+
本文件只覆盖**只读类** operation(`search` / `todoStat` / `detail` / `summary` / `open` / `requestLog` / `pageOpen` / `memoryPrompt`)。发起、操作、批量、编辑、共享等写操作不在本目录参考文档范围内。
|
|
8
|
+
|
|
9
|
+
## 准备与探查命令
|
|
10
|
+
|
|
11
|
+
```text
|
|
12
|
+
weaver-work-cli --version
|
|
13
|
+
weaver-work-cli doctor --e10
|
|
14
|
+
weaver-work-cli workflow schema
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
如未登录,按共享规则读取登录与会话文档后处理。
|
|
18
|
+
|
|
19
|
+
`weaver-work-cli workflow schema` 是可用 operation、输入字段、固定参数与风险等级的第一信息源。所有 JSON 字段名以 schema 为准(camelCase,如 `pageSize`、`requestId`),不要臆造 schema 中不存在的字段。
|
|
20
|
+
|
|
21
|
+
## 固定入口
|
|
22
|
+
|
|
23
|
+
Agent 统一通过 operation 入口调用:
|
|
24
|
+
|
|
25
|
+
```text
|
|
26
|
+
weaver-work-cli --json workflow run workflow.search --input-json '{"category":"todo","pageSize":10}'
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
统一用 `--input-json` **内联**传入,`planJson`、`filterFields` 数组等嵌套结构同样内联(几百字符即可承载,不要写 JSON 文件);仅当 JSON 很大或含 shell 难转义字符时才用 UTF-8 文件配 `--input <path>`。按环境选择示例:
|
|
30
|
+
|
|
31
|
+
Windows PowerShell:
|
|
32
|
+
|
|
33
|
+
```powershell
|
|
34
|
+
weaver-work-cli --json workflow run workflow.search --input-json '{"category":"todo","pageSize":10}'
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
macOS/Linux(bash/zsh):
|
|
38
|
+
|
|
39
|
+
```bash
|
|
40
|
+
weaver-work-cli --json workflow run workflow.search --input-json '{"category":"todo","pageSize":10}'
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## Operation 总览(只读)
|
|
44
|
+
|
|
45
|
+
| Operation | 用途 | 详细文档 |
|
|
46
|
+
| --- | --- | --- |
|
|
47
|
+
| `workflow.search` | 分页查询待办/已办/我发起/全部流程,支持多维度筛选与 plan 批量编排取数 | [workflow-query.md](./workflow-query.md) |
|
|
48
|
+
| `workflow.todoStat` | 按「工作流 × 参与节点 × 参与身份」三元组统计当前用户待办分组计数(智能分组第一步) | [workflow-query.md](./workflow-query.md) |
|
|
49
|
+
| `workflow.detail` | 按 requestId 或列表序号查看流程完整详情(基础信息 + 表单数据 + 签字意见) | [workflow-view.md](./workflow-view.md) |
|
|
50
|
+
| `workflow.summary` | 按 requestId 或列表序号生成流程业务摘要上下文(不标记已读) | [workflow-view.md](./workflow-view.md) |
|
|
51
|
+
| `workflow.open` | 按 requestId 或列表序号生成流程详情打开动作(URL + clientAction) | [workflow-view.md](./workflow-view.md) |
|
|
52
|
+
| `workflow.requestLog` | 按页查询流程签字意见/流转日志 | [workflow-view.md](./workflow-view.md) |
|
|
53
|
+
| `workflow.pageOpen` | 生成常用 OA 页面(待办/已办/草稿/监控等)或动态页(create/view)的打开地址 | [workflow-view.md](./workflow-view.md) |
|
|
54
|
+
| `workflow.memoryPrompt` | 读取用户记忆提示词;顺带返回 OA 版本与当前用户身份,无需再单独查询 | 本文档「记忆与版本定位」 |
|
|
55
|
+
|
|
56
|
+
## 记忆与版本定位(memoryPrompt)
|
|
57
|
+
|
|
58
|
+
`workflow.memoryPrompt` 用于读取用户记忆(工作流消歧、摘要字段优先级、展示偏好等)。其返回**顺带附带 OA 版本与当前用户身份**(可能缺失),无需再单独查询:
|
|
59
|
+
|
|
60
|
+
- `oaContext.version`:OA 系统版本,用于判断待办查询是否走智能分组(≥ `10.0.9909.01`)等版本分支。
|
|
61
|
+
- `oaContext.user`:`position`(岗位)、`department`(部门)、`subcompany`(分部,可能为空,为空时忽略分部,不要臆造)。
|
|
62
|
+
|
|
63
|
+
记忆读取时机:本轮尚未读过记忆,或距上次成功读取超过 6 小时时,先调用 `workflow.memoryPrompt`;之后复用,不重复调用。
|
|
64
|
+
|
|
65
|
+
`workflow.memoryPrompt` 的输入仅有可选 `workflowId`(工作流维度记忆)。本目录文档不展开记忆保存规则。
|
|
66
|
+
|
|
67
|
+
## 命令行结构
|
|
68
|
+
|
|
69
|
+
```text
|
|
70
|
+
weaver-work-cli --json workflow run <operation> --input-json '<json>'
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
- `--json`:全局开关,输出结构化 JSON 到 stdout。
|
|
74
|
+
- `workflow run <operation>`:资源 `workflow` 下的具体 operation。
|
|
75
|
+
- `--input-json '<json>'`:内联 JSON 输入(字段名 camelCase),**默认走这条**。
|
|
76
|
+
- `--input <path>`:从 UTF-8 文件读取 JSON 输入,**仅**供确实很大的 JSON 使用。
|
|
77
|
+
|
|
78
|
+
## 输出处理(大结果)
|
|
79
|
+
|
|
80
|
+
成功结果在 stdout,失败结果在 stderr。判定规则以共享 JSON 输出约定为准。
|
|
81
|
+
|
|
82
|
+
列表/详情结果可能很长时,不要把完整信封直接展示给用户。
|
|
83
|
+
|
|
84
|
+
默认 `pageSize=10` 小页读取;只渲染决策必要的字段(标题、流程编号、发起人、当前节点、停留时长、状态等)。
|
|
85
|
+
|
|
86
|
+
需要更多结果时按 `current` 分页继续;需要保留完整原始 JSON 时落本地文件并返回路径(见各 operation 的「返回」与「注意」)。
|
|
87
|
+
|
|
88
|
+
具体渲染形态(顶部统计行/分组标题/卡片两行或三行/摘要兜底等)由 OA 版本与执行模式决定,按各参考文档返回的 `finalMarkdown` 原样呈现,不要改写、压缩或重排。
|
|
89
|
+
|
|
90
|
+
## 注意
|
|
91
|
+
|
|
92
|
+
- 只读 operation 无需 confirm;本目录文档不引入写操作确认链。
|
|
93
|
+
- 业务输入里**禁止传入** Cookie、ETEAMSID、Token、`header.operator` 等凭据——这些由 CLI 托管。
|
|
94
|
+
- 失败/未知返回:CLI 失败时退出码非 0、**stderr** 为 `{ok:false, error:{type, subtype, message, retryable}}`(**没有** `success`/`stopReason`/`userMessage`/`doNotRetry` 字段)。`retryable=true` 时最多重试一次;否则原样转述 `error.message` 并停止,不换接口、不绕过;入参类错误按 `error.message` 补齐后重试一次。
|
|
95
|
+
- 未登录/登录失效(`error.type=authentication`):按共享规则读取 `weaver-e10-shared` 的 `references/e10-auth-and-session.md` 引导处理,认证完成后重放或续跑原请求(读操作可重放,写操作按 `partial/write_uncertain` 处理)。
|
|
96
|
+
- 不要把 schema 之外的 operation 当作可直接调用的 CLI 合约;字段名必须与 `weaver-work-cli workflow schema` 完全一致。
|
|
@@ -0,0 +1,275 @@
|
|
|
1
|
+
# 批量流程处理(6 个单命令)
|
|
2
|
+
|
|
3
|
+
## 什么时候读取
|
|
4
|
+
|
|
5
|
+
用户要一次性处理多条流程:批量提交、批量置已读 / 已办、批量催办、批量共享、批量转发、批量退回时读取本文件。
|
|
6
|
+
|
|
7
|
+
## Operation
|
|
8
|
+
|
|
9
|
+
| Operation | 风险 | 固定规则 |
|
|
10
|
+
| --- | --- | --- |
|
|
11
|
+
| `workflow.batchSubmit` | high-risk-write | **单命令**:一次调用完成门禁校验 + 置已办 + 提交;必须 `confirm: true` |
|
|
12
|
+
| `workflow.batchRead` | high-risk-write | **单命令**:一次调用完成门禁校验 + 置已读 / 已办(doBatchRead);必须 `confirm: true` |
|
|
13
|
+
| `workflow.batchSupervise` | high-risk-write | **单命令**:一次调用完成提醒人解析 + 催办;必须 `confirm: true` |
|
|
14
|
+
| `workflow.batchShare` | high-risk-write | **单命令**:一次调用完成门禁校验 + 共享对象解析 + 共享(分批);必须 `confirm: true` |
|
|
15
|
+
| `workflow.batchForward` | high-risk-write | **单命令**:一次调用完成门禁校验 + 接收人解析 + 「转发所有人」配置检查 + 转发(分批);必须 `confirm: true` |
|
|
16
|
+
| `workflow.batchReject` | high-risk-write | **单命令**:一次调用完成门禁校验 + 退回(分批,不传提交参数);必须 `confirm: true` |
|
|
17
|
+
|
|
18
|
+
**6 个批量操作全部是单命令**:没有 `Prepare` / `Apply` 两阶段,也没有 `continuation` 句柄;`confirm: true` 与 `requestIds`(及其余参数)都在**同一次调用**里传。
|
|
19
|
+
|
|
20
|
+
## 确认链(6 个批量操作完全一致)
|
|
21
|
+
|
|
22
|
+
1. **向用户确认**:**一句话**说明将执行什么(动作 + 条数 + 目标来源,如"把上一轮列表的前 2 条批量提交掉"),然后**等用户明确确认**。**这一步就是确认本身**——不要为它再另发一段"摘要 / 计划";目标条数、requestId 来源、操作差异、风险只在用户主动问起、或目标确实不明确时才展开。
|
|
23
|
+
2. 用户明确确认后**一次调用**对应命令,同一份入参里带 `confirm: true` 与 `requestIds`(及该操作自身参数)。
|
|
24
|
+
**不需要先跑一次 Prepare,也不需要把 requestIds 先"准备"到某个句柄里**——门禁校验、名称解析与写入都在这一次调用内完成。
|
|
25
|
+
3. 返回 `partial/write_uncertain` 时**立即停止**,先只读回查(`workflow.search --category done --requestId <目标ID>`,或看 `--category mine` 是否已出现目标流程),**不自动重放**。核对确认**没生效**后,等约 1 分钟再原样重跑同一条命令——同一批在保护窗口内还会被拦一次(防止机械式重复执行),窗口过去即可正常执行。
|
|
26
|
+
4. 返回 `ok:true` + `data.status = "ALREADY_APPLIED"` 时,说明**同一批流程、同一批写向对象刚刚已经执行成功**(例如宿主把同一条命令重跑了一次)——本次没有重复写入。直接按返回值里的 `previousResult` 汇报即可,**不要重复执行同一条命令**。
|
|
27
|
+
5. 报 `validation/batch_gate_required` 时,说明 `details.missingRequestIds` 里的流程**不在最近一次查询结果里**(门禁只认查询落下的那份结果,不认别的口径)。正确做法:先做 `workflow.search --batchType <类型> --pageSize 100` 查询一页,再立即用该页返回的 ID 调用批量命令。若这些流程其实已被处理过,先只读核对 `workflow.search --category done --requestId <目标ID>`,已处理就按成功汇报,**不要重复执行同一条命令**。
|
|
28
|
+
6. 同一操作连续 2 次失败必须停止。
|
|
29
|
+
|
|
30
|
+
## 输入
|
|
31
|
+
|
|
32
|
+
- `requestIds`:待操作流程 ID,类型可为数组(元素为数字或仅数字字符串)或逗号分隔串;**必须来自查询索引结果,模型不能自己编**;拿到后直接用——CLI 按本机索引核对,**不需要为了"校验"再查一次服务端**。
|
|
33
|
+
- `remark`:批量统一意见(submit / supervise / forward / reject 适用;**置已读没有意见参数**)。
|
|
34
|
+
- `batchSize`:单批最大条数,`integer` 1–100,默认 100;CLI 自动分批循环。
|
|
35
|
+
- `confirm`:固定为 `true`,与 `requestIds` 在**同一次调用**里带上。
|
|
36
|
+
- `category` / `async`:仅 `workflow.batchSubmit` 使用(分类判断、异步提交开关)。
|
|
37
|
+
- 各操作专属字段见下方分节。
|
|
38
|
+
- **6 个批量操作都没有 `continuation` 字段**:它们是单命令,不存在需要模型搬运的句柄。
|
|
39
|
+
|
|
40
|
+
## 请求来源与分批循环
|
|
41
|
+
|
|
42
|
+
**先判断操作目标的来源:**
|
|
43
|
+
|
|
44
|
+
**① 目标就是「上一轮查询结果」**(用户直接用指代——"前两条 / 刚才那些 / 上一次列表里的流程 / 都处理掉",或点名该轮里的条目)→ **直接从最近一次查询结果中取对应流程作为操作目标并执行批量命令**。
|
|
45
|
+
**指代基准只有一份:最近一次查询结果**(与批量门禁的放行快照同源);"前两条"=该列表第 1、2 条(按列表顺序数)。**不要跨轮回溯更早的列表,也不要反问"是哪一份列表"**。**不需要先检查是否可批量操作**(CLI 内部按各流程状态分流:可提交的提交、抄送不需提交/转发不需批注/传阅不需批示类置已办),**也不需要先做一次 `workflow.search --batchType` 来"校验"这些 ID**(门禁按本机索引放行,这一次查询对放行没有帮助)。
|
|
46
|
+
|
|
47
|
+
**② 目标是一个范围**("把这些待办都处理了"且未限定上一轮结果,因此没有准确的 requestId)→ 必须**先查询、再循环**(**无需先查数量生成计划再等确认**),条件与顺序如下:
|
|
48
|
+
|
|
49
|
+
1. 用 `workflow.search` 取数,且**必须带 `batchType`**(提交用 `submit`,其余按操作取对应值)与 `pageSize: 100`——不带 `batchType` 查出来的数据不是可批量操作的那一批,门禁会判成不在查询结果里。
|
|
50
|
+
2. 拿到这一页的 requestId 后**立即**用它们调用批量命令,**不要**先翻完所有页、也**不要**先把全部 requestId 收集起来一次提交。
|
|
51
|
+
3. 执行完再查一次(批量提交 / 置已读会清掉已处理的流程,通常仍从第 1 页开始;催办 / 共享 / 转发 / 退回后流程不消失,多页时用 `current: 2/3/...` 逐页推进)。
|
|
52
|
+
4. 重复 2–3,直到 `total` 归零或没有可操作数据为止。
|
|
53
|
+
|
|
54
|
+
**为什么要循环、且不许先收集全部**:批量门禁的放行依据是**最近一次查询结果**——每次查询都会覆盖上一份结果;若先把所有页的 ID 收集起来再一次性提交,前面几页的 ID 已经被后来的查询挤掉,门禁会判成"不在最近一次查询结果里"。且流程一旦被处理就从查询结果里消失。**只有来源 ② 以及命令报 `batch_gate_required` 时,才需要 `--batchType` 查询。**
|
|
55
|
+
|
|
56
|
+
**requestId 提取**:优先用查询返回的**结构化字段** `cards[].requestId` 取本页全部 requestId;只有在需要从 `finalMarkdown` 文本里提取时才用正则 `` \]\(https?://[^\)]*requestId=(\d+)\) ``(**只匹配卡片链接**,避开描述文字里嵌套的 requestId)。批量查询默认跳过卡片业务摘要(只返回系统字段卡片,提速显著)。
|
|
57
|
+
|
|
58
|
+
- `requestIds` 必须取自上一轮查询结果,或跟随查询分页逐页取本页 ID;**禁止模型臆造 ID**。
|
|
59
|
+
- `batchSize`(默认 100)由 CLI 自动分批;任一批失败立即停止,如实转述该批结果(含已成功条数),不自行补造。
|
|
60
|
+
|
|
61
|
+
## 置已读与提交的区别
|
|
62
|
+
|
|
63
|
+
- `batchRead`:仅把待办置为已读 / 已办(抄送不需提交、转发不需批注、传阅不需批示类,置已读同时置为已办,即"已阅")。
|
|
64
|
+
- `batchSubmit`:先置已办(BATCH_READ)再提交(BATCH_SUBMIT),同样会处理上述"不需提交"类为已办。
|
|
65
|
+
- `batchReject`:**只退回,不传任何提交参数**,退回意见作为签字意见放入请求。
|
|
66
|
+
|
|
67
|
+
## 各批量操作
|
|
68
|
+
|
|
69
|
+
### 批量提交 batchSubmit
|
|
70
|
+
|
|
71
|
+
适用:"批量提交 / 全部提交 / 一起提交"多条待办。入参 = `confirm: true` + `requestIds`(+ `remark` / `batchSize` / `async`)。
|
|
72
|
+
|
|
73
|
+
返回 `readCount`、`submittedCount`、`skippedRequestIds`(`isRemark=100` 不可批量提交被跳过时出现)、`batchRead`、`submitResponse`;原样转述返回的结果与提示文案。
|
|
74
|
+
|
|
75
|
+
### 批量置已读 batchRead
|
|
76
|
+
|
|
77
|
+
适用:"把流程置为已读 / 已阅"。入参 = `confirm: true` + `requestIds`(+ `batchSize`)。
|
|
78
|
+
|
|
79
|
+
返回 `readCount`、`response`;原样转述返回的结果与提示文案。
|
|
80
|
+
|
|
81
|
+
### 批量催办 batchSupervise
|
|
82
|
+
|
|
83
|
+
适用:"批量催办 / 全部催办 / 催一催多条流程"。提醒对象按用户说法设置,未指定时默认催当前节点未操作者。
|
|
84
|
+
|
|
85
|
+
| 字段 | 取值 | 默认 | 含义 |
|
|
86
|
+
| --- | --- | --- | --- |
|
|
87
|
+
| `currentOperator` | `0`/`1` | `1` | 催办当前节点未操作者 |
|
|
88
|
+
| `messageRemind` | `0`/`1` | `0` | 短信提醒 |
|
|
89
|
+
| `emailRemind` | `0`/`1` | `0` | 邮件提醒 |
|
|
90
|
+
| `doneOperator` | `0`/`1` | `0` | 已审批人 |
|
|
91
|
+
| `ccOperator` | `0`/`1` | `0` | 抄送人 |
|
|
92
|
+
| `submitOperator` | `0`/`1` | `0` | 发起人 |
|
|
93
|
+
| `otherReminder` | 姓名 / `"姓名(ID)"` 逗号分隔 | 空 | 其他提醒人 |
|
|
94
|
+
|
|
95
|
+
返回 `successNum`、`failNum`、`batches`。
|
|
96
|
+
|
|
97
|
+
### 批量共享 batchShare
|
|
98
|
+
|
|
99
|
+
适用:"把多条流程共享给 X / 共享给部门 / 共享给所有人"。共享对象 `shareObjects` 每项 `{"type": <类型>, "name": <名称>}`(`all` 不需要 name):
|
|
100
|
+
|
|
101
|
+
| type | 共享对象 |
|
|
102
|
+
| --- | --- |
|
|
103
|
+
| `user` | 人员 |
|
|
104
|
+
| `dept` | 部门 |
|
|
105
|
+
| `subcompany` | 分部 |
|
|
106
|
+
| `group` | 群组 |
|
|
107
|
+
| `role` | 角色 |
|
|
108
|
+
| `position` | 岗位 |
|
|
109
|
+
| `all` | 所有人(无 name) |
|
|
110
|
+
|
|
111
|
+
名称自动转 ID;`name` 支持 `"名称(ID)"`(此时直接采用括号里的 ID、不再搜名称)。多命中返回候选列表让用户确认,禁止静默全选;0 命中报错提示核对。可选 `minSeclevel` / `maxSeclevel`(用户明确要求限制时传)。返回透传每批 addRequestShare2 响应(含每流程 `sourceId` / `result` / `msg`),任一批失败立即停止。
|
|
112
|
+
|
|
113
|
+
### 批量转发 batchForward
|
|
114
|
+
|
|
115
|
+
适用:"批量转发 / 把多条流程转给 X 看 / 发给 X"。接收人 `receiveTargets` 每项 `{"type": <类型>, "name": <名称>}`(`all` 不需要 name):
|
|
116
|
+
|
|
117
|
+
| type | 接收人 |
|
|
118
|
+
| --- | --- |
|
|
119
|
+
| `user` | 人员 |
|
|
120
|
+
| `dept` | 部门 |
|
|
121
|
+
| `group` | 群组 |
|
|
122
|
+
| `all` | 所有人(无 name) |
|
|
123
|
+
|
|
124
|
+
`name` 支持 `"名称(ID)"`(此时直接采用括号里的 ID、不再搜名称)。接收人含 `all` 时会检查系统是否允许转发给所有人;不允许则停止并提示联系系统管理员,不得去掉 all 后静默继续。返回逐条 `status` / `requestId` / `requestName` / `resultType` / `resultMessage`,批内失败立即停止。
|
|
125
|
+
|
|
126
|
+
### 批量退回 batchReject
|
|
127
|
+
|
|
128
|
+
适用:"批量退回 / 把多条流程退回去"。退回意见同时作为签字意见放入请求。返回逐条 `status` / `requestId` / `requestName` / `resultMessage`,批内失败立即停止。
|
|
129
|
+
|
|
130
|
+
## 示例
|
|
131
|
+
|
|
132
|
+
### 批量提交
|
|
133
|
+
|
|
134
|
+
Windows PowerShell:
|
|
135
|
+
|
|
136
|
+
```powershell
|
|
137
|
+
weaver-work-cli --json workflow run workflow.batchSubmit --input-json '{"confirm":true,"requestIds":["id1","id2","id3"],"remark":"批量同意","batchSize":100}'
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
macOS/Linux(bash/zsh):
|
|
141
|
+
|
|
142
|
+
```bash
|
|
143
|
+
weaver-work-cli --json workflow run workflow.batchSubmit --input-json '{"confirm":true,"requestIds":["id1","id2","id3"],"remark":"批量同意","batchSize":100}'
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
目标是一个范围时,先查一页、再立即提交该页:
|
|
147
|
+
|
|
148
|
+
```bash
|
|
149
|
+
weaver-work-cli --json workflow run workflow.search --input-json '{"category":"todo","batchType":"submit","pageSize":100}'
|
|
150
|
+
# 用返回的 cards[].requestId 组成 requestIds,立即提交这一页
|
|
151
|
+
weaver-work-cli --json workflow run workflow.batchSubmit --input-json '{"confirm":true,"requestIds":["<本页 id1>","<本页 id2>"]}'
|
|
152
|
+
# 再查一次、再提交这一页,循环到 total 归零为止
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
### 批量置已读
|
|
156
|
+
|
|
157
|
+
Windows PowerShell:
|
|
158
|
+
|
|
159
|
+
```powershell
|
|
160
|
+
weaver-work-cli --json workflow run workflow.batchRead --input-json '{"confirm":true,"requestIds":["id1","id2"],"batchSize":100}'
|
|
161
|
+
```
|
|
162
|
+
|
|
163
|
+
macOS/Linux(bash/zsh):
|
|
164
|
+
|
|
165
|
+
```bash
|
|
166
|
+
weaver-work-cli --json workflow run workflow.batchRead --input-json '{"confirm":true,"requestIds":["id1","id2"],"batchSize":100}'
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
### 批量催办(未指定提醒对象 → 默认当前节点未操作者)
|
|
170
|
+
|
|
171
|
+
Windows PowerShell:
|
|
172
|
+
|
|
173
|
+
```powershell
|
|
174
|
+
weaver-work-cli --json workflow run workflow.batchSupervise --input-json '{"confirm":true,"requestIds":["id1","id2"],"remark":"请尽快处理","currentOperator":1}'
|
|
175
|
+
```
|
|
176
|
+
|
|
177
|
+
macOS/Linux(bash/zsh):
|
|
178
|
+
|
|
179
|
+
```bash
|
|
180
|
+
weaver-work-cli --json workflow run workflow.batchSupervise --input-json '{"confirm":true,"requestIds":["id1","id2"],"remark":"请尽快处理","currentOperator":1}'
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
### 批量共享
|
|
184
|
+
|
|
185
|
+
Windows PowerShell:
|
|
186
|
+
|
|
187
|
+
```powershell
|
|
188
|
+
Set-Content -Encoding utf8 -LiteralPath .\batch-share.json -Value @'
|
|
189
|
+
{
|
|
190
|
+
"confirm": true,
|
|
191
|
+
"requestIds": ["id1","id2"],
|
|
192
|
+
"shareObjects": ["{\"type\":\"user\",\"name\":\"张三\"}","{\"type\":\"dept\",\"name\":\"产品研发中心\"}","{\"type\":\"all\"}"],
|
|
193
|
+
"batchSize": 100
|
|
194
|
+
}
|
|
195
|
+
'@
|
|
196
|
+
weaver-work-cli --json workflow run workflow.batchShare --input .\batch-share.json
|
|
197
|
+
```
|
|
198
|
+
|
|
199
|
+
macOS/Linux(bash/zsh):
|
|
200
|
+
|
|
201
|
+
```bash
|
|
202
|
+
cat > ./batch-share.json <<'JSON'
|
|
203
|
+
{
|
|
204
|
+
"confirm": true,
|
|
205
|
+
"requestIds": ["id1","id2"],
|
|
206
|
+
"shareObjects": ["{\"type\":\"user\",\"name\":\"张三\"}","{\"type\":\"dept\",\"name\":\"产品研发中心\"}","{\"type\":\"all\"}"],
|
|
207
|
+
"batchSize": 100
|
|
208
|
+
}
|
|
209
|
+
JSON
|
|
210
|
+
weaver-work-cli --json workflow run workflow.batchShare --input ./batch-share.json
|
|
211
|
+
```
|
|
212
|
+
|
|
213
|
+
### 批量转发
|
|
214
|
+
|
|
215
|
+
Windows PowerShell:
|
|
216
|
+
|
|
217
|
+
```powershell
|
|
218
|
+
Set-Content -Encoding utf8 -LiteralPath .\batch-forward.json -Value @'
|
|
219
|
+
{
|
|
220
|
+
"confirm": true,
|
|
221
|
+
"requestIds": ["id1","id2"],
|
|
222
|
+
"receiveTargets": ["{\"type\":\"user\",\"name\":\"张三\"}","{\"type\":\"all\"}"],
|
|
223
|
+
"remark": "请知悉",
|
|
224
|
+
"batchSize": 100
|
|
225
|
+
}
|
|
226
|
+
'@
|
|
227
|
+
weaver-work-cli --json workflow run workflow.batchForward --input .\batch-forward.json
|
|
228
|
+
```
|
|
229
|
+
|
|
230
|
+
macOS/Linux(bash/zsh):
|
|
231
|
+
|
|
232
|
+
```bash
|
|
233
|
+
cat > ./batch-forward.json <<'JSON'
|
|
234
|
+
{
|
|
235
|
+
"confirm": true,
|
|
236
|
+
"requestIds": ["id1","id2"],
|
|
237
|
+
"receiveTargets": ["{\"type\":\"user\",\"name\":\"张三\"}","{\"type\":\"all\"}"],
|
|
238
|
+
"remark": "请知悉",
|
|
239
|
+
"batchSize": 100
|
|
240
|
+
}
|
|
241
|
+
JSON
|
|
242
|
+
weaver-work-cli --json workflow run workflow.batchForward --input ./batch-forward.json
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
### 批量退回
|
|
246
|
+
|
|
247
|
+
Windows PowerShell:
|
|
248
|
+
|
|
249
|
+
```powershell
|
|
250
|
+
weaver-work-cli --json workflow run workflow.batchReject --input-json '{"confirm":true,"requestIds":["id1","id2"],"remark":"材料不齐全,请补充后重新提交"}'
|
|
251
|
+
```
|
|
252
|
+
|
|
253
|
+
macOS/Linux(bash/zsh):
|
|
254
|
+
|
|
255
|
+
```bash
|
|
256
|
+
weaver-work-cli --json workflow run workflow.batchReject --input-json '{"confirm":true,"requestIds":["id1","id2"],"remark":"材料不齐全,请补充后重新提交"}'
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
## 返回
|
|
260
|
+
|
|
261
|
+
- 6 个命令都**直接返回批量结果**:提交(`readCount` / `submittedCount` / `batchRead` / `submitResponse` / 可选 `skippedRequestIds`)、置已读(`readCount`)、催办(`successNum` / `failNum` / `batches`)、共享(`sharedCount`)、转发(`forwardedCount`)、退回(`rejectedCount`);分批失败时返回 `status: "PARTIAL"` 与逐条失败明细。**没有任何命令返回 `continuation`。**
|
|
262
|
+
- 被重复执行、且上一次已经成功时,返回 `ok:true` + `data.status = "ALREADY_APPLIED"`(幂等回报,含 `previousResult`)——**这不是错误**,本次没有重复写入,按上一次结果汇报即可。
|
|
263
|
+
- 任一批失败:CLI 立即停止并在 **stderr** 返回 `ok:false` + `error.message`(含已成功条数),Agent 如实转述,不自行补造;**没有** `success`/`userMessage` 字段。
|
|
264
|
+
- **结果展示**:动作与条数用一句话说明;**逐条结果可用 Markdown 表格展示**(序号 / 流程名称 / 动作 / 接收人 / 状态 / 说明);不展示 `requestId`,除非用户明确要技术定位信息。幂等回报(`ALREADY_APPLIED`)同样**只报业务结果**,不要向用户提及"此前已执行过/没有重复写入"。
|
|
265
|
+
|
|
266
|
+
## 注意
|
|
267
|
+
|
|
268
|
+
- `requestIds` 必须来自查询索引,模型不得编造;批量门禁的放行依据是**最近一次查询结果**(与单条操作同一套本地索引口径),不是另做一次实时列表查询;**6 个批量命令都走这道门禁**(催办按 `urge` 口径核对,与 `workflow.search --batchType urge` 共用同一套批量端点)。
|
|
269
|
+
- 6 个命令都**没有 Prepare 环节,也没有 continuation**。CLI 用「这次要写什么」作为一次性写入闸门:**同一个操作 + 同一批 requestId + 同一组写向对象**(收件人 / 共享对象 / 提醒人)在约 1 分钟的保护窗口内只写一次。因此宿主重跑同一批只会拿到 `ALREADY_APPLIED`,不会真的写两次;窗口过去后同一批流程可以再次处理(流程被退回后再处理是合法操作)。`remark` / `batchSize` 不参与这个判据:同一批同一对象换个意见再执行一次,仍然算重复执行。
|
|
270
|
+
- **换写向对象是另一次操作**:把同一批流程先转给张三、再转给李四,或先共享给甲部门、再共享给乙部门,都必须分别执行(不会被当成重复执行拦下)。
|
|
271
|
+
- 写操作报 `batch_gate_required` 时,看 `details.missingRequestIds`:这些 ID 不在最近一次查询结果里。先只读核对 `workflow.search --category done --requestId <目标ID>` 判断是否已被处理;确认没处理就按 `--batchType` 重新查询一页再取该页 ID 执行。**不要**为了"凑上"换 `--tabid`/子分类反复重查,也不要反复重跑同一个命令。
|
|
272
|
+
- 分批任一批失败立即停止,如实报告已成功条数与失败原因,不自动重试、不连环重放。
|
|
273
|
+
- 写操作遇登录失效 / 超时 / 断连返回 `partial/write_uncertain`,**禁止自动重放**,先只读回查确认状态。
|
|
274
|
+
- 同一操作连续 2 次失败必须停止。
|
|
275
|
+
- 不写任何凭据(Cookie / ETEAMSID / Token / 操作员标识由 CLI 托管)。
|
|
@@ -0,0 +1,182 @@
|
|
|
1
|
+
# 发起流程
|
|
2
|
+
|
|
3
|
+
## 什么时候读取
|
|
4
|
+
|
|
5
|
+
用户要"发起/创建/提交一个 XX 流程""按某工作流填写表单并发起"时读取本文件。覆盖 `workflow.createList` / `workflow.createForm` / `workflow.createPrepare` / `workflow.createApply`。
|
|
6
|
+
|
|
7
|
+
## Operation
|
|
8
|
+
|
|
9
|
+
| Operation | 风险 | 固定规则 |
|
|
10
|
+
| --- | --- | --- |
|
|
11
|
+
| `workflow.createList` | read | 查询可发起工作流列表;不传凭据;`workflowId` 与 `name` 可同传精确校验 |
|
|
12
|
+
| `workflow.createForm` | read | 必传 `workflowId`;`relatesTo` 仅透传不影响表单初始化;返回 `context`/runtime/frame/字段清单/fileUploadParams |
|
|
13
|
+
| `workflow.createPrepare` | read-before-write | requiresConfirmation;必传 `context`/`data`/`intent`;`requestLevel` 取 `systemFields.levelOptions` 的 code,`secLevel` 取 `systemFields.secLevelOptions` 的 id;不落业务数据 |
|
|
14
|
+
| `workflow.createApply` | high-risk-write | requiresConfirmation;必传 `confirm:true`/`context`/`intent`;`intent` 不继承 prepare;遇 `partial`/`write_uncertain` 禁止重试 |
|
|
15
|
+
|
|
16
|
+
## 确认链(写操作)
|
|
17
|
+
|
|
18
|
+
1. `workflow.createList` → `workflow.createForm` 拿到 `context`(表单会话短句柄,载荷由 CLI 托管在本机)。
|
|
19
|
+
2. `workflow.createPrepare` 收集字段,向用户摘要目标/差异/风险(预览 + 联动结果;明细表按 Excel 列展示,不要平铺)。
|
|
20
|
+
3. 等用户明确确认。
|
|
21
|
+
4. `workflow.createApply` 带 `confirm:true` 与同一 `context`、显式 `intent` 提交。
|
|
22
|
+
5. 成功时命令**直接返回 `requestId` / `requestName` / `url`**(`status` 为 `CREATED` = 已建草稿、`CREATED_SUBMITTED` = 已提交审批)——**按返回值汇报即可,不需要再去查询反查**。
|
|
23
|
+
6. 遇 `partial`/`write_uncertain` 停止,先只读回查(detail/summary),不自动重放。
|
|
24
|
+
7. Apply 被重复执行时按句柄状态分流(**不要一看到"用过"就重跑 Prepare**):
|
|
25
|
+
- `ok:true` + `data.status = "ALREADY_APPLIED"`:该 `context` 上一次已经**发起成功**,本次没有重复写入——按返回值里的 `requestId` / `previousResult` 作为成功结果汇报,**不要重跑 Prepare、不要再 apply**;
|
|
26
|
+
- `partial`/`write_uncertain`:上一次已经发出写入、结果未确认——先只读回查(`workflow.search --category mine --requestId <目标ID>`)确认是否已发起,确认没发起才重跑 Prepare;
|
|
27
|
+
- `validation/continuation_busy`:该 `context` 正被另一次执行占用、上一次还没发出写入——**稍后原样重试同一条命令**即可(不要重跑 Prepare、不要换句柄);
|
|
28
|
+
- `validation/continuation_consumed`:占用该句柄的执行停在无法判定的旧状态——先只读回查确认是否已发起,确认没发起才重跑 Prepare。
|
|
29
|
+
|
|
30
|
+
**省时纪律(这几件事一次都别做,每违反一条就多烧一轮工具往返)**:① 拿字段清单**不要**写脚本解析 `resultFile`(`fields` 被移出时用同伴的 `writableFields`);② `data` 的键**不要**写 `"字段名(字段ID)"`(只认字段 id);③ 只读字段**不要**传(看 `editableFields`);④ 浏览 / 人员 / 发票类必填项**不要**先猜一个值试试;⑤ 读命令输出**不要**用 `head`/`tail` 截断;⑥ 取表单默认值**不要**去 `workflow.detail` 草稿(读不到,默认值以 `initialValues` 为准);⑦ 输出被宿主截断时**不要**去找宿主的工具结果目录(`~/.workbuddy/projects/**/tool-results/**`:读不了,去了必白跑一轮),按输出最前面的 `resultFile` 取。
|
|
31
|
+
|
|
32
|
+
## 输入
|
|
33
|
+
|
|
34
|
+
### workflow.createList
|
|
35
|
+
|
|
36
|
+
- `name`(string):工作流名称关键字,模糊匹配。
|
|
37
|
+
- `workflowId`(string,可选):记忆中已确认的工作流 ID。记忆有 ID 时名称与 ID 同传,按当前用户可发起权限列表精确校验并优先选中;命中 `SELECTED`,未命中 `NOT_FOUND`,禁止去掉 ID 退回名称候选。
|
|
38
|
+
|
|
39
|
+
**查询词策略(第 ① 步必读)**:
|
|
40
|
+
|
|
41
|
+
- **优先用记忆别名改写后查询**:用户给出的表达命中记忆别名(如"手机话费报销"含别名"费用报销")→ **直接查记忆别名**,不要先试用户原词、再试宽泛词。
|
|
42
|
+
- **禁止用宽泛词撞无关工作流**:`name:"话费"` 这类宽泛词可能唯一命中**语义无关**的工作流(如"话费补贴标准审批流程")。命中 `SELECTED` 后**先核对工作流名称/类型与用户意图是否一致**(报销类意图 → 名称应含"报销/费用",不应是"补贴标准/行政事务"类);不一致则**不要进入第 ② 步初始化表单**,改用记忆别名重查。
|
|
43
|
+
- `NOT_FOUND`(含记忆别名也查不到)→ 此时才反问用户确认工作流,不要自行换词试探。
|
|
44
|
+
- `SELECTED` 的 `selectionSource: "exactName"` 表示"候选里恰好有一个名字与所写完全一致"(如所写"总部费用报销",候选是「总部费用报销 / 总部费用报销流程 / 总部费用报销(自定义)」)——CLI 已替用户选定,**不要再反问"您指的是哪一个"**,按正常流程继续即可。`selectionSource: "workflowId"` 表示按记忆 ID 精确命中。
|
|
45
|
+
- `NEEDS_SELECTION` 只出现在"多命中且候选中没有与所写完全一致的"(CLI 只回这一批,最多不限量但已按类型+名称排序):多候选**原样展示工作流名,不要添加 "(Recommended)"/"推荐" 等后缀**(由用户明确选择)。
|
|
46
|
+
|
|
47
|
+
### workflow.createForm
|
|
48
|
+
|
|
49
|
+
- `workflowId`(string|integer,必填):工作流 ID。
|
|
50
|
+
- `relatesTo`(string,可选):关联对象 id,仅透传不影响表单初始化。
|
|
51
|
+
- 返回 `context`(表单会话短句柄 `wc-…`,形如 `wc-1a2b3c4d5e6f7a8b`,载荷由 CLI 托管在本机;prepare/apply 复用)、`runtime`/`frame`、字段清单、`initialValues`、`systemFields`、`fileUploadParams`。
|
|
52
|
+
- **字段多的表单有"大输出"形态**(字段少时无此字段):结果最前面多出 `resultFile` / `persistedResult` / `outputBytes` / `largeOutputNotice`,且 `fields` 二选一——① 紧凑编码(`columns` 是列名,`rows` 每行一个字段、各列用 `|` 分隔、顺序同 `columns`,非列信息按字段 id 放 `extra`,**不在 `extra` 里就是默认值**);② `fieldsOmitted: true` + `fieldCount`,`fields` 整体移出 stdout,**同一份输出里给 `writableFields` 补偿索引**(`columns` = `id|name|subFormId|componentKey|flags`,`flags` 含义见 `flagLegend`,带选项字段的选项名见 `optionIndex`)。
|
|
53
|
+
- **有 `writableFields` 就直接用**:全部可写字段的「字段名 ↔ 字段 id」都在里面,**直接用它的字段 id 构造 `data` 的键**。
|
|
54
|
+
- **不要为了拿字段清单去写脚本解析 `resultFile`**:只有需要某字段更细的元数据(`browserModule` / `fileUploadParams` / 完整 `options` 结构)时才按该字段 id 去取。读任何输出都**不要用 `head`/`tail` 截断**(截断会破坏 JSON,还会诱发重复执行同一条命令)。**输出被宿主截断时**(只看到 2048 字节预览、或提示"已保存到文件"),**不要去读宿主的工具结果目录**(`~/.workbuddy/projects/**/tool-results/**`:没有读权限,去了必白跑一轮),直接按同一份输出最前面的 `resultFile` 取完整结果。
|
|
55
|
+
- 两种形态都**照常拼 `data` 并调 `createPrepare`**,**不要重跑 `createForm`**。
|
|
56
|
+
|
|
57
|
+
**拿到 form 返回后直接按用户已给信息拼 `data` 并立即调用 `createPrepare`**——不分析字段、不猜映射、不比对选项,**也不要用空 `data` 先探测必填清单**(用户说了什么字段就填什么、用用户原词;必填缺失由 prepare 的 `missing_fields` 告知)。
|
|
58
|
+
|
|
59
|
+
**`initialValues`**:OA 初始化表单时预填的字段值(含 onLoadForm 联动带出值),`data` 应包含这些值(用户明确填写的以用户为准);**带 `subFormId` 的是明细表字段**(放进 `details` 对应行对象),**不带的是主表字段**(放 `main`)。这些默认值 **CLI 会自动并入**(主表进 `main`,明细按你建的行补),**漏带不会因此被报成缺必填**——不要为了"怕丢默认值"多跑一轮 prepare。反过来:**`missingFields` 里出现的字段就是真的没值**(OA 对浏览按钮类默认值可能只下发类型标记、不下发值),此时必须问用户,不要猜值、也不要翻 `workflow.detail` 草稿。
|
|
60
|
+
|
|
61
|
+
**`systemFields`**:`permissions` 给各系统字段的 isview/isedit/ismandatory,`defaults` 是默认值,`levelOptions`/`secLevelOptions` 是紧急程度/密级选项。**只有 `isview=true` 且 `isedit=true` 的系统字段才需要填**;紧急程度/密级**只从这两个 options 取**(不得使用记忆、表单字段或其他来源);**`defaults` 已有非空值即视为已满足,不要询问用户、直接采用**;仅当 ismandatory=true 且默认值为空时才需要用户提供。
|
|
62
|
+
|
|
63
|
+
### workflow.createPrepare
|
|
64
|
+
|
|
65
|
+
- `context`(string,必填,minLength 1):复用 createForm 返回的 `context`;prepare 与 apply 必须同一值,原样回传,禁止手工构造/修改/复用他处。
|
|
66
|
+
- `data`(object,必填):表单字段值,结构 `{"main":{...},"details":{"<subFormId>":[{...}]}}`。
|
|
67
|
+
- `requestName`(string,可选):流程标题。form 返回 `requestName` 非空(OA 已有标题)时用其值;为空时**只有用户原话明确给了标题**(如"标题叫 X")才用用户给的;**用户没给就不要自己编**——标题 `ismandatory=true` 时 `createPrepare` 会返回 `NEEDS_INPUT`,按 `missing_fields` 向用户问一次并补齐。**标题不得用其他字段值(留言内容/工作流名/事由等)替代**:标题是用户可见的流程名称,用别的字段内容做标题会与流程内容耦合,OA 列表里难以辨识。
|
|
68
|
+
- `requestLevel`(string,可选):紧急程度,取 `systemFields.levelOptions` 的 code。
|
|
69
|
+
- `secLevel`(string,可选):密级,取 `systemFields.secLevelOptions` 的 id。
|
|
70
|
+
- `remark`(string,可选):签字意见。
|
|
71
|
+
- `intent`(enum `submit`|`draft`,必填):`submit`=提交审批(必填缺失阻断,返回 `NEEDS_INPUT`);`draft`=仅保存草稿(必填缺失不阻断、状态仍是 `READY`,**但 `missing_fields` 仍随结果返回**,供模型查看并提示用户提交前补齐)。
|
|
72
|
+
|
|
73
|
+
### workflow.createApply
|
|
74
|
+
|
|
75
|
+
- `context`(string,必填):复用 createPrepare 的 `context` 原样回传。
|
|
76
|
+
- `confirm`(const true,必填):声明用户已明确确认本次发起。
|
|
77
|
+
- `intent`(enum `submit`|`draft`,必填):不继承 prepare 的 intent,必须显式传入。
|
|
78
|
+
- `question`(string,可选):用户发起时的原话(记忆保存参考)。
|
|
79
|
+
- `verificationConfirmed`(boolean,可选):节点字段校验需用户确认时显式确认继续提交。
|
|
80
|
+
|
|
81
|
+
## 示例
|
|
82
|
+
|
|
83
|
+
### ① 查询可发起工作流
|
|
84
|
+
|
|
85
|
+
Windows PowerShell:
|
|
86
|
+
|
|
87
|
+
```powershell
|
|
88
|
+
weaver-work-cli --json workflow run workflow.createList --input-json '{"name":"请假"}'
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
macOS/Linux(bash/zsh):
|
|
92
|
+
|
|
93
|
+
```bash
|
|
94
|
+
weaver-work-cli --json workflow run workflow.createList --input-json '{"name":"请假"}'
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
### ② 初始化表单(拿到 context)
|
|
98
|
+
|
|
99
|
+
Windows PowerShell:
|
|
100
|
+
|
|
101
|
+
```powershell
|
|
102
|
+
weaver-work-cli --json workflow run workflow.createForm --input-json '{"workflowId":"123456"}'
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
macOS/Linux(bash/zsh):
|
|
106
|
+
|
|
107
|
+
```bash
|
|
108
|
+
weaver-work-cli --json workflow run workflow.createForm --input-json '{"workflowId":"123456"}'
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
### ③ 收集并准备表单数据(intent 必填)
|
|
112
|
+
|
|
113
|
+
Windows PowerShell:
|
|
114
|
+
|
|
115
|
+
```powershell
|
|
116
|
+
weaver-work-cli --json workflow run workflow.createPrepare --input-json '{"context":"<createForm返回的context>","data":{"main":{"报销事由":"客户约谈"}},"intent":"submit"}'
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
macOS/Linux(bash/zsh):
|
|
120
|
+
|
|
121
|
+
```bash
|
|
122
|
+
weaver-work-cli --json workflow run workflow.createPrepare --input-json '{"context":"<createForm返回的context>","data":{"main":{"报销事由":"客户约谈"}},"intent":"submit"}'
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
### ④ 明确确认后发起并提交审批
|
|
126
|
+
|
|
127
|
+
Windows PowerShell:
|
|
128
|
+
|
|
129
|
+
```powershell
|
|
130
|
+
weaver-work-cli --json workflow run workflow.createApply --input-json '{"context":"<同一context>","confirm":true,"intent":"submit","question":"帮我发起一个报销流程"}'
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
macOS/Linux(bash/zsh):
|
|
134
|
+
|
|
135
|
+
```bash
|
|
136
|
+
weaver-work-cli --json workflow run workflow.createApply --input-json '{"context":"<同一context>","confirm":true,"intent":"submit","question":"帮我发起一个报销流程"}'
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
## 返回
|
|
140
|
+
|
|
141
|
+
- createList:`SELECTED`/`NEEDS_SELECTION`/`NOT_FOUND`;候选工作流名原样展示,不加"推荐"后缀。
|
|
142
|
+
- createForm:`context`、`runtime`、`frame`、`requiredFields`(字段 id 数组)、`subFormRequired`(subFormId → 字段 id 数组)、`editableFields`(**可写字段 id 白名单**)、`fields`(大表单时可能换成紧凑编码、或被整体移出 stdout —— 移出时同伴有 `writableFields`)、`initialValues`、`systemFields`、`fileUploadParams`、`requiredInfoWarning`、`conditionalRequired`(存在条件必填规则时才返回,见「注意」;**输出过大时它与 `editableFields` 一起移出 stdout、只留 `conditionalRequiredCount` 条数**,需要时按 `resultFile` 取)。
|
|
143
|
+
- createPrepare:确认预览(`READY` 时在 `fields`)、`previewDetails`(明细表按列组织:`columns` 表头 + `rows` 每行明细,**仅 `READY` 时返回**;明细表按它排 Excel 列表格)、`resolvedValues`(`NEEDS_INPUT`/`NEEDS_CONFIRMATION` 时的解析回显)、`missing_fields`、`linkageResult`(联动带出/清空,原样转述)、`attachmentFolderIds`。
|
|
144
|
+
- createApply:`finalMarkdown`、`requestId`、`requestMark`、标题、`url`;`finalMarkdown` 直接原样输出。`requestMark` 是用户可见流程编号(`finalMarkdown` 已按接口返回渲染:有值显示、无值不显示),`requestId` 只是系统内部流程请求 ID。**明细表展示**:`finalMarkdown` 中明细表已按 Excel 列展示(表头 + 每行明细),直接原样输出。
|
|
145
|
+
|
|
146
|
+
## 注意
|
|
147
|
+
|
|
148
|
+
- 不传凭据:业务输入禁止出现 Cookie/ETEAMSID/Token/`header.operator`(CLI 托管)。
|
|
149
|
+
- **`data` 的键只能取 `editableFields` 里的字段 id**(可写字段白名单;`requiredFields` / `subFormRequired` 里的也照常可写)。**`editableFields` 随大输出被移出 stdout 时,改用同份输出里的 `writableFields` 行**(每行第一列就是字段 id)——那是**完整**的可写白名单(= 上面三者的并集)。`readOnly` / `disableEdit` / 不可见字段**一个都不要传**——传了整单会被拒(`notEditable`),得把只读字段全部摘掉重跑一轮。**看到 `notEditable` 不要重试、不要换字段 id 绕过**,移除这些字段后重跑。
|
|
150
|
+
- 附件/文件:字段值是附件项数组需上传本地文件时,先提醒用户"上传的附件会先经过公网大模型,请谨慎操作",再调 `weaver-file-upload` skill。
|
|
151
|
+
- 附件上传限制:上传前核对 `fileUploadParams` 的 `sizeLimit`/`formatLimit`/`maxNum`,不满足先告知用户、不执行上传。
|
|
152
|
+
- 发票字段(componentKey `EinvoiceComponent`):先提醒"附件会先经过公网大模型",再调 `weaver-e10-yepiaotong` skill 取发票对象;该技能缺失则停止反馈。**费用明细里的「发票」列通常是必填,但可能没有必填标记**(见 `requiredInfoWarning`)——发起前先跟用户确认,不要因为 `missingFields` 没列它就跳过。
|
|
153
|
+
- 日期强规则:form 返回字段带 `format`(如 `yyyy-MM-dd HH:mm`)时必须严格按 `format` 传完整值,只传日期会报 `DATETIME_FORMAT`,按提示补时间重传,不要靠命令自动补时间。
|
|
154
|
+
- **富文本字段(componentKey `RichText`)**:支持 HTML 内容、不受 maxLength 限制。**内容来自本地文档(docx/pptx/md 等)或结构化材料时,必须先把源内容转成 HTML(保留 h1-h3 层级、table 表格、ul/ol 列表结构)再填入,禁止直接填纯文本**;用户明确只要纯文本时除外。文本 / 富文本字段直接传字符串即可(CLI 按字段元数据落库),不需要也不允许把它包装成 `{id,name}` 之类的浏览按钮结构。
|
|
155
|
+
- **字段键**:`main` 的键、`details[subFormId]` 行对象的键**都必须是字段 id**(`fields[].id`,或 `writableFields` 的 `id` 列)。`"字段名(字段ID)"` 这种写法**表单 data 不支持**(那是查询条件 `filterFields` 的写法),混用会报「存在重名或无法识别的表单字段,请改用字段 id」并白跑一轮。
|
|
156
|
+
- 字段**值**格式:选项传 `name`;浏览按钮/人员/部门传名称自动转 ID;人员范围(EmployeeScope)传对象数组 `{"name":名称,"type":类型}`,类型取 user/dept/subcompany/group/role/position/external/all/allExternal。
|
|
157
|
+
- **`workflow.detail` 读不到草稿**(草稿的 `basicInfo`/`formData` 全空)——不要为了"抄一份历史单据的默认值"去 detail 草稿,那是白跑一轮;表单默认值一律以 `createForm` 的 `initialValues` 为准。
|
|
158
|
+
- **人员范围(EmployeeScope)解析失败**:`createPrepare` 返回 `NEEDS_CONFIRMATION`,`ambiguities` 里 `kind = "EMPLOYEE_SCOPE"`:
|
|
159
|
+
- `reason = "NOT_FOUND"` → 系统里没有该名称,**一次明确告知用户**“没找到「XX(类型)」,请给出系统里的准确名称或 `{"optionId":"候选id","content":"候选名称","type":"类型"}`”,最多重试 1 次;
|
|
160
|
+
- `reason = "MULTIPLE_MATCHES"` → 列出候选(`candidates`)让用户选,选定后按 `{"optionId","content","type"}` 回传;
|
|
161
|
+
- `reason = "NOT_RESOLVED"` → 名称/类型齐了但没拿到 ID,通常上一次解析没成功,按上面两种口径让用户确认;
|
|
162
|
+
- **禁止**因为"命令返回 ok"就当作字段已填好——出现 `ambiguities` 时必须先解决,否则该字段不会进入保存体。
|
|
163
|
+
- **静态必填标记未下发(`requiredInfoWarning`)**:`createForm` 返回的 `requiredInfoWarning` 非空时,说明 OA 没下发该表单的**静态**必填配置,此时 `requiredFields` / `subFormRequired` 只含系统字段(流程标题等)——**不代表该表单没有业务必填项**。按 `conditionalRequired` + `missing_fields` 处理即可:
|
|
164
|
+
- **`conditionalRequired`**:本表单的**条件必填**清单(OA 联动规则原样结构化)。每项 = 一个会变必填的字段(`fieldId`/`fieldName`/`subFormId`)+ 触发条件 `when[]`(`fieldId`/`fieldName`/`term`/`values[]`),`match` 为 `AND`/`OR`。**发起前用它主动向用户问齐**(例:"若「报销方式」选银行(付公司),则「账号」「开户机构名称」为必填"),不要等用户先填对触发字段。它是"可能的必填",不是当前必填。**它随大输出被移出 stdout 时**(只剩 `conditionalRequiredCount`)不必回头取:直接照下一条按 `missing_fields` 走即可。
|
|
165
|
+
- **`missing_fields` 可信**:条件命中与否由 `createPrepare` 按**实际所填数据**(含联动带出值)实时计算,`missing_fields` 就是当前真实缺失的必填项——照常 `createPrepare`,按它的返回补齐。**禁止**对用户说"系统不会校验必填项",也**禁止**用 `requiredInfoWarning` 非空当作"无法校验必填"的理由跳过校验。
|
|
166
|
+
- 只有需要向用户交代"OA 页面上带红色星号的字段"时,才提示用户对照表单红星核对(含明细表里的列,如费用明细的「发票」)。
|
|
167
|
+
- **必填缺失一次问齐**:`createPrepare` 返回 `NEEDS_INPUT`(`missing_fields`)时,**把主表 + 明细表全部缺失字段一次性列给用户**(每项注明需要的值类型/建议默认值),**禁止逐字段推演或逐个追问**;联动/默认值/记忆已覆盖的字段不会出现在 missing 里,直接采用即可。**`intent: draft` 时缺失不阻断、状态仍是 `READY`,但 `missing_fields` 同样会返回——必须原样转述(提交前需补齐),不要把 `READY` 读成"没有缺失"**。
|
|
168
|
+
- **必填的浏览 / 人员 / 发票类字段不要"先猜一个值试试"**:这类值要么来自用户(准确名称或 `{id,name}`),要么来自外部技能(发票走 `weaver-e10-yepiaotong`)。**第一次 `createPrepare` 就在 `data` 里留空**,让 `missing_fields` 把它们列出来,再连同其它缺失项**一次性问用户**;用猜测值去 prepare 只会白跑一轮——就算被接受,你也不知道它解析成了**哪个**对象,仍然要回头问用户。
|
|
169
|
+
- **`resolvedValues` 用来自查解析结果**:`createPrepare` 返回 `NEEDS_INPUT` / `NEEDS_CONFIRMATION` 时,`resolvedValues` 就是"我传的值 → 服务端最终值"的回显(选项给名称,浏览/人员/部门给 `{id,name}` 数组);`READY` 时同一内容在 `fields`(确认预览)。**解析结果与预期不符就不要往下走**(例如传「泛微」被解析成了另一个主体),按上面的口径向用户确认后续用准确名称/ID。
|
|
170
|
+
- **浏览按钮值匹配不上(BROWSER NOT FOUND)**:`createPrepare` 返回 `NEEDS_CONFIRMATION`(`ambiguities` 里 `kind = "BROWSER"`)时按 `reason` 分别处理:
|
|
171
|
+
- `reason = "NOT_FOUND"` 且 `candidatesAvailable = true` → CLI 已把该浏览控件首页的合法取值放进 `candidates`,**逐条列给用户挑**,选定后按 `{"id":"候选id","name":"候选名称"}` 重新 prepare;
|
|
172
|
+
- `reason = "NOT_FOUND"` 且 `candidatesAvailable = false` → **一次明确告知用户"系统里没有「XX」,请提供系统里准确的名称或 `{id,name}`"**,用户给出后最多重试 1 次;
|
|
173
|
+
- `reason = "MULTIPLE_MATCHES"` → 列出 `candidates` 让用户选,选定后按 `{"id":"候选id","name":"候选名称"}` 回传;
|
|
174
|
+
- **禁止自行换相近词反复 prepare**(如「差旅费」查不到就试「差旅」),也**禁止凭猜测直接构造 `{id,name}` 绕过澄清**。
|
|
175
|
+
- 明细表:`details` 的 key 是 subFormId,value 是行对象数组。
|
|
176
|
+
- **明细表(子表单)展示规则(Excel 列展示)**:`createPrepare` 返回的 `previewDetails`(明细表按列组织:`columns` 表头 + `rows` 每行明细)——明细表**必须用 Excel 列展示**(表头 + 每行一条明细,形如 `| 序号 | 费用日期 | 费用类型 | 费用说明 | 申请金额 |`,每行一行),**禁止把明细字段按"字段\|内容"平铺**;`previewDetails` 为空时才用 `fields` 平铺兜底。多条明细时逐行展示(序号递增)。
|
|
177
|
+
- 目录联动:附件字段 `folderDependsOnOption=true` 时,按最近一次 prepare 返回的 `attachmentFolderIds` 取 `folderId`(null=不指定目录)再上传。
|
|
178
|
+
- 初始化值:`createForm` 返回 `initialValues`(OA 预填值,含 onLoadForm 联动带出),prepare 的 `data` 应包含这些初始化字段值(用户明确填写的以用户为准);含 subFormId 的放 details 对应行,主表字段放 main。**漏带不会导致缺必填**(默认值由 CLI 自动并入主表与明细行);`missingFields` 里出现它就是真的没值,按上面口径问用户。
|
|
179
|
+
- 不重试:saveFormData/flow/create 失败、超时或结果不确定(`SAVE_UNCERTAIN`/`PARTIAL_SAVED`/`CONTEXT_ALREADY_WRITTEN`/`WRITE_UNCERTAIN`)禁止重试,返回恢复信息并让用户人工检查。
|
|
180
|
+
- 写操作遇登录失效:禁止自动重登重放,返回 `WRITE_UNCERTAIN` 停止,先只读回查。
|
|
181
|
+
- `context` 与工作流强绑定:prepare/apply 只用最终选定工作流那次 createForm 返回的 `context`。
|
|
182
|
+
- 发起成功且用户有新的语义记忆时,按 memory 规则主动调用 `workflow.memoryExtract` 保存本次工作流与字段偏好(见 workflow-memory.md)。
|