首页
/ impeccable `extract` 流程全解析:把重复 UI 系统化抽取为设计 Token 与可复用组件

impeccable `extract` 流程全解析:把重复 UI 系统化抽取为设计 Token 与可复用组件

2026-09-07 20:08:51作者:董斯意

impeccable(The design language that makes your AI harness better at design)为每个命令提供一份可执行的 reference 指南,本篇文章聚焦其中的 Extract Flowplugin/skills/impeccable/reference/extract.md,该文件在多份技能产物中同步镜像,如 skill/reference/extract.md.claude/skills/impeccable/reference/extract.md)。它的任务一句话可概括:识别代码库中可复用的模式、组件与设计 Token,将其抽取并沉淀进设计系统,实现系统性复用。读完本文,你将掌握一条从“发现设计系统”到“抽取—丰富—迁移—文档化”的六步方法论,理解 impeccable 对“过度抽象”的明确边界(3+ 次使用与意图一致),并能结合仓库中的 DESIGN.md Token 规范、sidecar 结构与相邻命令分工,在自己项目中安全地收敛样式与组件漂移。

1. extract 的定位:把“系统”从漂移中捞回来

在 impeccable 技能中,extract 属于命令表中的 Build 类命令,其完整行定义为:

Command Category Description Reference
extract [target] Build Pull reusable tokens and components into design system reference/extract.md

该行来自技能主文件 skill/SKILL.src.md(并在 plugin/skills/impeccable/SKILL.md 及多份镜像中保持一致)。技能的 description 元信息里,extract 与 design / redesign / shape / critique / audit / polish / clarify / distill / harden / optimize / adapt / animate / colorize 等动作并列,覆盖“设计系统与可复用 token 的建立与维护”;根目录 README.md 也将其收录为面向用户的可调用命令:/impeccable extract — Pull reusable components and tokens into the design system。

补充两点定位细节:

  • 触发时机:当代码库出现“漂移”(drift)与不一致时最适合调用本命令。命令元数据 plugin/skills/impeccable/scripts/command-metadata.json 给出了面向路由的官方描述:“Pull reusable patterns, components, and design tokens into the design system. Identifies repeated patterns and consolidates them. Use when you have drift across the codebase and want to bring things back to a consistent system.”,并注明参数形式为 [target](指明目标页面/功能/目录范围)。
  • 分发归类:provider 侧的分类映射 scripts/lib/skill-categories.jsinitdocumentextractlive 统一归入 system(SYSTEM - setup and tooling),与文档中标记的 Build 语义形成互补视角——它既是一次“构建”,也是一种对项目系统化状态的维护动作。

执行时无需加载额外 playbook:进入 extract 流程后,直接以本 reference 的六个步骤作为操作主线。

2. Step 1 · 发现设计系统(Discover the Design System)

抽取的第一步不是看“重复代码”,而是先找到设计系统本身。文档要求你定位:

  • 设计系统 / 组件库 / 共享 UI 目录所在位置;
  • 其组织方式:组件如何组织、命名约定是什么、设计 Token 的结构、导入导出(import/export)约定。

关键停止条件(CRITICAL):如果项目当前根本不存在设计系统,流程要求你不要擅自新建一个,而是 STOP 并调用 harness 的提问工具(文档原文为 AskUserQuestion)向用户澄清——确认偏好的存放位置与结构之后,再决定是否从零搭建。这与 impeccable 的核心守则一脉相承:视觉权威是证据,而非文件名;凭空建立的 token 规范等于“制造事实”。

从仓库可看到这套“设计系统”在磁盘上的典型落地形态(由 sibling reference skill/reference/document.md 说明):

  • 根目录的 DESIGN.md:YAML frontmatter 存放机器可读 token(colorstypographyroundedspacingcomponents),正文按八个固定 Markdown 小节书写(Overview / Colors / Typography / Layout / Elevation & Depth / Shapes / Components / Do's and Don'ts);
  • .impeccable/design.json sidecar:承载 schema 放不下的元数据——色阶 tonal ramp、shadow/elevation token、motion token、断点,以及可直接渲染进 shadow DOM 的组件 HTML/CSS 片段。

仓库内 demos/landing-demo/DESIGN.md 是一个真实的、可供对照的设计系统样例:其 frontmatter 定义了 name: Lumina、颜色角色(cream / accent / accent-deep 等)、六档 typography role(display / headline / title / body / lede / label)、radius 阶梯(card: 20px / pill: 999px)与 spacing 阶梯(xs: 8px2xl: 80px)。Step 1 的“理解 Token 结构、命名约定”就是要去读懂这类文件,使后续抽取的新 token 与既有阶梯、命名风格严丝合缝。

3. Step 2 · 识别模式(Identify Patterns)

在目标区域内寻找“可抽取的机会点”,文档给出了六类典型线索:

线索类型 观察对象
重复组件(Repeated components) 3+ 次出现的相似 UI 模式:按钮、卡片、输入框
硬编码值(Hard-coded values) 本应成为 token 的颜色、间距、字体、阴影
不一致变体(Inconsistent variations) 同一概念存在多种实现方式
组合模式(Composition patterns) 重复出现的布局/交互组合:表单行、工具栏组、空状态
字型样式(Type styles) 反复出现的 font-size + weight + line-height 组合
动效模式(Animation patterns) 反复出现的 easing、duration、keyframe 组合

价值评估准则是整份文档的重心:只有“使用 3+ 次且意图相同”的东西才值得抽取——过早抽象比重复更糟(Premature abstraction is worse than duplication)。反之,两个视觉相似但服务不同目的按钮(例如“提交订单”与“删除账号”)应当各自保留,合并它们反而制造语义灾难。这条“意图一致性”约束在后续 NEVER 清单中再次出现,是判断边界的主尺。

仓库同源的理念可参见 skill/reference/document.md 的扫描模式(approach C: auto-extract, then confirm):它在为项目生成 DESIGN.md 时同样只抽取“真实被复用”的 token,并明确告诫“Don't extract every token. Stop at what's actually reused; one-offs pollute the system.”——extract 流程与 document 流程在“识别复用物”这件事上共享同一套克制哲学。

4. Step 3 · 规划抽取(Plan Extraction)

识别出候选后,不要立刻动手改写,先产出一份系统化计划,至少覆盖五个维度:

  1. 要抽取的组件:哪些 UI 元素应变成可复用组件?
  2. 要创建的 Token:哪些硬编码值应变成设计 Token?
  3. 要支持的变体:每个组件需要哪些 variant(primary / secondary / ghost / hover / disabled…)?
  4. 命名约定:组件名、token 名、prop 名都要与既有模式对齐;
  5. 迁移路径:如何把现有使用点重构到新的共享版本上。

IMPORTANT 提示:设计系统是增量生长的。只抽取“当下明确可复用”的东西,而不是“将来某天或许能用”的东西。规划阶段若发现某个抽象缺乏三个真实使用点,就把它留在原地。

在具体命名时,文档要求 token 具备清晰的 primitive(原始层)vs semantic(语义层) 分层与正确的层级组织:primitive 是物理值阶梯(具体色值、字号、间距步进),semantic 表达使用角色(bg-surfacetext-primaryradius-card)。组件 token 通过 {path.to.token} 引用 primitive(例如 backgroundColor: "{colors.primary}"),primitive 之间不得互相引用——这套约束见 skill/reference/document.md 的 frontmatter 规则部分。仓库样例 demos/landing-demo/DESIGN.mdaccent: "#c8552b"accent-deep: "#a8431f" 这类“描述性 slug 而非 blue-800”的命名方式,正是值得沿用的既有约定。

5. Step 4 · 抽取与丰富(Extract & Enrich)

进入实现阶段,目标不是“照抄”,而是构建改良后的可复用版本。三类产出各有质量底线:

  • 组件(Components):清晰的 props API + 合理默认值;为不同用例提供正确的 variant;把可访问性内建进去(ARIA、键盘导航、焦点管理);附带文档与使用示例。
  • 设计 Token(Design Tokens):清晰的命名(primitive vs semantic)、正确的层级组织、以及“何时用哪个 token”的说明文档。不要给每个值都建 token——token 必须承载语义意义。
  • 模式(Patterns):记录何时使用该模式、给出代码示例、说明其变体与组合方式。

补充组件侧可落地的规范(来自 document.md 的“组件翻译规则”,用于把组件写入 sidecar 供 live panel 渲染):

  • 每个组件必须自包含、可直接 drop-in,CSS 用字面量属性写全,不依赖 Tailwind/框架运行时;
  • 作用域类名统一 ds- 前缀(如 ds-btn-primary),避免同一 shadow DOM 内冲突;
  • 图标内联为 SVG,不得引用图标字体包或 <img src>
  • 补全 :hover:focus-visible 状态规则,让静态快照“活”起来;
  • 只保留该组件的标志性 CSS(背景、文字色、padding、圆角、字号、过渡),跳过 box-sizing 之类的通用 reset。

文档同时强调:抽取时必须持续对照既有设计系统约定(Step 1 的产出),不能凭空发明一套新的体系。

6. Step 5 · 迁移(Migrate)

用新共享版本替换既有使用点,四个动作缺一不可:

  1. 找出所有实例(Find all instances):系统化搜索刚抽取的模式,不要凭记忆;
  2. 系统性替换(Replace systematically):逐一让每个使用点消费共享版本;
  3. 彻底测试(Test thoroughly):确保视觉与功能对等(visual and functional parity)——迁移的最大风险是“看起来一样、行为悄悄变了”;
  4. 删除死代码(Delete dead code):清掉旧实现,避免“新旧两套并存”的二次漂移。

迁移的验证环节可以联动 impeccable 的其他命令形成闭环:例如以 skill/reference/audit.md 对抽取后的组件做技术质量复检(可访问性、性能、响应式),用 skill/reference/craft-floor.md 的质量底线兜住“品质下限”;测试层面,仓库为行为守则建立了大量可执行断言,tests/skill-behavior/scenarios.test.mjstests/skill-behavior/workflow-contract.test.mjs 展示了参考文档如何被当作“行为契约”来验证——迁移后“视觉与功能对等”也应以这类可验证断言为准绳,而非口头声明。

7. Step 6 · 文档化(Document)

迁移完成后,把成果写回系统文档,让下一次 AI/Agent 会话能看到新秩序:

  • 向组件库登记新组件;
  • 记录 token 的用法与取值;
  • 补充示例与使用指南(guidelines);
  • 同步更新 Storybook 或组件目录(component catalog)。

仓库语境下,这与 document 命令(生成/刷新 DESIGN.md 与 .impeccable/design.json)形成天然的“抽取 → 固化”接力:extract 把重复实现收敛成共享组件与 token 后,由 document/doctor 机制负责把 DESIGN.md 与 sidecar 刷新到与实现一致的状态(skill/reference/document.md 明确要求 regenerate sidecar whenever you regenerate root DESIGN.md)。文档化做得到位,后续 shape / new-work / live 等命令才有可靠的“on-brand”依据。

8. 绝不能做的事(NEVER 清单)

文档以六条禁令收尾,它们是抽取工作不可逾越的红线:

禁令 为什么
不抽取未经泛化的、一次性/强上下文实现 脱离具体上下文的实现缺乏复用价值
不创建“泛化到无用”的组件 抽象若失去具体语义,就只是一层空壳
不忽视既有设计系统约定进行抽取 新抽象必须融进现有体系,否则制造第二套系统
不跳过 TypeScript 类型与 prop 文档 弱类型、无文档的共享组件等于埋雷
不为每个值都建 token token 必须承载语义意义,否则只是给硬编码换了个名字
不抽取“意图不同”的东西 外观相似但目的不同(两个按钮服务不同动作)应保持分离

其中第 1 条与第 6 条正是 Step 2“3+ 次 + 意图一致”这一准绳的两端:前者拒绝低复用度的抽取,后者拒绝高相似度但语义冲突的合并。抽象的价值不取决于“长得像不像”,而取决于“意图是否可共享”。

9. 与相邻命令的分工与取舍

extract 容易与两个命令混淆,实际分工如下:

  • document:以当前实现为输入,把“现状视觉系统”固化成 DESIGN.md(含 frontmatter token)与 sidecar——本质是描述与固化。它的扫描模式里也用到 “auto-extract” 一词,但那是指从代码里自动读出既有 token 值,而非新建共享组件。
  • extract:面向“代码库有漂移、同一概念被多次实现”的场景,任务是识别、抽取、沉淀,让重复收敛到统一系统——本质是收敛与重构

实践中的建议是先后互补:项目尚无 DESIGN.md 时先跑 document 建立基线;当多处实现开始发散、同一按钮出现三种圆角四种配色时,跑 extract 收敛;收敛完成后再让 document 刷新文档。抽取全程保持“增量生长、克制抽象、以用户确认为前置”的心态——impeccable 的设计哲学在这里体现得尤为清晰:系统服务于真实复用,而不是为抽象而抽象

登录后查看全文
热门项目推荐
相关项目推荐

项目优选

收起
kernelkernel
deepin linux kernel
C
33
18
ops-transformerops-transformer
本项目是CANN提供的transformer类大模型算子库,实现网络在NPU上加速计算。
C++
1.13 K
2.75 K
pytorchpytorch
作为 Ascend for PyTorch 社区的核心组件,TorchNPU 是昇腾专为 PyTorch 打造的深度学习适配插件,使 PyTorch 框架能够直接调用昇腾 NPU,为开发者提供昇腾 AI 处理器的超强算力。
Python
857
1.35 K
docsdocs
暂无描述
Markdown
897
5.8 K
kernelkernel
openEuler内核是openEuler操作系统的核心,既是系统性能与稳定性的基石,也是连接处理器、设备与服务的桥梁。
C
529
593
ops-nnops-nn
本项目是CANN提供的神经网络类计算算子库,实现网络在NPU上加速计算。
C++
915
1.83 K
jiuwenswarmjiuwenswarm
JiuwenSwarm 是一款基于openJiuwen开发的智能AI Agent,它能够将大语言模型的强大能力,通过你日常使用的各类通讯应用,直接延伸至你的指尖。
Python
3.58 K
1.01 K
ops-mathops-math
本项目是CANN提供的数学类基础计算算子库,实现网络在NPU上加速计算。
C++
1.35 K
1.46 K
cann-learning-hubcann-learning-hub
CANN 学习中心仓,支持在线互动运行、边学边练,提供教程、示例与优化方案,一站式助力昇腾开发者快速上手。
Jupyter Notebook
1.01 K
515
AscendNPU-IRAscendNPU-IR
AscendNPU-IR是基于MLIR(Multi-Level Intermediate Representation)构建的,面向昇腾亲和算子编译时使用的中间表示,提供昇腾完备表达能力,通过编译优化提升昇腾AI处理器计算效率,支持通过生态框架使能昇腾AI处理器与深度调优
C++
547
388