PicoBot/.qoder/skills/lark-sheets/references/lark-sheets-conditional-format.md
ooodc a7883dbed9 refactor(todo): 重构待办事项管理逻辑及更新状态规则
- 移除 TodoItem 中的 priority、created_at 和 updated_at 字段
- 强制每个任务都必须有唯一 id,且由用户负责生成
- 修改合并模式逻辑,merge=true 下保留未提及的旧任务
- 支持已完成和已取消任务重新激活(状态改回 pending 或 in_progress)
- 禁止 in_progress 状态退回到 pending,必须标记为 completed 或 cancelled
- 优化状态转换校验,允许特定状态间合法切换
- 简化任务变更消息,移除详细的新增/更新/移除统计
- 更新文档和示例,明确 id 必须由用户生成和使用
- 修复和补充测试,增强状态转换和合并模式验证
- 调整任务时间戳生成逻辑,统一使用当前时间及索引
- 该变更提供更合理的任务状态机械及管理模式,提升稳定性和易用性
2026-06-13 09:22:33 +08:00

180 lines
11 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Lark Sheet Conditional Format
## 真对象硬约束 + 触发词清单
用户出现以下口语指令时,**强制**走 `+cond-format-{create|update|delete}`**禁止**用 `+cells-set` 写静态背景色 / 字体色代替:
- **颜色动作**"标红 / 标黄 / 标绿 / 上色 / 染色 / 涂色 / 表红色 / 表黄色"
- **视觉强调**"高亮 / 突出 / 标记 / 标注 / 区分"
- **条件触发**"重复的标出来 / 异常的圈出来 / 过期的染红 / 大于 X 的标黄 / 不达标的标红"
- **联动语义**"颜色随数据变 / 联动 / 自动更新 / 改了数据颜色也跟着变"
- **数值可视化**"数据条 / 色阶 / 渐变色 / 进度条样式"
飞书表格的"颜色标记"语义 = 条件格式规则 ≠ 静态背景色。如果用 `+cells-set` 写静态,源数据变化时颜色不会跟着变(典型反例:用户要求"过期单元格标红"时,模型用静态填充——日期变化后单元格颜色不再准确反映过期状态)。
**判断标准**:交付后 `+cond-format-list` 必须能返回该规则;否则视为违规。
**大数据量首选**:当数据量 > 1000 行时,条件格式是首选——它由飞书自身渲染,比"本地脚本逐行计算 + `+cells-set` 写静态背景色"更高效、更稳(颜色还能随源数据自动联动)。
## 使用场景
读写条件格式对象。本 reference 覆盖 4 个 shortcut
| 操作需求 | 使用工具 | 说明 |
|---------|---------|------|
| 查看已有条件格式 | `+cond-format-list` | 获取规则类型、范围和样式配置 |
| 创建/更新/删除条件格式 | `+cond-format-{create|update|delete}` | 对条件格式规则执行写入操作 |
典型工作流:先读取现有条件格式了解配置 → 执行创建/更新/删除 → **必须再次读取验证结果**
**常见配置错误(必须注意)**
- **创建后必须验证**:条件格式创建后必须调用 `+cond-format-list` 验证规则是否生效。如果验证发现规则未生效或配置不正确,应立即修复并重试
- **范围要精确**:条件格式的应用范围必须精确覆盖用户指定的列/行,不要遗漏
- **`style.back_color` vs `style.fore_color` 的中文语义**:用户中文语境下的"**标红/高亮/染色/标记**"指**单元格背景色**,用 `back_color`"**文字红/字体红/把字变红**"才用 `fore_color`。默认无说明时选 `back_color`。把过期数据涂红、重复值高亮等都应该是 `back_color: "#FFE6E6"`(或类似浅红)配合可选的 `fore_color` 加深字体
- **日期/空值比较必须防空**:用户说"过期的标红"时,除了 `TODAY()`,公式必须排除空单元格,否则空白格也会被误判为"早于今天"而全表标红。正确公式:`=AND(E1<>"", E1<=TODAY())`;错误公式:`=E1<=TODAY()`(空值会被当作 0 判为过期)
- **公式条件注意引用方式**:自定义公式条件中的单元格引用需要根据实际场景选择相对/绝对引用(如 `=E1<=TODAY()` 而非 `=$E$1<=TODAY()`,后者只比较一个格)
⚠️ **用户明确要求"辅助列+条件格式"两步走时,禁止用 `expression` 绕过(高频致命错误)**:当用户说以下任意一种表达时,必须按两步走(先建辅助列 → 再基于辅助列做条件格式),**禁止**直接用一个 `rule_type: "expression"` 公式一步完成:
- "**增加辅助列**,再/然后标记……"
- "**先计算/判断** XX **是否** YY**再**标记……"
- "**新建一列**放结果,再用结果染色"
- 明确要求用 "辅助列"、"辅助字段"、"判断列"、"标记列"
**正确做法(两步走)**
```
Step 1: `+cells-set` 在新列写判断公式(形成"是/否"或布尔辅助列)
range="H2", cells=[[{formula: "=IF(A2>B2, \"是\", \"否\")"}]], --copy-to-range="H2:H100"
Step 2: 基于辅助列值做条件格式(用 cellIs 或引用辅助列的 expression
`+cond-format-{create|update|delete}` create
rule_type: "expression"
ranges: ["A2:H100"] // 整行高亮
attrs: [{formula: ["=$H2=\"是\""]}] // 引用辅助列
style: {back_color: "#FFECEC"}
```
**错误做法(一步走绕过辅助列)**
```
`+cond-format-{create|update|delete}` create
rule_type: "expression"
ranges: ["2:145"]
attrs: [{formula: ["=$O2>$H2"]}] ← 虽然逻辑等价,但产物里缺辅助列 → 不满足用户明确要求的"辅助列"诉求
```
为什么禁止一步走:用户明确要求辅助列是有**业务意图**的——让人肉眼能在表里看到"是/否"列;条件格式只是视觉辅助。一步 expression 虽然效果对了,但用户打开表格看不到辅助列,被视为"操作不完整/未采用公式"。
`expression` 单独使用的场景是:用户**没有**明确要求辅助列、只要"标红符合条件的行"时。
⚠️ **创建条件格式前必须读数据行确认列对应**:仅读首行表头(`+csv-get range="A1:Z1"`)不够——如果表头语义含糊(比如"时间"、"日期"这种多列同义词formula 里引用的列字母可能张冠李戴。必须再读 3-5 行**数据样本**(如 `range="A2:Z6"`)确认:①列名对应的实际值;②字段含义匹配用户描述;③数据类型是日期/数字/文本。特别是比较类条件格式(`=$A2>$B2` 这种),列字母选错整条规则就废了。
## Shortcuts
| Shortcut | Risk | 分组 |
| --- | --- | --- |
| `+cond-format-list` | read | 对象 |
| `+cond-format-create` | write | 对象 |
| `+cond-format-update` | write | 对象 |
| `+cond-format-delete` | high-risk-write | 对象 |
## Flags
### `+cond-format-list`
_公共四件套 · 系统:`--dry-run`_
| Flag | Type | 必填 | 说明 |
| --- | --- | --- | --- |
| `--rule-id` | string | optional | 按规则 id 过滤 |
### `+cond-format-create`
_公共四件套 · 系统:`--dry-run`_
| Flag | Type | 必填 | 说明 |
| --- | --- | --- | --- |
| `--properties` | string + File + Stdin复合 JSON | required | 规则配置 JSON`style`(命中样式,必填)和 `attrs?`(规则参数列表,因 `rule_type` 不同结构而异)/ `has_ref?``rule_type``ranges` 已拎为独立 flag |
| `--rule-type` | string | required | 条件格式规则类型;优先级高于 `--properties` 中同名字段(可选值:`duplicateValues` / `uniqueValues` / `cellIs` / `containsText` / `timePeriod` / `containsBlanks` / `notContainsBlanks` / `dataBar` / `colorScale` / `rank` / `aboveAverage` / `expression` / `iconSet` |
| `--ranges` | string + File + Stdin简单 JSON | required | 应用条件格式的 A1 范围 JSON 数组(如 `["A1:A100","C2:C50"]`);优先级高于 `--properties` 中同名字段 |
### `+cond-format-update`
_公共四件套 · 系统:`--dry-run`_
| Flag | Type | 必填 | 说明 |
| --- | --- | --- | --- |
| `--rule-id` | string | required | 目标规则 id |
| `--properties` | string + File + Stdin复合 JSON | required | 规则配置 JSON结构同 `+cond-format-create``--properties`update 是整组覆盖式 |
| `--rule-type` | string | required | 条件格式规则类型;优先级高于 `--properties` 中同名字段(可选值:`duplicateValues` / `uniqueValues` / `cellIs` / `containsText` / `timePeriod` / `containsBlanks` / `notContainsBlanks` / `dataBar` / `colorScale` / `rank` / `aboveAverage` / `expression` / `iconSet` |
| `--ranges` | string + File + Stdin简单 JSON | required | 应用条件格式的 A1 范围 JSON 数组(如 `["A1:A100","C2:C50"]`);优先级高于 `--properties` 中同名字段 |
### `+cond-format-delete`
_公共四件套 · 系统:`--yes`、`--dry-run`_
| Flag | Type | 必填 | 说明 |
| --- | --- | --- | --- |
| `--rule-id` | string | required | 目标规则 id |
## Schemas
> 复合 JSON flag 字段速查(只列顶层 + 一层嵌套)。深层结构看下方 `## Examples`,或用 `--print-schema` 读完整 JSON Schema用法见 SKILL.md「公共 flag 速查」与「Agent 使用提示」)。
### `+cond-format-create` `--properties` / `+cond-format-update` `--properties`
_创建/更新的条件格式属性_
**顶层字段**
- `rule_type` (enum) — 条件格式规则类型 [duplicateValues / uniqueValues / cellIs / containsText / timePeriod / containsBlanks / notContainsBlanks / dataBar / colorScale / rank / aboveAverage / expression / iconSet] — ⚠️ 已拎为独立 flag `--rule-type`,请勿在此 JSON 内重复填写(同名以独立 flag 为准)
- `ranges` (array<string>) — 应用条件格式的 A1 范围列表 — ⚠️ 已拎为独立 flag `--ranges`,请勿在此 JSON 内重复填写(同名以独立 flag 为准)
- `style` (object) — 命中规则时应用的单元格样式 { back_color?: string, fore_color?: string, text_decoration?: enum, font?: enum }
- `attrs` (array<oneOf>?) — 规则参数列表
- `has_ref` (boolean?) — 可选
## Examples
公共四件套:所有 shortcut 顶部排列 `--url` / `--spreadsheet-token` / `--sheet-id` / `--sheet-name`XOR
### `+cond-format-list`
```bash
# 列出当前 sheet 全部条件格式规则(拿 rule_id 供 update/delete
lark-cli sheets +cond-format-list --url "..." --sheet-id "$SID"
```
### `+cond-format-create`
`--rule-type` / `--ranges` 是独立 flag不要再放 `--properties``style` / `attrs` 等结构走 `--properties`
```bash
# 重复值高亮
lark-cli sheets +cond-format-create --url "..." --sheet-id "$SID" \
--rule-type duplicateValues --ranges '["A1:A100"]' \
--properties '{"style":{"back_color":"#FFD7D7"}}'
# 数据条
lark-cli sheets +cond-format-create --url "..." --sheet-id "$SID" \
--rule-type dataBar --ranges '["B2:B100"]' \
--properties @rule.json
```
### `+cond-format-update`
整组覆盖式:先 `+cond-format-list --rule-id <id>` 拿当前完整配置,改后整组传回。
### `+cond-format-delete`
```bash
lark-cli sheets +cond-format-delete --url "..." --sheet-id "$SID" --rule-id "$RULE_ID" --yes
```
> 一次只删一个 `--rule-id`。要删**多个**条件格式时,先 `+cond-format-list` 拿到各 `rule-id`,再用 `+batch-update` 把多个 `+cond-format-delete` 合并为单次原子提交,不要逐个调用。
### Validate / DryRun / Execute 约束
- `Validate`XOR 公共四件套;`--rule-type` / `--ranges` 必填;`--properties` 必须能解析为合法 JSON`--rule-type` 检查必填子字段(`cellIs``attrs.operator` + `attrs.value``expression``attrs.formula``colorScale``min/mid/max` 配色等);`+cond-format-delete` 强制 `--yes``--dry-run`
- `DryRun`:写操作输出"将要 POST/PATCH/DELETE 的 conditional_format 请求模板"。
- `Execute`:写后不自动回读;如需确认,自行调用 `+cond-format-list --rule-id <id>` 比对规则 / 范围 / 样式。