@jahanxu/code-flow 0.1.2 → 0.2.0
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/package.json +1 -1
- package/src/adapters/claude/CLAUDE.md +11 -1
- package/src/adapters/claude/commands/cf-init.md +269 -0
- package/src/adapters/claude/commands/cf-inject.md +41 -0
- package/src/adapters/claude/commands/cf-learn.md +120 -0
- package/src/adapters/claude/commands/cf-scan.md +56 -0
- package/src/adapters/claude/commands/cf-stats.md +65 -0
- package/src/adapters/claude/commands/cf-validate.md +71 -0
- package/src/cli.js +7 -10
- package/src/adapters/claude/skills/cf-init.md +0 -13
- package/src/adapters/claude/skills/cf-inject.md +0 -12
- package/src/adapters/claude/skills/cf-learn.md +0 -11
- package/src/adapters/claude/skills/cf-scan.md +0 -12
- package/src/adapters/claude/skills/cf-stats.md +0 -11
- package/src/adapters/claude/skills/cf-validate.md +0 -12
- package/src/core/code-flow/scripts/cf_init.py +0 -829
- package/src/core/code-flow/scripts/cf_inject.py +0 -150
- package/src/core/code-flow/scripts/cf_learn.py +0 -202
- package/src/core/code-flow/scripts/cf_validate.py +0 -340
package/package.json
CHANGED
|
@@ -18,6 +18,16 @@
|
|
|
18
18
|
|
|
19
19
|
## Spec Loading
|
|
20
20
|
This project uses the code-flow layered spec system.
|
|
21
|
-
|
|
21
|
+
|
|
22
|
+
**Auto-inject rule**: Before answering any coding question, you MUST:
|
|
23
|
+
1. Determine domain(s) from the user's question:
|
|
24
|
+
- **frontend**: mentions components, pages, hooks, styles, UI, CSS, React/Vue/Angular, or references .tsx/.jsx/.css/.scss files
|
|
25
|
+
- **backend**: mentions services, API, database, models, logging, or references .py/.go files, SQL, ORM
|
|
26
|
+
2. Read `.code-flow/config.yml` → find matching domain's `specs` list
|
|
27
|
+
3. Read each spec file from `.code-flow/specs/` and apply as constraints
|
|
28
|
+
4. If question spans multiple domains, load all matching specs
|
|
29
|
+
5. If no domain matches, skip spec loading
|
|
30
|
+
|
|
31
|
+
Do NOT ask the user which specs to load — decide automatically based on context.
|
|
22
32
|
|
|
23
33
|
## Learnings
|
|
@@ -0,0 +1,269 @@
|
|
|
1
|
+
# cf-init
|
|
2
|
+
|
|
3
|
+
项目规范体系一键初始化。检测技术栈,生成完整的 .code-flow/ 目录、spec 模板、配置文件和 Hook 配置。
|
|
4
|
+
|
|
5
|
+
## 输入
|
|
6
|
+
|
|
7
|
+
- `/project:cf-init` — 自动检测技术栈
|
|
8
|
+
- `/project:cf-init frontend` — 强制前端项目
|
|
9
|
+
- `/project:cf-init backend` — 强制后端项目
|
|
10
|
+
- `/project:cf-init fullstack` — 强制全栈项目
|
|
11
|
+
|
|
12
|
+
## 执行步骤
|
|
13
|
+
|
|
14
|
+
### 1. 检测技术栈
|
|
15
|
+
|
|
16
|
+
用 Glob 扫描项目根目录:
|
|
17
|
+
|
|
18
|
+
- `package.json` 存在 → 前端项目。用 Read 读取,检查 dependencies 中的 react/vue/@angular/core 确定框架。
|
|
19
|
+
- `pyproject.toml` 或 `requirements.txt` 存在 → Python 后端
|
|
20
|
+
- `go.mod` 存在 → Go 后端
|
|
21
|
+
- 同时存在前后端标识 → 全栈项目
|
|
22
|
+
- 均不存在 → Generic(前后端均生成)
|
|
23
|
+
|
|
24
|
+
如果用户指定了 `frontend|backend|fullstack` 参数,跳过检测直接使用。
|
|
25
|
+
|
|
26
|
+
### 2. 生成 .code-flow/config.yml
|
|
27
|
+
|
|
28
|
+
如果文件不存在,用 Write 生成。如果已存在,用 Read 读取后仅补充缺失的顶层 key。
|
|
29
|
+
|
|
30
|
+
模板内容:
|
|
31
|
+
|
|
32
|
+
```yaml
|
|
33
|
+
version: 1
|
|
34
|
+
|
|
35
|
+
budget:
|
|
36
|
+
total: 2500
|
|
37
|
+
l0_max: 800
|
|
38
|
+
l1_max: 1700
|
|
39
|
+
|
|
40
|
+
inject:
|
|
41
|
+
auto: true
|
|
42
|
+
code_extensions:
|
|
43
|
+
- ".py"
|
|
44
|
+
- ".go"
|
|
45
|
+
- ".ts"
|
|
46
|
+
- ".tsx"
|
|
47
|
+
- ".js"
|
|
48
|
+
- ".jsx"
|
|
49
|
+
- ".java"
|
|
50
|
+
- ".rs"
|
|
51
|
+
- ".rb"
|
|
52
|
+
- ".vue"
|
|
53
|
+
- ".svelte"
|
|
54
|
+
skip_extensions:
|
|
55
|
+
- ".md"
|
|
56
|
+
- ".txt"
|
|
57
|
+
- ".json"
|
|
58
|
+
- ".yml"
|
|
59
|
+
- ".yaml"
|
|
60
|
+
- ".toml"
|
|
61
|
+
- ".lock"
|
|
62
|
+
- ".csv"
|
|
63
|
+
- ".xml"
|
|
64
|
+
- ".svg"
|
|
65
|
+
- ".png"
|
|
66
|
+
- ".jpg"
|
|
67
|
+
skip_paths:
|
|
68
|
+
- "docs/**"
|
|
69
|
+
- "*.config.*"
|
|
70
|
+
- ".code-flow/**"
|
|
71
|
+
- ".claude/**"
|
|
72
|
+
- "node_modules/**"
|
|
73
|
+
- "dist/**"
|
|
74
|
+
- "build/**"
|
|
75
|
+
- ".git/**"
|
|
76
|
+
|
|
77
|
+
path_mapping:
|
|
78
|
+
frontend:
|
|
79
|
+
patterns:
|
|
80
|
+
- "src/components/**"
|
|
81
|
+
- "src/pages/**"
|
|
82
|
+
- "src/hooks/**"
|
|
83
|
+
- "src/styles/**"
|
|
84
|
+
- "**/*.tsx"
|
|
85
|
+
- "**/*.jsx"
|
|
86
|
+
- "**/*.css"
|
|
87
|
+
- "**/*.scss"
|
|
88
|
+
specs:
|
|
89
|
+
- "frontend/directory-structure.md"
|
|
90
|
+
- "frontend/quality-standards.md"
|
|
91
|
+
- "frontend/component-specs.md"
|
|
92
|
+
spec_priority:
|
|
93
|
+
"frontend/directory-structure.md": 1
|
|
94
|
+
"frontend/quality-standards.md": 2
|
|
95
|
+
"frontend/component-specs.md": 3
|
|
96
|
+
backend:
|
|
97
|
+
patterns:
|
|
98
|
+
- "services/**"
|
|
99
|
+
- "api/**"
|
|
100
|
+
- "models/**"
|
|
101
|
+
- "**/*.py"
|
|
102
|
+
- "**/*.go"
|
|
103
|
+
specs:
|
|
104
|
+
- "backend/directory-structure.md"
|
|
105
|
+
- "backend/logging.md"
|
|
106
|
+
- "backend/database.md"
|
|
107
|
+
- "backend/platform-rules.md"
|
|
108
|
+
- "backend/code-quality-performance.md"
|
|
109
|
+
spec_priority:
|
|
110
|
+
"backend/directory-structure.md": 1
|
|
111
|
+
"backend/database.md": 2
|
|
112
|
+
"backend/logging.md": 3
|
|
113
|
+
"backend/code-quality-performance.md": 4
|
|
114
|
+
"backend/platform-rules.md": 5
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
根据检测结果,只保留相关的 path_mapping 条目(仅前端项目删除 backend,仅后端项目删除 frontend)。
|
|
118
|
+
|
|
119
|
+
### 3. 生成 .code-flow/validation.yml
|
|
120
|
+
|
|
121
|
+
如果文件不存在,用 Write 生成:
|
|
122
|
+
|
|
123
|
+
```yaml
|
|
124
|
+
validators:
|
|
125
|
+
- name: "TypeScript 类型检查"
|
|
126
|
+
trigger: "**/*.{ts,tsx}"
|
|
127
|
+
command: "npx tsc --noEmit"
|
|
128
|
+
timeout: 30000
|
|
129
|
+
on_fail: "检查类型定义,参见 specs/frontend/quality-standards.md"
|
|
130
|
+
|
|
131
|
+
- name: "ESLint"
|
|
132
|
+
trigger: "**/*.{ts,tsx,js,jsx}"
|
|
133
|
+
command: "npx eslint {files}"
|
|
134
|
+
timeout: 15000
|
|
135
|
+
on_fail: "运行 npx eslint --fix 自动修复"
|
|
136
|
+
|
|
137
|
+
- name: "Python 类型检查"
|
|
138
|
+
trigger: "**/*.py"
|
|
139
|
+
command: "python3 -m mypy {files}"
|
|
140
|
+
timeout: 30000
|
|
141
|
+
on_fail: "检查类型注解,参见 specs/backend/code-quality-performance.md"
|
|
142
|
+
|
|
143
|
+
- name: "Pytest"
|
|
144
|
+
trigger: "**/*.py"
|
|
145
|
+
command: "python3 -m pytest --tb=short -q"
|
|
146
|
+
timeout: 60000
|
|
147
|
+
on_fail: "测试失败,检查断言和 mock 是否需要更新"
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
根据技术栈只保留相关 validators。
|
|
151
|
+
|
|
152
|
+
### 4. 生成 spec 文件
|
|
153
|
+
|
|
154
|
+
在 `.code-flow/specs/` 下,按检测到的技术栈生成 spec 模板。每个 spec 遵循统一格式:
|
|
155
|
+
|
|
156
|
+
```markdown
|
|
157
|
+
# [规范名称]
|
|
158
|
+
|
|
159
|
+
## Rules
|
|
160
|
+
- 规则1
|
|
161
|
+
|
|
162
|
+
## Patterns
|
|
163
|
+
- 推荐模式
|
|
164
|
+
|
|
165
|
+
## Anti-Patterns
|
|
166
|
+
- 禁止模式
|
|
167
|
+
|
|
168
|
+
## Learnings
|
|
169
|
+
```
|
|
170
|
+
|
|
171
|
+
前端项目生成:
|
|
172
|
+
- `.code-flow/specs/frontend/directory-structure.md`
|
|
173
|
+
- `.code-flow/specs/frontend/quality-standards.md`
|
|
174
|
+
- `.code-flow/specs/frontend/component-specs.md`
|
|
175
|
+
|
|
176
|
+
后端项目生成:
|
|
177
|
+
- `.code-flow/specs/backend/directory-structure.md`
|
|
178
|
+
- `.code-flow/specs/backend/logging.md`
|
|
179
|
+
- `.code-flow/specs/backend/database.md`
|
|
180
|
+
- `.code-flow/specs/backend/platform-rules.md`
|
|
181
|
+
- `.code-flow/specs/backend/code-quality-performance.md`
|
|
182
|
+
|
|
183
|
+
**已存在的 spec 文件不覆盖**。
|
|
184
|
+
|
|
185
|
+
### 5. 生成 CLAUDE.md
|
|
186
|
+
|
|
187
|
+
如果 CLAUDE.md 不存在,用 Write 生成 L0 模板:
|
|
188
|
+
|
|
189
|
+
```markdown
|
|
190
|
+
# Project Guidelines
|
|
191
|
+
|
|
192
|
+
## Team Identity
|
|
193
|
+
- Team: [team name]
|
|
194
|
+
- Project: [project name]
|
|
195
|
+
- Language: [primary language]
|
|
196
|
+
|
|
197
|
+
## Core Principles
|
|
198
|
+
- All changes must include tests
|
|
199
|
+
- Single responsibility per function (<= 50 lines)
|
|
200
|
+
- No loose typing or silent exception handling
|
|
201
|
+
- Handle errors explicitly
|
|
202
|
+
|
|
203
|
+
## Forbidden Patterns
|
|
204
|
+
- Hard-coded secrets or credentials
|
|
205
|
+
- Unparameterized SQL
|
|
206
|
+
- Network calls inside tight loops
|
|
207
|
+
|
|
208
|
+
## Spec Loading
|
|
209
|
+
This project uses the code-flow layered spec system.
|
|
210
|
+
Specs live in .code-flow/specs/ and are injected on demand.
|
|
211
|
+
|
|
212
|
+
## Learnings
|
|
213
|
+
```
|
|
214
|
+
|
|
215
|
+
如果 CLAUDE.md 已存在,用 Read 读取后仅补充缺失的 `##` 段落(不覆盖已有内容)。展示 diff 供用户确认。
|
|
216
|
+
|
|
217
|
+
### 6. 生成 .claude/settings.local.json Hook 配置
|
|
218
|
+
|
|
219
|
+
用 Read 检查是否存在。如果不存在,用 Write 生成:
|
|
220
|
+
|
|
221
|
+
```json
|
|
222
|
+
{
|
|
223
|
+
"hooks": {
|
|
224
|
+
"PreToolUse": [
|
|
225
|
+
{
|
|
226
|
+
"matcher": "Edit|Write|MultiEdit",
|
|
227
|
+
"hooks": [
|
|
228
|
+
{
|
|
229
|
+
"type": "command",
|
|
230
|
+
"command": "python3 .code-flow/scripts/cf_inject_hook.py",
|
|
231
|
+
"timeout": 5
|
|
232
|
+
}
|
|
233
|
+
]
|
|
234
|
+
}
|
|
235
|
+
],
|
|
236
|
+
"SessionStart": [
|
|
237
|
+
{
|
|
238
|
+
"hooks": [
|
|
239
|
+
{
|
|
240
|
+
"type": "command",
|
|
241
|
+
"command": "python3 .code-flow/scripts/cf_session_hook.py"
|
|
242
|
+
}
|
|
243
|
+
]
|
|
244
|
+
}
|
|
245
|
+
]
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
```
|
|
249
|
+
|
|
250
|
+
如果已存在,用 Read 读取 JSON,仅合并 `hooks` 字段中缺失的事件条目,保留其他配置(如 permissions)不变。用 Write 回写。
|
|
251
|
+
|
|
252
|
+
### 7. 安装 pyyaml
|
|
253
|
+
|
|
254
|
+
用 Bash 执行:
|
|
255
|
+
|
|
256
|
+
```bash
|
|
257
|
+
python3 -m pip install pyyaml
|
|
258
|
+
```
|
|
259
|
+
|
|
260
|
+
成功 → 继续。失败 → 输出 warning("请手动安装: pip install pyyaml"),不阻塞。
|
|
261
|
+
|
|
262
|
+
### 8. 输出摘要
|
|
263
|
+
|
|
264
|
+
输出以下信息:
|
|
265
|
+
- 检测到的技术栈
|
|
266
|
+
- 已生成/跳过的文件列表
|
|
267
|
+
- 各 spec 文件的 token 估算(字符数 / 4)
|
|
268
|
+
- Hook 配置状态确认
|
|
269
|
+
- 提醒用户填充 spec 文件的具体规范内容
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
# cf-inject
|
|
2
|
+
|
|
3
|
+
强制重新注入指定领域的编码规范(通常不需要手动调用)。
|
|
4
|
+
|
|
5
|
+
## 自动注入机制
|
|
6
|
+
|
|
7
|
+
本项目的规范注入是**全自动**的,通过两层机制保障:
|
|
8
|
+
|
|
9
|
+
1. **CLAUDE.md 指令**(主要):Claude 根据用户提问内容自动判断领域,读取 `.code-flow/config.yml` 和对应 spec 文件,作为约束应用
|
|
10
|
+
2. **PreToolUse Hook**(安全网):编辑代码文件时 Hook 自动触发,注入匹配领域的 specs
|
|
11
|
+
|
|
12
|
+
正常情况下**无需手动调用**此命令。
|
|
13
|
+
|
|
14
|
+
## 何时使用
|
|
15
|
+
|
|
16
|
+
- 需要强制刷新已注入的规范(如 spec 文件刚被修改)
|
|
17
|
+
- 想要预览某个领域的完整规范内容
|
|
18
|
+
- 自动注入未生效时的排查手段
|
|
19
|
+
|
|
20
|
+
## 输入
|
|
21
|
+
|
|
22
|
+
- `/project:cf-inject frontend` — 强制加载前端全部 specs
|
|
23
|
+
- `/project:cf-inject backend` — 强制加载后端全部 specs
|
|
24
|
+
|
|
25
|
+
## 执行步骤
|
|
26
|
+
|
|
27
|
+
1. 用 Read 读取 `.code-flow/config.yml`,获取指定领域的 `specs` 列表
|
|
28
|
+
2. 用 Read 逐个读取 `.code-flow/specs/` 下的匹配文件
|
|
29
|
+
3. 将规范内容直接输出到对话中,格式:
|
|
30
|
+
|
|
31
|
+
```
|
|
32
|
+
## Active Specs (manual inject)
|
|
33
|
+
|
|
34
|
+
### [spec-path]
|
|
35
|
+
[spec 内容]
|
|
36
|
+
|
|
37
|
+
---
|
|
38
|
+
以上规范是本次开发的约束条件,生成代码必须遵循。
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
4. 用 Write 更新 `.code-flow/.inject-state`,防止 Hook 重复注入
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
# cf-learn
|
|
2
|
+
|
|
3
|
+
自动扫描项目配置文件和代码模式,提取隐含的编码约束和团队规范,呈现给用户确认后写入 CLAUDE.md 或 spec 文件。
|
|
4
|
+
|
|
5
|
+
## 输入
|
|
6
|
+
|
|
7
|
+
- `/project:cf-learn` — 全量扫描
|
|
8
|
+
- `/project:cf-learn frontend` — 仅扫描前端相关
|
|
9
|
+
- `/project:cf-learn backend` — 仅扫描后端相关
|
|
10
|
+
|
|
11
|
+
## 执行步骤
|
|
12
|
+
|
|
13
|
+
### 1. 扫描项目配置文件
|
|
14
|
+
|
|
15
|
+
用 Glob 查找以下配置文件(存在则 Read 读取内容):
|
|
16
|
+
|
|
17
|
+
**前端配置**:
|
|
18
|
+
- `.eslintrc*` / `eslint.config.*` — 提取 lint 规则(no-any、import 排序、命名规范等)
|
|
19
|
+
- `tsconfig.json` — 提取 strict 模式、path alias、target 等关键配置
|
|
20
|
+
- `.prettierrc*` / `prettier.config.*` — 提取格式化规则(缩进、引号、分号)
|
|
21
|
+
- `tailwind.config.*` — 提取自定义 theme、spacing 规则
|
|
22
|
+
- `next.config.*` / `nuxt.config.*` / `vite.config.*` — 提取框架特定约束
|
|
23
|
+
- `jest.config.*` / `vitest.config.*` — 提取测试配置(覆盖率阈值等)
|
|
24
|
+
|
|
25
|
+
**后端配置**:
|
|
26
|
+
- `pyproject.toml` — 提取 ruff/mypy/pytest 配置、Python 版本要求
|
|
27
|
+
- `setup.cfg` / `tox.ini` — 提取测试和 lint 配置
|
|
28
|
+
- `.golangci.yml` — 提取 Go lint 规则
|
|
29
|
+
- `Makefile` — 提取构建和测试命令
|
|
30
|
+
- `Dockerfile` / `docker-compose.yml` — 提取运行时约束
|
|
31
|
+
|
|
32
|
+
**通用配置**:
|
|
33
|
+
- `.github/workflows/*.yml` / `.gitlab-ci.yml` — 提取 CI 检查步骤(哪些 lint/test 是必须通过的)
|
|
34
|
+
- `.editorconfig` — 提取编辑器统一配置
|
|
35
|
+
- `.gitignore` — 推断项目结构(哪些目录被排除)
|
|
36
|
+
- `package.json` 的 scripts 字段 — 提取常用命令
|
|
37
|
+
|
|
38
|
+
### 2. 扫描代码模式
|
|
39
|
+
|
|
40
|
+
用 Grep 在项目代码中搜索以下模式,提取隐含规范:
|
|
41
|
+
|
|
42
|
+
- 错误处理模式:`try/except`、`catch`、自定义 Error 类的使用方式
|
|
43
|
+
- 日志模式:使用的日志库和格式(structlog、winston、pino 等)
|
|
44
|
+
- 测试模式:测试框架、断言风格、mock 方式
|
|
45
|
+
- 导入规范:absolute vs relative imports、barrel exports
|
|
46
|
+
- 命名模式:文件命名(kebab-case / PascalCase)、变量命名风格
|
|
47
|
+
|
|
48
|
+
### 3. 综合分析并生成候选学习点
|
|
49
|
+
|
|
50
|
+
将扫描结果综合分析,提取 **具体的、可执行的** 编码约束。每个学习点格式:
|
|
51
|
+
|
|
52
|
+
```
|
|
53
|
+
[来源] 约束描述
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
例如:
|
|
57
|
+
```
|
|
58
|
+
[tsconfig.json] strict 模式已启用,禁止 implicit any
|
|
59
|
+
[.eslintrc] import 必须按 builtin → external → internal 排序
|
|
60
|
+
[pyproject.toml] Python 最低版本 3.11,可使用 match/case 语法
|
|
61
|
+
[CI: lint.yml] PR 必须通过 ruff check + mypy --strict
|
|
62
|
+
[代码模式] 错误处理统一使用自定义 AppError 类,不使用裸 Exception
|
|
63
|
+
[Makefile] 测试命令为 make test,覆盖率阈值 80%
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
**过滤规则**:
|
|
67
|
+
- 跳过已在 CLAUDE.md 或 spec 文件中记录的规范(避免重复)
|
|
68
|
+
- 只提取对 AI 生成代码有实际影响的约束
|
|
69
|
+
- 忽略纯格式化规则(如果有 Prettier/formatter 自动处理)
|
|
70
|
+
|
|
71
|
+
### 4. 呈现给用户确认
|
|
72
|
+
|
|
73
|
+
将候选学习点分组展示:
|
|
74
|
+
|
|
75
|
+
```
|
|
76
|
+
扫描发现以下未记录的编码约束:
|
|
77
|
+
|
|
78
|
+
全局约束(建议写入 CLAUDE.md):
|
|
79
|
+
1. [x] [tsconfig.json] strict 模式已启用,禁止 implicit any
|
|
80
|
+
2. [x] [CI] PR 必须通过 lint + type check
|
|
81
|
+
3. [ ] [.editorconfig] 缩进使用 2 空格
|
|
82
|
+
|
|
83
|
+
前端约束(建议写入 specs/frontend/):
|
|
84
|
+
4. [x] [.eslintrc] React hooks 必须遵循 exhaustive-deps 规则
|
|
85
|
+
5. [x] [代码模式] 组件文件使用 PascalCase 命名
|
|
86
|
+
|
|
87
|
+
后端约束(建议写入 specs/backend/):
|
|
88
|
+
6. [x] [pyproject.toml] 使用 ruff 替代 flake8/isort
|
|
89
|
+
7. [x] [代码模式] 所有 API handler 使用 async def
|
|
90
|
+
|
|
91
|
+
确认要写入的条目(输入编号,或 all 全部写入,或 none 跳过):
|
|
92
|
+
```
|
|
93
|
+
|
|
94
|
+
等待用户确认。
|
|
95
|
+
|
|
96
|
+
### 5. 写入确认的条目
|
|
97
|
+
|
|
98
|
+
根据用户选择:
|
|
99
|
+
|
|
100
|
+
- **全局约束** → 用 Edit 追加到 `CLAUDE.md` 的 `## Learnings` 段落,格式:`- [YYYY-MM-DD] 内容`
|
|
101
|
+
- **前端约束** → 询问用户写入哪个 spec 文件,用 Edit 追加到对应 spec 的 `## Learnings` 段落
|
|
102
|
+
- **后端约束** → 同上
|
|
103
|
+
|
|
104
|
+
每条写入后输出确认。
|
|
105
|
+
|
|
106
|
+
### 6. 输出摘要
|
|
107
|
+
|
|
108
|
+
```
|
|
109
|
+
已写入 N 条学习点:
|
|
110
|
+
- CLAUDE.md: +3 条
|
|
111
|
+
- specs/frontend/quality-standards.md: +2 条
|
|
112
|
+
- specs/backend/code-quality-performance.md: +2 条
|
|
113
|
+
Token 变化: CLAUDE.md 138 → 195 tokens
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
## 异常处理
|
|
117
|
+
|
|
118
|
+
- 无配置文件可扫描 → 提示项目可能未初始化,建议手动添加
|
|
119
|
+
- 未发现新约束 → 输出"未发现未记录的约束,当前规范已覆盖项目配置"
|
|
120
|
+
- `.code-flow/` 不存在 → 提示运行 `/project:cf-init`
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
# cf-scan
|
|
2
|
+
|
|
3
|
+
审计规范文件的 token 分布,检测冗余和过时内容,输出优化建议。
|
|
4
|
+
|
|
5
|
+
## 输入
|
|
6
|
+
|
|
7
|
+
- `/project:cf-scan` — 完整审计
|
|
8
|
+
- `/project:cf-scan --json` — 仅输出原始 JSON
|
|
9
|
+
- `/project:cf-scan --only-issues` — 仅显示有问题的文件
|
|
10
|
+
- `/project:cf-scan --limit=N` — 限制输出行数
|
|
11
|
+
|
|
12
|
+
## 执行步骤
|
|
13
|
+
|
|
14
|
+
### 1. 调用 Python 脚本
|
|
15
|
+
|
|
16
|
+
用 Bash 执行:
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
python3 .code-flow/scripts/cf_scan.py [--json] [--only-issues] [--limit=N]
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
将用户传入的参数原样透传。
|
|
23
|
+
|
|
24
|
+
### 2. 解析输出
|
|
25
|
+
|
|
26
|
+
解析 stdout 的 JSON 输出,格式如下:
|
|
27
|
+
|
|
28
|
+
```json
|
|
29
|
+
{
|
|
30
|
+
"files": [
|
|
31
|
+
{"path": "CLAUDE.md", "tokens": 650, "percent": "26%", "issues": []},
|
|
32
|
+
{"path": "specs/frontend/component-specs.md", "tokens": 420, "percent": "17%", "issues": ["冗余: '结构化日志' 3处重复"]}
|
|
33
|
+
],
|
|
34
|
+
"total_tokens": 2150,
|
|
35
|
+
"budget": 2500,
|
|
36
|
+
"warnings": []
|
|
37
|
+
}
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
### 3. 格式化输出
|
|
41
|
+
|
|
42
|
+
将 JSON 格式化为人类可读的表格:
|
|
43
|
+
|
|
44
|
+
| 文件 | Tokens | 占比 | 问题 |
|
|
45
|
+
|------|--------|------|------|
|
|
46
|
+
| CLAUDE.md | ~650 | 26% | - |
|
|
47
|
+
| specs/frontend/component-specs.md | ~420 | 17% | - |
|
|
48
|
+
| **合计** | **~2150** | **/ 2500** | |
|
|
49
|
+
|
|
50
|
+
如有 warnings,在表格下方输出优化建议。
|
|
51
|
+
|
|
52
|
+
## 异常处理
|
|
53
|
+
|
|
54
|
+
- `.code-flow/` 不存在 → 提示运行 `/project:cf-init`
|
|
55
|
+
- Python 脚本执行失败 → 输出错误信息,建议检查 Python 环境和 pyyaml 安装
|
|
56
|
+
- spec 文件全为空模板 → 输出 warning,提示先填充规范内容
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
# cf-stats
|
|
2
|
+
|
|
3
|
+
统计规范体系的 token 使用情况,包括各文件分布和预算利用率。
|
|
4
|
+
|
|
5
|
+
## 输入
|
|
6
|
+
|
|
7
|
+
- `/project:cf-stats` — 完整统计
|
|
8
|
+
- `/project:cf-stats --human` — 人类可读格式
|
|
9
|
+
- `/project:cf-stats --domain=frontend` — 仅统计指定领域
|
|
10
|
+
|
|
11
|
+
## 执行步骤
|
|
12
|
+
|
|
13
|
+
### 1. 调用 Python 脚本
|
|
14
|
+
|
|
15
|
+
用 Bash 执行:
|
|
16
|
+
|
|
17
|
+
```bash
|
|
18
|
+
python3 .code-flow/scripts/cf_stats.py [--human] [--domain=frontend]
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
将用户传入的参数原样透传。
|
|
22
|
+
|
|
23
|
+
### 2. 解析输出
|
|
24
|
+
|
|
25
|
+
解析 stdout 的 JSON 输出,格式如下:
|
|
26
|
+
|
|
27
|
+
```json
|
|
28
|
+
{
|
|
29
|
+
"l0": {"file": "CLAUDE.md", "tokens": 650, "budget": 800},
|
|
30
|
+
"l1": {
|
|
31
|
+
"frontend": [
|
|
32
|
+
{"path": "frontend/directory-structure.md", "tokens": 180},
|
|
33
|
+
{"path": "frontend/quality-standards.md", "tokens": 150}
|
|
34
|
+
],
|
|
35
|
+
"backend": [
|
|
36
|
+
{"path": "backend/database.md", "tokens": 200}
|
|
37
|
+
]
|
|
38
|
+
},
|
|
39
|
+
"total_tokens": 1580,
|
|
40
|
+
"total_budget": 2500,
|
|
41
|
+
"utilization": "63%"
|
|
42
|
+
}
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
### 3. 格式化输出
|
|
46
|
+
|
|
47
|
+
将 JSON 格式化为人类可读的统计信息:
|
|
48
|
+
|
|
49
|
+
```
|
|
50
|
+
L0 (CLAUDE.md): ~650 / 800 tokens
|
|
51
|
+
|
|
52
|
+
L1 Frontend:
|
|
53
|
+
- directory-structure.md: ~180 tokens
|
|
54
|
+
- quality-standards.md: ~150 tokens
|
|
55
|
+
|
|
56
|
+
L1 Backend:
|
|
57
|
+
- database.md: ~200 tokens
|
|
58
|
+
|
|
59
|
+
Total: ~1580 / 2500 tokens (63%)
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
## 异常处理
|
|
63
|
+
|
|
64
|
+
- `.code-flow/` 不存在 → 提示运行 `/project:cf-init`
|
|
65
|
+
- Python 脚本执行失败 → 输出错误信息,建议检查 Python 环境
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
# cf-validate
|
|
2
|
+
|
|
3
|
+
根据变更文件自动匹配并执行验证规则(测试、类型检查、lint),失败时自动尝试修复。
|
|
4
|
+
|
|
5
|
+
## 输入
|
|
6
|
+
|
|
7
|
+
- `/project:cf-validate` — 基于 git diff 自动获取变更文件
|
|
8
|
+
- `/project:cf-validate src/Foo.tsx` — 验证指定文件
|
|
9
|
+
- `/project:cf-validate --files=src/a.ts,src/b.ts` — 验证多个文件
|
|
10
|
+
|
|
11
|
+
## 执行步骤
|
|
12
|
+
|
|
13
|
+
### 1. 获取变更文件列表
|
|
14
|
+
|
|
15
|
+
用 Bash 执行:
|
|
16
|
+
|
|
17
|
+
```bash
|
|
18
|
+
git diff --name-only HEAD
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
如果用户指定了文件路径,使用用户指定的文件。如果无变更文件,输出"无变更需要验证"。
|
|
22
|
+
|
|
23
|
+
### 2. 读取验证规则
|
|
24
|
+
|
|
25
|
+
用 Read 读取 `.code-flow/validation.yml`。如果不存在,尝试读取 `package.json` 中的 `scripts.test` 和 `scripts.lint` 作为回退。
|
|
26
|
+
|
|
27
|
+
validation.yml 格式:
|
|
28
|
+
|
|
29
|
+
```yaml
|
|
30
|
+
validators:
|
|
31
|
+
- name: "验证器名称"
|
|
32
|
+
trigger: "**/*.{ts,tsx}"
|
|
33
|
+
command: "npx tsc --noEmit"
|
|
34
|
+
timeout: 30000
|
|
35
|
+
on_fail: "修复建议"
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
### 3. 匹配并执行验证
|
|
39
|
+
|
|
40
|
+
对每条验证规则:
|
|
41
|
+
- 将 `trigger` glob 与变更文件列表做匹配
|
|
42
|
+
- 匹配到 → 用 Bash 执行 `command`(将 `{files}` 替换为匹配到的文件路径,**每个路径用单引号包裹防止注入**)
|
|
43
|
+
- 未匹配 → 跳过该规则
|
|
44
|
+
|
|
45
|
+
每条命令使用对应的 `timeout` 值(毫秒)。
|
|
46
|
+
|
|
47
|
+
### 4. 汇总结果
|
|
48
|
+
|
|
49
|
+
- **全部通过** → 输出确认信息
|
|
50
|
+
- **有失败** → 展示每个失败项的:
|
|
51
|
+
- 验证器名称
|
|
52
|
+
- 执行的命令
|
|
53
|
+
- 错误输出(截取关键部分)
|
|
54
|
+
- `on_fail` 修复建议
|
|
55
|
+
|
|
56
|
+
### 5. 自动修复
|
|
57
|
+
|
|
58
|
+
对于失败的验证项,根据错误输出分析问题根因,自动尝试修复代码。修复后提示用户再次运行 `/project:cf-validate` 确认。
|
|
59
|
+
|
|
60
|
+
## 安全设计
|
|
61
|
+
|
|
62
|
+
- 对 `{files}` 中的每个文件路径用单引号包裹,防止 shell 注入
|
|
63
|
+
- 仅接受 `git diff` 输出的文件路径或用户显式指定的路径
|
|
64
|
+
- 用户指定的路径必须位于项目根目录内
|
|
65
|
+
|
|
66
|
+
## 异常处理
|
|
67
|
+
|
|
68
|
+
- validation.yml 不存在 → 尝试检测 package.json scripts 中的 test/lint 命令
|
|
69
|
+
- 命令执行超时 → 输出超时提示,建议增大 timeout 或缩小验证范围
|
|
70
|
+
- 命令不存在 → 提示安装依赖(如 `pip install mypy`)
|
|
71
|
+
- 无变更文件 → 输出"无变更需要验证"
|
package/src/cli.js
CHANGED
|
@@ -69,18 +69,15 @@ function runInit() {
|
|
|
69
69
|
copyFileIfMissing(path.join(adaptersDir, 'claude', 'CLAUDE.md'), path.join(cwd, 'CLAUDE.md'));
|
|
70
70
|
copyDirRecursive(path.join(adaptersDir, 'claude'), path.join(cwd, '.claude'));
|
|
71
71
|
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
{
|
|
76
|
-
);
|
|
77
|
-
|
|
78
|
-
if (result.error) {
|
|
79
|
-
process.stderr.write(`Error: ${result.error.message}\n`);
|
|
80
|
-
process.exit(1);
|
|
72
|
+
// Clean up legacy .claude/skills/ if it exists
|
|
73
|
+
const legacySkills = path.join(cwd, '.claude', 'skills');
|
|
74
|
+
if (fs.existsSync(legacySkills)) {
|
|
75
|
+
fs.rmSync(legacySkills, { recursive: true });
|
|
81
76
|
}
|
|
82
77
|
|
|
83
|
-
process.
|
|
78
|
+
process.stdout.write('code-flow initialized.\n');
|
|
79
|
+
process.stdout.write('Run /project:cf-init in Claude Code to complete setup.\n');
|
|
80
|
+
process.exit(0);
|
|
84
81
|
}
|
|
85
82
|
|
|
86
83
|
const args = process.argv.slice(2);
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
# cf-init
|
|
2
|
-
|
|
3
|
-
初始化 code-flow 规范体系(目录、配置、spec、skill、hooks)。
|
|
4
|
-
|
|
5
|
-
## Usage
|
|
6
|
-
- `/cf-init`
|
|
7
|
-
- `/cf-init frontend|backend|fullstack`
|
|
8
|
-
|
|
9
|
-
## Command
|
|
10
|
-
- `python3 .code-flow/scripts/cf_init.py [frontend|backend|fullstack]`
|
|
11
|
-
|
|
12
|
-
## Notes
|
|
13
|
-
- 依赖 Python 3.9+ 与 pyyaml(脚本会尝试自动安装)。
|