# 业票通发票管理 CLI

来源目录：`weaver-e10-yepiaotong`，内容版本 `3.0.0`。本模块把接口文档中可安全自动化的能力封装为 `weaver-work-cli invoice` 命令，供 AI Agent 通过结构化 JSON 调用。

源码位于 `src/shortcuts/invoice`。命令注册、operation manifest 和业务执行逻辑分离；具体执行逻辑在 `src/shortcuts/invoice/operations` 中按 operation class 维护。

面向 Agent 的说明位于 `skills/weaver-e10-yepiaotong`。入口 `SKILL.md` 只负责共享规则和 reference 路由；具体细节拆在 `skills/weaver-e10-yepiaotong/references/`，与飞书 CLI 的业务 Skill 组织方式保持一致。

## 公共前置

先通过 E10 鉴权模块登录：

```text
weaver-work-cli auth login --base-url "https://weapp.xxx.cn" --agent_type "<当前智能体名称>"
weaver-work-cli auth status --no-check
```

每个业票通业务请求由 CLI 托管：

1. 读取当前 `weaver-work-cli auth` Profile 的 E10 会话。
2. 调用或复用 `/api/inc/proxy/getToken?appType=1` 取得发票业务 Token。
3. 业务请求同时携带 E10 Cookie/ETEAMSID 和 `token` Header。

系统 Keychain/Secret Service 不可用时，发票 Token 只保存在当前命令进程内，
安全缓存失败不会阻断票夹查询；CLI 不会降级为明文 Token 文件。

Agent 不得在业务 JSON 中传 `access_token`、`app_key`、`app_secret`、Cookie、ETEAMSID 或发票 Token。

## Agent 入口

优先使用 `invoice run <operation>`：

Windows PowerShell：

```powershell
weaver-work-cli invoice schema
weaver-work-cli --json invoice run invoice.list --input-json '{"page_size":10,"start_pos":0}'
weaver-work-cli --json invoice list --view summary
weaver-work-cli --json invoice list --fields number,detailUrl
```

macOS/Linux（bash/zsh）：

```bash
weaver-work-cli invoice schema
weaver-work-cli --json invoice run invoice.list --input-json '{"page_size":10,"start_pos":0}'
weaver-work-cli --json invoice list --view summary
weaver-work-cli --json invoice list --fields number,detailUrl
```

成功和失败都使用 JSON envelope。成功写 stdout；失败写 stderr，并设置非 0 退出码。

当前输出层把完整 JSON 直接写 stdout。0.1.17 起可用 `--view summary`（列表语义平表，仅 `invoice.list` / `invoice.enterprise.list` 支持）与 `--fields a,b.c`（点路径投影，所有 operation 可用）裁剪输出——两者互斥，只影响输出、不改变请求参数；仍不提供飞书 CLI 的 `--jq`、`--format table/ndjson` 或通用 `--page-all`。Agent 使用时应默认小页读取和摘要渲染：列表先 `page_size=10`，按 `start_pos` 继续；回复只展示关键字段和数量，超长详情/OCR/调试 JSON 落本地文件后给路径。

## Operation 目录

| Operation | 风险 | 固定规则 |
| --- | --- | --- |
| `invoice.list` | 只读 | 个人票夹固定 `flag=0` |
| `invoice.enterprise.list` | 只读 | 企业票夹固定 `flag=6`，权限失败不降级个人票夹 |
| `invoice.get` | 只读 | `fid` 优先，或按 `number` 查询 |
| `invoice.upload` | 外部制品 | 固定上传 `ocr=0`，只取上传文件 ID，不做上传阶段解析 |
| `invoice.ocr.preview` | 上传+只读 | 固定 `flag=13`、`is_sync=1`、`is_save=1`，不保存票夹 |
| `invoice.validate.preview` | 外部查询 | 先取详情，固定 `flag=100`、`is_save=1`，不回写查验结果 |
| `invoice.import.prepare/apply` | 高风险写 | continuation 绑定本地文件 SHA-256 或远程 URL；导入默认推荐 `validate=true`、`syncToOa=true`，`filedMap` 在 inputSchema 中保持 JSON object |
| `invoice.add.prepare/apply` | 高风险写 | 单张票面校验、重复检查、确认后新增并回查 |
| `invoice.update.prepare/apply` | 高风险写 | 基于完整详情修改白名单字段，保留附件并回查 |
| `invoice.download` | 本地文件写 | 先校验 `fileId` 属于目标 `fid`，拒绝覆盖 |
| `invoice.delete.prepare/apply` | 高风险写 | 固定软删除 `flag=0`，确认后执行并回查 |
| `invoice.browse-field.data` | 只读 | 基于详情接口生成流程表单发票浏览按钮 JSON |
| `invoice.reim.file-ocr.preview` | 文件识别预览 | 对 E10 fileId 调用报销场景的发票识别接口，只保留成功项 |
| `invoice.reim.requests.list` | 只读 | 查询事前申请流程列表，默认 `pageNo=1`、`pageSize=20` |
| `invoice.reim.workflow.resolve` | 只读 | 根据事前申请 ID 获取报销工作流；无事前申请时传空数组 |
| `invoice.reim.form.structure` | 只读 | 获取报销流程表单字段结构 |
| `invoice.reim.row-info` | 只读 | 使用 urlencoded 请求获取单张发票明细行预填信息 |
| `invoice.reim.employee-superiors` | 只读 | 获取当前人员和上级信息 |
| `invoice.reim.field.search` | 只读 | 搜索表单关联字段值，用于用户修正或出差客户确认 |
| `invoice.reim.flow.create.prepare/apply` | 高风险写 | continuation 绑定已组装报销单 JSON；`work_flow_id/mainFormId/request_name/main_fields/detail_rows` 等字段在 schema 顶层逐项暴露，确认后调用 `createFlowNew` |
| `invoice.reim.flow.update.prepare/apply` | 高风险写 | continuation 绑定更新报销单 JSON；确认后调用 `updateFlow` |
| `invoice.issuing.make.prepare/apply` | 高风险写 | 固定销方信息，确认后调用 `makeInvoice` 开票或存台账 |

共享、转让和标签仍暂不暴露给 Agent：新版源资料给出了提交接口，但还缺少稳定的接收人 `appid/cid/uid` 解析来源、标签关系查询和写后回查契约。

## 常用命令

```text
weaver-work-cli --json invoice list --input-json '{"page_size":10,"start_pos":0}'
weaver-work-cli --json invoice enterprise list --input-json '{"page_size":10,"start_pos":0}'
weaver-work-cli --json invoice get --fid INVOICE_FID
weaver-work-cli --json invoice upload --file ./invoice.pdf
weaver-work-cli --json invoice ocr preview --file ./invoice.pdf
weaver-work-cli --json invoice validate preview --fid INVOICE_FID --scope personal
weaver-work-cli --json invoice download --fid INVOICE_FID --file-id FILE_ID --output ./invoice.pdf
weaver-work-cli --json invoice run invoice.browse-field.data --input-json '{"fid":"INVOICE_FID"}'
weaver-work-cli --json invoice run invoice.reim.requests.list --input-json '{"pageNo":1,"pageSize":20}'
```

写操作必须先 prepare，再 apply：

Windows PowerShell：

```powershell
weaver-work-cli --json invoice run invoice.ocr.preview --input-json '{"file":"./invoice.pdf"}'

weaver-work-cli --json invoice import prepare --input-json '{"file":"./invoice.pdf","validate":true,"syncToOa":true}'

weaver-work-cli --json invoice import apply --input-json '{"file":"./invoice.pdf","continuation":"PREPARE_CONTINUATION","confirm":true}'

weaver-work-cli --json invoice run invoice.reim.flow.create.prepare --input .\reim-create.json

weaver-work-cli --json invoice run invoice.issuing.make.prepare --input .\issuing.json
```

macOS/Linux（bash/zsh）：

```bash
weaver-work-cli --json invoice run invoice.ocr.preview --input-json '{"file":"./invoice.pdf"}'

weaver-work-cli --json invoice import prepare --input-json '{"file":"./invoice.pdf","validate":true,"syncToOa":true}'

weaver-work-cli --json invoice import apply --input-json '{"file":"./invoice.pdf","continuation":"PREPARE_CONTINUATION","confirm":true}'

weaver-work-cli --json invoice run invoice.reim.flow.create.prepare --input ./reim-create.json

weaver-work-cli --json invoice run invoice.issuing.make.prepare --input ./issuing.json
```

导入发票文件或远程 URL 时，面向 Agent 的正常链路是先 `invoice.ocr.preview`，再 `invoice.import.prepare` 使用 `validate=true`、`syncToOa=true`。只有用户明确要求跳过查验或离线导入时才传 `validate=false`；`validate=false` 表示跳过查验，不能描述为“查验通过”。`filedMap`、嵌套字段映射等 JSON 参数在 `--input-json` 中保持对象，CLI 只在 multipart 提交前序列化。

报销单创建和开票/存台账只接受 Agent 已组装好的结构化 JSON。CLI 不负责猜测事前申请匹配、出差客户或税率；这些规则在 Skill reference 中指导 Agent 组装和展示预览。报销单创建的字段必须在 operation 顶层逐项传入，不再包一层通用 `payload`。当前修正资料包没有客户档案查询或红字发票红冲接口，`invoice.customer.*` 和 `invoice.red.*` 不暴露为 operation，Agent 不能绕过 CLI 调用原始接口。写操作出现网络中断、部分成功、缺少回执 ID 或回查失败时，CLI 返回 `partial/write_uncertain`，Agent 禁止自动重复提交。

## 编辑白名单

`invoice.update.prepare` 只允许修改：

```text
code
number
comm_info.pro.date
comm_info.price.amount
comm_info.price.total
comm_info.price.dtax
comm_info.buyer.company
comm_info.buyer.tcode
comm_info.payer.company
comm_info.payer.tcode
fylx
currency
currencyName
```

禁止修改 `fid/id`、附件关联、`sedit`、Dubbo 字段、认证字段、`skipFlag=1` 等内部控制字段。
