feat: 对齐 lark-cli——搜索 enrich + 输出工程化 + 多维表格/表格/vc/mail/markdown 全套补全#158
feat: 对齐 lark-cli——搜索 enrich + 输出工程化 + 多维表格/表格/vc/mail/markdown 全套补全#158nengqi wants to merge 16 commits into
Conversation
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 5b6667c6b4
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| } | ||
| body := map[string]any{"status": status} | ||
| return bitableRun(cmd, func(bt string) bitableReq { | ||
| return bitableReq{method: "PUT", path: client.BitableV1Path("apps", bt, "workflows", workflowID), body: body, useV1: true} |
There was a problem hiding this comment.
Call the Base v3 workflow toggle endpoints
When bitable workflow enable or disable is run, this sends PUT /open-apis/bitable/v1/apps/{app_token}/workflows/{workflow_id} with a status body, but the current Lark base workflow shortcuts document the toggle APIs as PATCH /open-apis/base/v3/bases/:base_token/workflows/:workflow_id/enable and /disable (see github.com/larksuite/cli/shortcuts/base). In practice these new commands will hit the wrong service/path and fail to toggle workflows; route through BaseV3Call and append the status action to the path instead.
Useful? React with 👍 / 👎.
| return fmt.Errorf("解析 --config 失败: %w", err) | ||
| } | ||
| return bitableRun(cmd, func(bt string) bitableReq { | ||
| return bitableReq{method: "PATCH", path: formPath(bt, tableID, formID, "questions", questionID), body: body} |
There was a problem hiding this comment.
Patch form questions at the collection path
When bitable form field patch is used, the request goes to /forms/{form_id}/questions/{question_id} with the raw config as the body, but the Base v3 form-question update shortcut is PATCH /open-apis/base/v3/bases/:base_token/tables/:table_id/forms/:form_id/questions and expects a questions array whose item includes the id. The per-question path is not the documented endpoint, so this command will 404 or fail validation instead of updating the question; wrap the supplied fields with the questionID and call the collection endpoint.
Useful? React with 👍 / 👎.
提供 lark-cli 风格输出能力,供 api / search / bitable 新命令统一消费: - --format json|pretty|table|ndjson|csv - --jq <expr>(内置 gojq v0.12.17,纯 Go,无需外部 jq;pin 该版本保持 go 1.21 兼容) - 大整数精度:json.Number 链路,飞书 19 位 ID 不被 float64 截断 - table/csv:CJK 宽度对齐 + 单元格换行净化 带 13+ 单测(格式化/jq/大整数/CJK/csv)。
在既有 api 透传命令上增量加 --format json|pretty|table|ndjson|csv + --jq(走 internal/output): - 显式指定 --format/--jq 时走内置渲染(含大整数保精度);否则保持原 pretty/raw 行为不变 - 保留既有鉴权/dry-run/-o/include-headers/timeout/业务错误码处理
对齐 lark-cli +messages-search。原命令只返回消息 ID,现默认 enrich:
- search → 消息 ID → BatchGetMessages 取详情 → 解析发送者名/群名 → 人类可读视图
- --ids-only 退回纯 ID(省额外 API 调用)
- --format/--jq 结构化输出;--page-all/--page-limit 自动翻页
- 不兼容:-o json 输出从 {MessageIDs,...} 对象变 []EnrichedMessage 数组(详见 CHANGELOG)
带纯转换单测 + mock 集成测试。
…tch-get 补齐公开 API 支持、此前缺失的多维表格命令: - dashboard list|copy;form get|patch + form field list|patch - role member list|create|delete|batch-create|batch-delete - workflow enable|disable;bitable update(重命名/高级权限);record batch-get - 新增 internal/client/bitable_v1.go(dashboard copy/role-member/app update/workflow 启停走 bitable/v1,base/v3 无对应端点) - 统一执行器 bitableRun + 请求描述符 bitableReq 路由 base/v3 与 bitable/v1,写命令支持 --dry-run - 新命令统一接 internal/output(--format/--jq) 带 BitableV1Call mock 单测 + dry-run/form patch body 构造单测。
- README 全功能覆盖表:加 Raw API 行、多维表格行补全、搜索行标 enrich;技能数 25→26 + 加 feishu-cli-api 行 - CHANGELOG Unreleased 条目:三类新增详述 + search -o json breaking change 标注 - repo CLAUDE.md 命令速查:bitable 新命令 + search enrich + api --jq/--format - 新增 skills/feishu-cli-api/SKILL.md(裸调 API 子技能)
…lection 批量端点
响应 codex P1 review:
- workflow enable/disable 原走 bitable/v1 PUT apps/{token}/workflows/{id}+status(错误路径),
改为 base/v3 PATCH .../workflows/{id}/enable|disable(无 body),对齐 lark-cli base +workflow-enable/disable
- form-questions-update 原走 per-question 路径 .../questions/{qid}(不存在),
改为 collection 端点 .../questions + {questions:[{id,...}]} 数组(单次≤10),加 --questions flag
- 补回归单测锁住正确端点路径
默认走 collectMessageIDs:人类可读 ID 列表 + -o json 返回旧 schema
{MessageIDs,HasMore,PageToken},与升级前完全一致。--enrich 才走
collectEnrichedMessages 补全内容/发送者/群名/时间。去掉 --ids-only。
card-content-type 校验下沉到 --enrich 路径。
端点全走 base/v3,与 lark-cli base +dashboard-* --dry-run 逐个印证。 theme-style 嵌套 body.theme.theme_style;block create type 枚举校验; 读命令无 dry-run、写命令带 dry-run+config 全量覆盖。新增独立文件不动现有命令。
…record 附件 form create/delete + detail/submit(按 share_token 端点) + questions create/delete(collection 端点) workflow create/get/update(base/v3, update=PUT 整体替换) record upload/download/remove-attachment(table 级 append/get/remove_attachments + drive medias) form questions 组加 questions 别名;端点全部经 lark-cli dry-run 双重印证
- image get/update/media-upload/write-image(v3 float_images get/PATCH + drive medias/upload_all sheet_image + v2 values_image) - filter-view get/update(v3 filter_views GET/PATCH) - filter-view condition create/get/update/delete/list(v3 filter_views/:id/conditions,create 带 condition_id、update 走 PUT 由路径携带) - dropdown get/update/delete(v2 dataValidation GET?range + PUT/:sheet_id + DELETE) - batch-set-style(v2 styles_batch_update,复用 SetCellStyleBatch) - 全部新文件,helper 加 sheet 前缀,不改 go.mod/go.sum 及现有命令;端点经 lark-cli strings+help+dry-run 双重印证;新增单测 + 真实只读路径 e2e 验证
… diff vc bot meeting-join/leave/events 对齐 lark vc bots 域(POST bots/join+leave、GET bots/events) mail signature 读 user_mailboxes settings/signatures 列表,支持 --detail 筛单条 markdown diff 下载远端内容本地算 unified diff(远端版本互比 / 远端 vs 本地文件),不改远端 端点经 lark-cli strings+help 双重印证;新命令均带 dry-run + 单测,go.mod 未动
…vc bot + mail signature + markdown diff 到 CHANGELOG/README/skill
1. markdown diff 远端版本下载改用 files/{token}/download?version=N(同 token+version 查询参数,不再 GetFileVersion 拿 token 当下载目标),新增 client.DownloadFileVersion(raw ApiReq+Do,SDK builder 丢 QueryParams)+ FetchFileVersionContent
2. sheet UpdateFloatImage offset-x/-y 改 *float64 指针表达「是否更新」,0 为合法值;cmd 层用 Changed() 区分未传 vs 显式 0
3. vc events page-size 校验改 pageSize!=0 && (<20||>100),拒绝 1-19
4. bitable download-attachment 总是先 get_attachments 拿 extra_info,再带 extra 下载(与 lark 一致,防 403)
5. bitable question-ids 兼容 JSON 数组与 CSV
6. sheet dropdown get 删冗余 output 分支
7. vc events dry-run 只展示非空参数
更新 offset/page-size/question-ids/attachment 单测
…md 限制提示 - download-attachment 不再注册 --format/--jq(避免 output.ParseOptions 抢用 --output 把结果 JSON 覆盖下载的附件),结果改 printJSON 到 stdout,--output 专用于附件保存目标(e2e 实测 clobber bug) - markdown diff Long + 版本下载错误补提示:模式2/3 版本对比需文件有版本快照,普通 .md 无数字版本会 404,仅 docx/sheet/bitable 等支持(mode1 不受影响)
…l+边界校验)
- H1 DownloadFileVersion: HTTP 200 + JSON 业务错误体 {code,msg} 不再当二进制写盘,优先 Content-Type 判 JSON、'{' 前缀作辅助且须 parse 出 code!=0
- H2 markdown diff: 加 maxDiffLines=50000 上限,算 LCS 前拦截超大内容防 OOM
- M2 download-attachment: 多 --file-token 部分缺失打 stderr 警告并继续下载已匹配的,仅全空才报错
- M3 vc meeting-events: --start/--end 改 int64 数值比较,修字典序在位数不同时误判先后
- M1 DownloadFileVersion: 补注释说明 size 检查为非流式内存载入后防超大写盘
- L1 UpdateFloatImage: image==nil 防御
- L3 sheet image update: width/height 显式设置时校验≥20、offset≥0,与 help 一致
- L2 vc page-size: flag/help 注明不传或 0=默认 20
- 补 H2/M2/M3/L1/L3/H1 单测
…-width 0 报错
- [CRITICAL] markdown checkDiffSize 加 n*m 乘积上限 maxDiffCells(单侧降到 20000):原单侧 50000 不约束 LCS 矩阵内存,两侧各 50000 行=25亿 int≈10GB OOM
- [WARN] parseDownloadJSONError 改只信 Content-Type(去掉 RawBody 前缀辅助路径):避免把内容恰为 {code:N} 的合法文件误判为业务错误;注明 DownloadFileVersion 仅用于 markdown 文本下载
- [MINOR] sheet image update 前置 guard 改用 Changed() 判断 width/height:--width 0 现报 width<20 而非误报未指定字段
- 同步更新 TestCheckDiffSize(新增乘积超限断言)/TestParseDownloadJSONError(只信 CT)
背景
进一步对齐 lark-cli,把此前需回退 lark-cli 的场景补齐到 feishu-cli:消息搜索结果 enrich、输出工程化(jq/表格)、多维表格全套、电子表格高级、vc/mail/markdown 补全。基于
main增量实现,不改既有命令默认行为(无不兼容变更)。改了什么
① 消息搜索 enrich(
search messages)--enrichopt-in:补全 内容/发送者/群名/时间(对齐 lark+messages-search)-o json仍返回{MessageIDs,HasMore,PageToken}旧 schema(完全向后兼容)② 输出工程化 +
api增强internal/output包:--format json|pretty|table|ndjson|csv+--jq(内置 gojq v0.12.17 纯 Go,pin 保持go 1.21)api命令新增--format/--jq(显式指定才走内置渲染,否则保留原 pretty/raw +-o/--include-headers/--timeout/业务错误码处理)json.Number,飞书 19 位message_id/chat_id不被 float64 截断③ 多维表格补全(
bitable)internal/client/bitable_v1.go:dashboard copy / role-member / app update 等 base/v3 无对应端点的走 bitable/v1④ 电子表格高级(
sheet)⑤ vc / mail / markdown
vc botmeeting-join/leave/eventsmail signaturemarkdown diff(本地 unified diff:远端最新 vs 本地文件 / 远端版本对比;自带 LCS,无外部依赖)验证
go build/vet/test ./...全绿;新增单测覆盖输出格式化(大整数/jq/table CJK/csv)、enrich、bitable/sheet/vc/mail/markdown 命令的请求构造与边界。--dry-run端点)+ codex 独立 review 两轮 + 复核,修复 12+ findings(端点路由、LCS 内存上限、download 业务错误检查、附件 extra、时间数值比较、边界校验等)。几处端点与 lark-cli 现状不同(已实测核对)
.../workflows/{id}/enable|disable(无 body),form questions update 走 collection 端点.../forms/{id}/questions+{questions:[...]},record 附件下载总是先get_attachments取extra_info再带extra下载——均与 lark-cli--dry-run实证一致。mail signature走.../user_mailboxes/{id}/settings/signatures:实测返回 200,而 lark-cli 的me/signatures(无settings)实测 404——飞书 API 已演进,采用前者。依赖
新增
github.com/itchyny/gojq v0.12.17(pin 保持go 1.21兼容,未抬升 go directive)。