canicode 0.10.0 → 0.10.2
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/README.md +5 -3
- package/dist/cli/index.js +39 -3
- package/dist/cli/index.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/mcp/server.js +1 -1
- package/dist/mcp/server.js.map +1 -1
- package/package.json +1 -1
- package/skills/canicode-gotchas/SKILL.md +45 -23
- package/skills/canicode-roundtrip/SKILL.md +54 -8
package/package.json
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: canicode-gotchas
|
|
3
|
-
description:
|
|
3
|
+
description: Gotcha survey workflow plus accumulating per-design answers — one Workflow region on top, numbered sections appended per Figma design
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
# CanICode Gotchas -- Design Gotcha Survey & Skill Writer
|
|
7
7
|
|
|
8
|
-
Run a gotcha survey on a Figma design to identify implementation pitfalls, collect developer answers, and
|
|
8
|
+
Run a gotcha survey on a Figma design to identify implementation pitfalls, collect developer answers, and upsert them into this skill file so code generation agents can reference them automatically. The file has two regions: the **Workflow** below (installed by `canicode init`, never overwritten) and the **Collected Gotchas** region at the bottom (one numbered section per design, replaced in place on re-runs).
|
|
9
9
|
|
|
10
10
|
## Prerequisites
|
|
11
11
|
|
|
@@ -38,7 +38,7 @@ Either channel returns:
|
|
|
38
38
|
|
|
39
39
|
If `isReadyForCodeGen` is `true` or `questions` is empty:
|
|
40
40
|
- Tell the user: "This design scored **{designGrade}** and is ready for code generation — no gotchas to resolve."
|
|
41
|
-
- Do NOT write
|
|
41
|
+
- Do NOT write to the skill file.
|
|
42
42
|
- Stop here.
|
|
43
43
|
|
|
44
44
|
### Step 3: Present questions to the user
|
|
@@ -59,41 +59,54 @@ Wait for the user's answer before moving to the next question. The user may:
|
|
|
59
59
|
- Say "skip" to skip a question
|
|
60
60
|
- Say "n/a" if the question is not applicable
|
|
61
61
|
|
|
62
|
-
### Step 4:
|
|
62
|
+
### Step 4: Upsert the gotcha section
|
|
63
63
|
|
|
64
|
-
After collecting all answers,
|
|
64
|
+
After collecting all answers, **upsert** this design's section into the `# Collected Gotchas` region at the bottom of this file:
|
|
65
65
|
|
|
66
66
|
```
|
|
67
67
|
.claude/skills/canicode-gotchas/SKILL.md
|
|
68
68
|
```
|
|
69
69
|
|
|
70
|
-
This file goes in the **user's project** (current working directory), NOT in the canicode repo.
|
|
70
|
+
This file goes in the **user's project** (current working directory), NOT in the canicode repo. The Workflow region above **must never be modified** — only the `# Collected Gotchas` region below is touched.
|
|
71
71
|
|
|
72
|
-
|
|
72
|
+
#### Step 4a: Compute `designKey`
|
|
73
73
|
|
|
74
|
-
|
|
74
|
+
`designKey` uniquely identifies the design so re-running on the same URL replaces the existing section in place. Parse it from the survey input:
|
|
75
75
|
|
|
76
|
-
|
|
76
|
+
- **Figma URL** — extract `fileKey` and `nodeId` from the URL and join them as `<fileKey>#<nodeId>`. Example: `https://figma.com/design/abc123XYZ/My-File?node-id=42-100` → `designKey = "abc123XYZ#42:100"` (convert `-` to `:` in nodeId, the same normalization the Figma MCP uses). Drop any other query-string parameters — only `node-id` matters for the key.
|
|
77
|
+
- **Fixture path** — use the absolute path, e.g. `/Users/me/project/fixtures/simple.json`.
|
|
77
78
|
|
|
78
|
-
|
|
79
|
-
---
|
|
80
|
-
name: canicode-gotchas
|
|
81
|
-
description: Design gotcha answers for {designName} — reference during code generation
|
|
82
|
-
---
|
|
79
|
+
Do **not** use the raw survey input URL as the key: trailing query parameters (`?t=...`, `?mode=...`) break string matching on re-runs.
|
|
83
80
|
|
|
84
|
-
|
|
81
|
+
#### Step 4b: Read the existing file and locate the target section
|
|
85
82
|
|
|
86
|
-
|
|
83
|
+
1. Read `.claude/skills/canicode-gotchas/SKILL.md` if it exists.
|
|
84
|
+
2. Detect the file's state using the two structural markers that uniquely identify each case — the YAML frontmatter (present on every `canicode init` install) and the `# Collected Gotchas` heading (present on every post-#340 install):
|
|
85
|
+
- **File missing** → tell the user to run `canicode init` first, then re-invoke this skill. Stop here.
|
|
86
|
+
- **File has YAML frontmatter AND a `# Collected Gotchas` heading** (the default shipped shape since #340) → proceed to step 3 below.
|
|
87
|
+
- **File has YAML frontmatter but no `# Collected Gotchas` heading** (an older workflow install, or a user-edited workflow that dropped the trailing heading) → preserve everything above unchanged and append a new `# Collected Gotchas` heading at the bottom, then proceed to step 3.
|
|
88
|
+
- **File missing the YAML frontmatter** (a pre-#340 single-design clobber — the old overwrite rewrote the frontmatter's `description` to the per-design variant, so a well-formed canicode frontmatter is the cleanest discriminator) → **do not attempt to reconstruct the workflow inline**. Tell the user: "Your gotchas SKILL.md looks like the pre-#340 single-design format. Run `canicode init --force` to restore the workflow, then re-run this survey — your answers will land in a clean numbered section." Stop here.
|
|
89
|
+
3. Walk the existing `## #NNN — ...` sections under `# Collected Gotchas` and look for one whose `- **Design key**:` bullet matches the `designKey` from Step 4a. Substring match against the bullet value is sufficient.
|
|
90
|
+
- **Found** → replace that section in place. **Preserve its `#NNN` number** so external references (downstream skills, user notes) remain stable.
|
|
91
|
+
- **Not found** → append a new section at the bottom of the region. `#NNN = (highest existing number) + 1`, zero-padded to three digits. Never reuse a number that appeared earlier and was deleted; numbering is monotonic.
|
|
87
92
|
|
|
88
|
-
|
|
93
|
+
The Workflow region above must never be touched. Do NOT copy Workflow prose into the per-design section; the section only carries metadata + gotcha answers.
|
|
94
|
+
|
|
95
|
+
## Output Template
|
|
96
|
+
|
|
97
|
+
Each per-design section in the `# Collected Gotchas` region has this exact shape:
|
|
98
|
+
|
|
99
|
+
````markdown
|
|
100
|
+
## #NNN — {designName} — {YYYY-MM-DD}
|
|
89
101
|
|
|
90
102
|
- **Figma URL**: {figmaUrl}
|
|
103
|
+
- **Design key**: {designKey}
|
|
91
104
|
- **Grade**: {designGrade}
|
|
92
105
|
- **Analyzed at**: {analyzedAt}
|
|
93
106
|
|
|
94
|
-
|
|
107
|
+
### Gotchas
|
|
95
108
|
|
|
96
|
-
|
|
109
|
+
#### {ruleId} — {nodeName}
|
|
97
110
|
|
|
98
111
|
- **Severity**: {severity}
|
|
99
112
|
- **Node ID**: {nodeId}
|
|
@@ -108,8 +121,11 @@ Collected from canicode gotcha survey. Reference these answers when implementing
|
|
|
108
121
|
|
|
109
122
|
| Field | Source |
|
|
110
123
|
|-------|--------|
|
|
124
|
+
| `NNN` | `sectionNumber` — zero-padded three-digit index. Preserved on re-run, incremented on append. |
|
|
111
125
|
| `designName` | Figma file name or fixture name from the input |
|
|
126
|
+
| `YYYY-MM-DD` | Today's date (the day you are running the survey) |
|
|
112
127
|
| `figmaUrl` | The input URL or fixture path provided by the user |
|
|
128
|
+
| `designKey` | `<fileKey>#<nodeId>` for Figma URLs, absolute path for fixtures (see Step 4a) |
|
|
113
129
|
| `designGrade` | `designGrade` from gotcha-survey response |
|
|
114
130
|
| `analyzedAt` | Current timestamp (ISO 8601) |
|
|
115
131
|
| `ruleId` | `ruleId` from each question |
|
|
@@ -122,7 +138,7 @@ Collected from canicode gotcha survey. Reference these answers when implementing
|
|
|
122
138
|
|
|
123
139
|
### Skipped questions
|
|
124
140
|
|
|
125
|
-
If the user skipped a question or said "n/a", still include it in the
|
|
141
|
+
If the user skipped a question or said "n/a", still include it in the section with:
|
|
126
142
|
|
|
127
143
|
```markdown
|
|
128
144
|
- **Answer**: _(skipped)_
|
|
@@ -132,7 +148,13 @@ This ensures the code generation agent knows the gotcha exists even if no answer
|
|
|
132
148
|
|
|
133
149
|
## Edge Cases
|
|
134
150
|
|
|
135
|
-
- **No questions returned**: The design is ready for code generation. Inform the user and stop (Step 2).
|
|
136
|
-
- **
|
|
151
|
+
- **No questions returned**: The design is ready for code generation. Inform the user and stop (Step 2). Do not touch the file.
|
|
152
|
+
- **Re-run on the same design**: Replace that design's section in place (matched by `Design key`) — preserve the original `#NNN` number. Do NOT append a duplicate.
|
|
153
|
+
- **Re-run on a different design**: Append a new section with the next `#NNN`. Prior designs' sections are untouched.
|
|
154
|
+
- **Workflow region**: Never modified. If you notice the Workflow region has been edited by the user, leave their edits alone — only the `# Collected Gotchas` region is under skill control.
|
|
155
|
+
- **Pre-#340 clobbered file** (the YAML frontmatter was rewritten to a per-design variant, so the canonical `canicode-gotchas` frontmatter is missing): tell the user to run `canicode init --force` to restore the workflow, then re-run the survey. The prior single-design content cannot be automatically migrated into a `## #001` section — the user re-runs and gets a clean section.
|
|
137
156
|
- **MCP tool not available**: Fall back to `npx canicode gotcha-survey <input> --json` — the CLI returns the same `GotchaSurvey` shape. If the CLI is also unavailable (e.g. no node runtime), tell the user to install the canicode MCP server or the `canicode` npm package (see Prerequisites).
|
|
138
|
-
- **Partial answers**: If the user stops mid-survey,
|
|
157
|
+
- **Partial answers**: If the user stops mid-survey, upsert the section with answers collected so far. Mark remaining questions as _(skipped)_.
|
|
158
|
+
- **Manual section deletion**: If the user deletes a middle section by hand, do not renumber existing sections. The next new section still gets `(highest existing number) + 1`; numeric gaps are acceptable (same pattern as `.claude/docs/ADR.md`).
|
|
159
|
+
|
|
160
|
+
# Collected Gotchas
|
|
@@ -18,6 +18,18 @@ Orchestrate the full design-to-code roundtrip: analyze a Figma design for readin
|
|
|
18
18
|
|
|
19
19
|
## Workflow
|
|
20
20
|
|
|
21
|
+
### Step 0: Verify Figma MCP tools are loaded
|
|
22
|
+
|
|
23
|
+
Before Step 1, verify that `use_figma` is callable in **this** session — not merely listed in `.mcp.json`. Newly registered MCP servers (e.g. via `claude mcp add -s project -t http figma https://mcp.figma.com/mcp`) require a Claude Code restart to load their tools; reading `.mcp.json` is not a substitute for checking the live tool list you have access to right now.
|
|
24
|
+
|
|
25
|
+
If `use_figma` is unavailable in the current session, **Do NOT proceed to Step 1**. Steps 1 (analyze) and 3 (gotcha-survey) spend real Figma API calls and 5–15 minutes of human survey time before Step 4 would otherwise discover `use_figma` is missing. Halt immediately and tell the user:
|
|
26
|
+
|
|
27
|
+
1. Confirm `.mcp.json` registers the Figma MCP entry (e.g. `figma` under `mcpServers`).
|
|
28
|
+
2. Restart Claude Code so the newly registered tools load.
|
|
29
|
+
3. Re-invoke `/canicode-roundtrip <url>`.
|
|
30
|
+
|
|
31
|
+
See the Edge Case **No Figma MCP server** below for the one-way fallback when Figma MCP genuinely cannot be installed — the precheck above is for the common "installed but not restarted" case, not a replacement for that fallback.
|
|
32
|
+
|
|
21
33
|
### Step 1: Analyze the design
|
|
22
34
|
|
|
23
35
|
If the `analyze` MCP tool is available, call it with the user's Figma URL:
|
|
@@ -94,7 +106,7 @@ Wait for the user's answer before moving to the next question. The user may:
|
|
|
94
106
|
- Say "skip" to skip a question
|
|
95
107
|
- Say "n/a" if the question is not applicable
|
|
96
108
|
|
|
97
|
-
After all questions are answered, **
|
|
109
|
+
After all questions are answered, **upsert this design's gotcha section** into `.claude/skills/canicode-gotchas/SKILL.md` in the user's project. Read the existing file, then either replace the section whose `Design key` matches this run (same Figma URL → fileKey+nodeId) or append a new numbered section under `# Collected Gotchas`. Never modify anything above the `# Collected Gotchas` heading — the region above it (frontmatter + workflow prose) is the skill loader contract installed by `canicode init`. See the `/canicode-gotchas` skill's "Upsert the gotcha section" step (Step 4) for the exact section format and matching rule.
|
|
98
110
|
|
|
99
111
|
Then proceed to **Step 4** to apply answers to the Figma design.
|
|
100
112
|
|
|
@@ -309,7 +321,7 @@ Applied {N} changes to the Figma design:
|
|
|
309
321
|
- 📝 {nodeName}: annotation added to canicode:auto-fix — raw color needs token binding (raw-value)
|
|
310
322
|
```
|
|
311
323
|
|
|
312
|
-
### Step 5: Re-analyze and
|
|
324
|
+
### Step 5: Re-analyze and report what the roundtrip addressed
|
|
313
325
|
|
|
314
326
|
Run `analyze` again on the same Figma URL:
|
|
315
327
|
|
|
@@ -317,10 +329,32 @@ Run `analyze` again on the same Figma URL:
|
|
|
317
329
|
analyze({ input: "<figma-url>" })
|
|
318
330
|
```
|
|
319
331
|
|
|
320
|
-
|
|
332
|
+
Under ADR-012's annotate-by-default policy, most instance-child gotchas route to 📝 annotations and do **not** move the numeric grade — so the headline for this step is the **issues-delta** (what the roundtrip captured), not a grade comparison. Grade is kept as a footnote so the Row 8 regression guardrail still applies.
|
|
333
|
+
|
|
334
|
+
**Tally inputs** — derive the counts from the data you already have:
|
|
335
|
+
- `X` (✅ resolved): count of ✅ + 🔧 + 🔗 markers from the Step 4 report block you just emitted (scene/instance-child writes, auto-fix renames, and variable bindings all successfully landed the value).
|
|
336
|
+
- `Y` (📝 annotated): count of 📝 markers from Step 4 — gotcha answers captured as Figma annotations for code-gen reference.
|
|
337
|
+
- `Z` (🌐 definition writes): count of 🌐 markers from Step 4 — only non-zero when the orchestrator opted in with `allowDefinitionWrite: true` (helper context option, not a CLI flag).
|
|
338
|
+
- `W` (⏭️ skipped): count of ⏭️ markers from Step 4 plus any Step 3 questions the user answered with `skip` or `n/a`.
|
|
339
|
+
- `V` (remaining): `issues.length` from the re-analyze response — unresolved gotchas plus non-actionable rules still flagged by the design.
|
|
340
|
+
- `N` (addressed) = `X + Y + Z + W`.
|
|
321
341
|
|
|
322
|
-
|
|
323
|
-
|
|
342
|
+
If Step 4 produced no report block (e.g. user skipped every question, or no gotcha survey ran), all four counts are zero — that is a legitimate outcome; report the breakdown with zeros rather than treating it as an error.
|
|
343
|
+
|
|
344
|
+
**All gotcha issues resolved** (`V == 0`, i.e. re-analyze surfaces no remaining issues — note this is independent of grade since ADR-012 annotations do not move the score):
|
|
345
|
+
- Tell the user (fill in the counts from the tally above):
|
|
346
|
+
|
|
347
|
+
```
|
|
348
|
+
Roundtrip complete — N issues addressed:
|
|
349
|
+
✅ X resolved (auto-fix or property write succeeded)
|
|
350
|
+
📝 Y annotated on Figma (gotcha answers captured for code-gen)
|
|
351
|
+
🌐 Z definition writes propagated (only when allowDefinitionWrite: true)
|
|
352
|
+
⏭️ W skipped (user declined or "skip")
|
|
353
|
+
—
|
|
354
|
+
V issues remaining (unresolved gotchas + non-actionable rules)
|
|
355
|
+
|
|
356
|
+
Grade: {oldGrade} → {newGrade}. Ready for code generation.
|
|
357
|
+
```
|
|
324
358
|
- Clean up canicode annotations: remove annotations with `[canicode]` prefix from fixed nodes via `use_figma`. Apply `stripAnnotations` to avoid the D1 mutex:
|
|
325
359
|
```javascript
|
|
326
360
|
const nodeIds = ["id1", "id2"]; // nodes that now pass
|
|
@@ -335,9 +369,20 @@ for (const id of nodeIds) {
|
|
|
335
369
|
```
|
|
336
370
|
- Proceed to **Step 6**.
|
|
337
371
|
|
|
338
|
-
**Some issues remain
|
|
339
|
-
- Show
|
|
340
|
-
|
|
372
|
+
**Some issues remain** (`V > 0`):
|
|
373
|
+
- Show the same breakdown and ask whether to proceed:
|
|
374
|
+
|
|
375
|
+
```
|
|
376
|
+
Roundtrip complete — N issues addressed:
|
|
377
|
+
✅ X resolved (auto-fix or property write succeeded)
|
|
378
|
+
📝 Y annotated on Figma (gotcha answers captured for code-gen)
|
|
379
|
+
🌐 Z definition writes propagated (only when allowDefinitionWrite: true)
|
|
380
|
+
⏭️ W skipped (user declined or "skip")
|
|
381
|
+
—
|
|
382
|
+
V issues remaining (unresolved gotchas + non-actionable rules)
|
|
383
|
+
|
|
384
|
+
Grade: {oldGrade} → {newGrade}. Proceed to code generation with remaining context?
|
|
385
|
+
```
|
|
341
386
|
- If yes → proceed to **Step 6** with remaining gotcha context.
|
|
342
387
|
- If no → stop and let the user address remaining issues manually.
|
|
343
388
|
|
|
@@ -350,6 +395,7 @@ Follow the **figma-implement-design** skill workflow to generate code from the F
|
|
|
350
395
|
- Gotchas with severity **blocking** MUST be addressed — the design cannot be implemented correctly without this information
|
|
351
396
|
- Gotchas with severity **risk** SHOULD be addressed — they indicate potential issues that will surface later
|
|
352
397
|
- Reference the specific node IDs from gotcha answers to locate the affected elements in the design
|
|
398
|
+
- Pass the Figma URL (or `designKey` = `<fileKey>#<nodeId>`) to `figma-implement-design` so it can grep the matching `## #NNN — …` section in `.claude/skills/canicode-gotchas/SKILL.md` instead of reading the whole accumulated file
|
|
353
399
|
|
|
354
400
|
**If all issues were resolved in Steps 4-5**, no additional gotcha context is needed — the design speaks for itself.
|
|
355
401
|
|