From 390e215fbfbccc6707e1869631d3dc84ed306abe Mon Sep 17 00:00:00 2001 From: Rahul Krishna Date: Mon, 3 Aug 2026 10:42:06 -0700 Subject: [PATCH 1/4] Add planning-cldk-work: the mode upstream of design The ladder had no entry point for work that is not yet a single change. Every routing row assumed the change had already been chosen, so a team shaping a quarter -- or a theme like "microservice static analysis" -- had to run design mode repeatedly and got N unrelated specs with nothing expressing order, dependency, or what was deliberately excluded. The entry test is "can this be stated as a single contract decision?" Two shapes fail it and both belong here: a theme that decomposes into several decisions, and several initiatives competing for the same quarter. Plurality lives in the contract decisions, not in how many things the user named -- counting nouns gets both directions wrong, which is what S2 and S3 pin down. The core is the contract-collision sweep, and it is the reason the mode is worth having: microservice analysis and polyglot analysis both need boundary-edge vocabulary, so that is ONE design decision. Designed in separate sessions they produce two vocabularies for one concept, and the parity clause forbids renaming either afterwards. No other mode can see this -- they are all single-change scoped. Output is a committed roadmap (codellm-devkit/.github -> docs/design/roadmap.md) plus an epic for the one decision actually starting. Not one epic per candidate: that is the July flood with a nicer name, and it is called out in the red flags. Deliberately excluded: estimation, capacity, velocity. The mode reasons about contracts, dependencies and release trains -- the things specific to a multi-repo ecosystem under a shared schema -- and records and challenges rather than facilitating, since a planning session between people is a meeting an agent cannot run. Wires into the dispatcher (diagram, routing row, two scope-guard red flags), the README, and designing-cldk-changes' entry preconditions, which now note that work arriving from planning comes with its collision group already known. --- .claude-plugin/plugin.json | 14 +- README.md | 21 ++- skills/designing-cldk-changes/SKILL.md | 6 + skills/planning-cldk-work/SKILL.md | 149 ++++++++++++++++++ .../references/roadmap-template.md | 80 ++++++++++ skills/using-cldk-devtools/SKILL.md | 9 ++ .../planning-cldk-work/s1-collision-sweep.md | 43 +++++ .../s2-not-really-planning.md | 29 ++++ .../s3-single-theme-is-planning.md | 31 ++++ 9 files changed, 377 insertions(+), 5 deletions(-) create mode 100644 skills/planning-cldk-work/SKILL.md create mode 100644 skills/planning-cldk-work/references/roadmap-template.md create mode 100644 tests/scenarios/planning-cldk-work/s1-collision-sweep.md create mode 100644 tests/scenarios/planning-cldk-work/s2-not-really-planning.md create mode 100644 tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md diff --git a/.claude-plugin/plugin.json b/.claude-plugin/plugin.json index ba73440..28254dd 100644 --- a/.claude-plugin/plugin.json +++ b/.claude-plugin/plugin.json @@ -1,8 +1,8 @@ { "name": "cldk-devtools", "displayName": "CLDK DevTools", - "description": "The CLDK developer's mode ladder: skills for designing, building, maintaining, and releasing CodeLLM-DevKit — from a language's backend analyzer through the frontend SDKs, plus day-to-day upkeep across the codellm-devkit org.", - "version": "0.3.0", + "description": "The CLDK developer's mode ladder: skills for designing, building, maintaining, and releasing CodeLLM-DevKit \u2014 from a language's backend analyzer through the frontend SDKs, plus day-to-day upkeep across the codellm-devkit org.", + "version": "0.4.0", "author": { "name": "Rahul Krishna", "email": "i.m.ralk@gmail.com" @@ -10,5 +10,13 @@ "homepage": "https://codellm-devkit.info", "repository": "https://github.com/codellm-devkit/cldk-devtools", "license": "Apache-2.0", - "keywords": ["cldk", "codellm-devkit", "code-analysis", "static-analysis", "dataflow", "skills", "mode-ladder"] + "keywords": [ + "cldk", + "codellm-devkit", + "code-analysis", + "static-analysis", + "dataflow", + "skills", + "mode-ladder" + ] } diff --git a/README.md b/README.md index 4cff961..8806ae4 100644 --- a/README.md +++ b/README.md @@ -31,10 +31,15 @@ diffs them. ``` using-cldk-devtools (dispatcher) │ + too plural for one design │ + ▼ │ + planning-cldk-work │ roadmap doc + ONE epic + │ pick one decision │ + ▼ ▼ structural work │ upkeep work ▼ ▼ designing-cldk-changes maintaining-cldk - │ spec + GitHub epic │ HARD GATE: escalate to design mode + │ spec + tracking record │ HARD GATE: escalate to design mode ▼ │ if the fix moves schema v2 / public API codeanalyzer-backend │ ▼ │ @@ -49,6 +54,7 @@ diffs them. | Work type | Entry point | Path | | --- | --- | --- | +| Work too plural for one design session — a theme decomposing into several contract decisions, or several initiatives competing for a quarter | planning-cldk-work | plan → design (one decision) → … | | New language for CLDK | designing-cldk-changes | design → backend → frontend → finishing | | Schema v2 evolution / migration | designing-cldk-changes | design → backend (all affected analyzers) → frontend (all affected SDKs) → finishing | | New analysis level (L2/L3/L4) for a language | designing-cldk-changes | design → backend → frontend (if surface changes) → finishing | @@ -66,7 +72,18 @@ diffs them. before any action on a codellm-devkit repo, including quick fixes, questions, and issue triage; in practice it is injected automatically by the `SessionStart` hook rather than invoked by name. **References:** none — it stays under 500 words by design and defers all workflow detail to the -other five skills. +other skills. + +### [`planning-cldk-work`](skills/planning-cldk-work/) + +**Owns:** everything upstream of a single design session — decomposing a theme into the contract +decisions it contains, the **collision sweep** that catches candidates sharing schema vocabulary +(which the parity clause makes permanent once coined), dependency order, release trains, and the +explicit not-now list. Produces a committed roadmap at `codellm-devkit/.github` → +`docs/design/roadmap.md`, plus an epic for the one decision actually starting — never one per +candidate. **Triggers:** the work cannot be stated as a single contract decision, either because a +theme contains several or because several initiatives compete. **References:** +`roadmap-template.md`. ### [`designing-cldk-changes`](skills/designing-cldk-changes/) diff --git a/skills/designing-cldk-changes/SKILL.md b/skills/designing-cldk-changes/SKILL.md index 54bcbf6..5612d79 100644 --- a/skills/designing-cldk-changes/SKILL.md +++ b/skills/designing-cldk-changes/SKILL.md @@ -19,6 +19,12 @@ any cross-repo feature. If it arrived as a "small fix" that turned out to move the schema v2 output or the public SDK API, **maintaining-cldk**'s contract gate escalated it here — say so and continue; it is now a structural change, not a fix. +If it arrived from **planning-cldk-work**, it comes with its collision group +already known: the roadmap says which other candidates share this change's +vocabulary. Design the shared part **once, here**, for the whole group — the parity +clause makes a term coined twice permanently wrong. If the work is plural enough +that you cannot name one contract decision, it belongs back in planning mode. + ## Contract-Impact Triage **First move, always — before any design detail.** Answer, out loud: diff --git a/skills/planning-cldk-work/SKILL.md b/skills/planning-cldk-work/SKILL.md new file mode 100644 index 0000000..576a88a --- /dev/null +++ b/skills/planning-cldk-work/SKILL.md @@ -0,0 +1,149 @@ +--- +name: planning-cldk-work +description: Use when CLDK work is too plural for one design session — a theme that decomposes into several contract decisions, or several initiatives competing for a quarter — before any one of them enters design mode. +--- + +# Planning CLDK work + +The planning mode of the CLDK ladder, and the only mode that reasons across **more +than one contract decision at a time**. Every other mode is single-change scoped: +they take "we have decided to do X" and carry X to release. This one comes before +that — it decides *which* decisions, in what order, and which of them are secretly +the same decision. + +Planning is **shallow across many**; design mode is **deep on one**. Resist +designing here. + +## Entry Preconditions + +**The test: can this be stated as a single contract decision?** If yes, it is design +mode. If no, it is planning. Two shapes fail that test, and both belong here: + +- **A theme that decomposes into several contract decisions.** "Microservice static + analysis" is not a feature — it contains boundary-edge vocabulary, service + topology, per-framework entrypoint detection, cross-service reachability. Those + compete for order, some are not-now, and one of them may collide with a different + theme entirely. One initiative, still plural. +- **Several initiatives competing for the same quarter.** The portfolio case. + +Either way there is something to **order, group, and exclude** — and that is what +this mode does that no other can. + +Counter-test, so the mode does not fire on ordinary work: if you can name the one +contract decision and the only open question is how its PRs sequence, that is +`designing-cldk-changes`'s decomposition step, not a roadmap. Go L3/L4 on one +analyzer is one decision; do not manufacture a roadmap for it. + +Candidates may be vague. Vagueness is fine and expected — the collision sweep below +works on rough shapes. + +## The Loop + +Run it **WITH the user** — every ordering and grouping call is theirs +(`AskUserQuestion`), not a silent pick. + +### 1. Inventory — at the altitude of contract decisions + +One line per candidate. No design detail. + +**A theme is not a candidate — decompose it first.** "Microservice static analysis" +is not one row; it is boundary-edge vocabulary, service topology, per-framework +entrypoints, cross-service reachability — each a contract decision that can be +ordered, deferred, or found to collide with something else. Break themes down to +that altitude before going further, or the collision sweep has nothing to compare. + +The test for a row: could it be one design session? If it is clearly several, split +it. If two rows would obviously be decided together, merge them. + +### 2. Contract-collision sweep — the reason this mode exists + +For each candidate, ask the Contract-Impact Triage question **shallowly**: does it +move schema v2 output (a node/edge kind, field, level, or id shape)? Then +cross-reference the answers: + +> **Which candidates touch the same vocabulary?** + +Any overlap is **one decision, not two** — it must be settled in a single design +session even if the features ship months apart. The +[parity clause](../designing-cldk-changes/references/canonical-schema.md) forbids +renaming or repurposing shared vocabulary once it exists, so a term coined twice +is coined wrong permanently. + +Output: **collision groups**. A group is a set of candidates plus the vocabulary +they share. + +Nothing else in the ladder can find these, because nothing else sees more than one +change at a time. This step is why the mode is worth having. + +### 3. Dependency order + +A DAG, not a list. For each candidate: what must exist first? Blocked-by +relationships are the plan — a roadmap that does not say what unblocks what is an +unordered wishlist. + +### 4. Release trains + +Which train carries which candidate, and where a schema major forces lockstep +between repos. **Candidates sharing a schema major should ride one migration**, not +one migration each — that is usually the largest saving planning finds. + +### 5. Explicit not-now + +What is deliberately excluded from this pass, and why. A roadmap without a not-now +list is a wishlist; the exclusions are what make the inclusions mean something. + +### 6. Commit the roadmap, then start at most one thing + +Write the roadmap to **`codellm-devkit/.github` → `docs/design/roadmap.md`**, per +`references/roadmap-template.md`. It is committed and reviewable, alongside the +epics and cross-repo specs it coordinates. + +Then file an epic for **the single feature actually starting now** — and nothing +else. The roadmap records the rest; the tracker does not need to mirror it. + +## + +No candidate may enter `designing-cldk-changes` until the **collision sweep has run +and its group is known**. Designing a feature in isolation that shares vocabulary +with another candidate is the one planning mistake the parity clause makes +permanent — every other planning error is recoverable by re-planning. + +The gate is on the sweep, never on the roadmap's length or polish. + +## Terminal State + +The ONLY skill you invoke after planning-cldk-work is `designing-cldk-changes`, for +the one feature being started. + +**Checkpoint first.** Do not auto-invoke it. Summarize the collision groups, the +dependency order, and what was excluded, then `AskUserQuestion` — start the first +feature's design now, start a different one, or stop here (see +`using-cldk-devtools` → Transition Checkpoint). + +**Parking after the roadmap is a legitimate outcome, and often the right one.** The +roadmap is the deliverable of this mode; starting a feature is optional and can +happen in a later session without losing anything. + +## Red Flags + +| Rationalization | Reality | +| --- | --- | +| "File all six epics so the board shows the quarter." | Six idle epics is inventory, and inventory rots. File the one you are starting; the roadmap records the rest. | +| "These are separate features, design them separately." | Run the collision sweep first. Shared vocabulary decided twice is decided wrong, permanently. | +| "Put the roadmap in a tracking issue so it's visible." | Docs carry content, trackers carry state. The roadmap is a committed doc; the Project board is the live view. | +| "Let's plan all six in depth while we're here." | Planning is shallow across many. Depth is design mode, per feature, when that feature starts. | +| "We'll work out the ordering as we go." | Dependency order *is* the plan. Without it you have a list of wishes. | +| "There's only one contract decision here, but let's roadmap it anyway." | Then this is not planning. Route to designing-cldk-changes and skip the ceremony. | +| "'Microservice analysis' is one row on the roadmap." | It is a theme, not a decision. Decompose it into the contract decisions it contains, or the collision sweep has nothing to compare and the ordering is fiction. | +| "The user is busy; I'll group and order these myself." | Grouping and ordering are the user's calls. `AskUserQuestion`, never solo. | + +## Scope Guard + +This mode plans **CLDK feature work**. It is not a general project-management tool: +no estimation, no capacity modelling, no velocity. It reasons about contracts, +dependencies, and release trains — the things specific to a multi-repo analyzer +ecosystem governed by a shared schema. + +If a planning session is really a meeting between people, this mode **records and +challenges**; it does not facilitate. Capture what they decide, surface the +collisions they missed, and say plainly when a call is theirs to make. diff --git a/skills/planning-cldk-work/references/roadmap-template.md b/skills/planning-cldk-work/references/roadmap-template.md new file mode 100644 index 0000000..5c567bc --- /dev/null +++ b/skills/planning-cldk-work/references/roadmap-template.md @@ -0,0 +1,80 @@ +# Roadmap template + +The artifact `planning-cldk-work` produces. Lives at **`codellm-devkit/.github` → +`docs/design/roadmap.md`**, committed, next to the epics and cross-repo specs it coordinates. + +One roadmap per planning pass, amended in place rather than duplicated per quarter — the git +history is the record of how thinking changed, which is exactly what an issue body cannot give you. + +## Why a doc and not issues + +A roadmap is **content**: why these, in this order, and what is excluded. Content belongs in a +reviewable, diffable document. Issues are **state**: what is in flight right now. + +Filing an epic per planned feature converts the roadmap into inventory — issues that sit idle, +go stale, and bury the ones that are live. File the epic for the feature you are starting; let the +roadmap carry the rest. + +A PR that amends the roadmap can reference the epics it affects, so each change shows up in their +timelines automatically. That is the tracking, and it costs nothing to maintain. + +## Template + +```markdown +# CLDK roadmap + +**Pass:** · **Planned with:** +**Status:** current (supersede by editing, not by adding a second roadmap) + +## Candidates + +| # | Feature | Moves schema v2? | Collision group | Blocked by | +| - | ------- | ---------------- | --------------- | ---------- | +| 1 | | yes — / no | A | — | +| 2 | | yes — | A | 1 | +| 3 | | no — SDK surface only | — | 1 | + +## Collision groups + +Candidates that touch the same schema vocabulary. **Each group is ONE design session for the +shared part**, even where the features ship far apart — the parity clause makes a term coined +twice permanently wrong. + +- **Group A — **: candidates 1, 2. + + Design session: . + +## Dependency order + + + + 1 (vocabulary) ──▶ 2 (linking) ──▶ 3 (surface) + +## Release trains + +| Train | Carries | Notes | +| ----- | ------- | ----- | +| | 1 | schema major — SDK pins only once cut | +| | 3 | after the analyzer release lands | + +Candidates sharing a schema major ride **one** migration, not one each. + +## Not now + +**The list that makes the rest mean something.** What is excluded from this pass, and why. + +- + +## Starting now + + +Everything else on this roadmap has no issue yet, by design. +``` + +## Amending it + +- Change the doc, not a mirror of it in a tracker. +- Reference affected epics in the PR body so the change lands in their timelines. +- When a candidate starts, add its epic link under **Starting now** and move the previous one out. +- When a candidate is dropped, move it to **Not now** with the reason. Deleting the row loses the + fact that it was considered, which is often the most useful thing the roadmap records. diff --git a/skills/using-cldk-devtools/SKILL.md b/skills/using-cldk-devtools/SKILL.md index 95b29af..855b8bd 100644 --- a/skills/using-cldk-devtools/SKILL.md +++ b/skills/using-cldk-devtools/SKILL.md @@ -40,6 +40,11 @@ while asking. ``` using-cldk-devtools (dispatcher) │ + too plural for one design │ + ▼ │ + planning-cldk-work │ roadmap doc + ONE epic + │ pick one decision │ + ▼ ▼ structural work │ upkeep work ▼ ▼ designing-cldk-changes maintaining-cldk @@ -58,6 +63,7 @@ while asking. | Work type | Entry point | Path | | --- | --- | --- | +| **Work too plural for one design session** — a theme that decomposes into several contract decisions ("microservice analysis"), or several initiatives competing for a quarter | planning-cldk-work | plan → design (one decision) → … | | New language for CLDK | designing-cldk-changes | design → backend → frontend → finishing | | Schema v2 evolution / migration | designing-cldk-changes | design → backend (all affected analyzers) → frontend (all affected SDKs) → finishing | | New analysis level (L2/L3/L4) for a language | designing-cldk-changes | design → backend → frontend (if surface changes) → finishing | @@ -72,6 +78,9 @@ while asking. | Rationalization | Reality | | --- | --- | | "It's just a small schema tweak" | Schema changes enter at designing-cldk-changes. | +| "They named two things, so this is planning" | Count contract decisions, not nouns. The test is: *can this be stated as ONE contract decision?* Yes → design mode. Go L3/L4 is two levels of one decision, not a roadmap. | +| "They named one thing, so this is design" | Same test, other direction. "Microservice analysis" is one *theme* containing several decisions — boundary edges, topology, entrypoints — so it is planning even though they named one thing. | +| "We're planning several things, I'll design them all now" | Planning is shallow across many; design is deep on one. Run the collision sweep, then design the one that starts. | | "I'll patch the SDK model directly" | Check the schema contract first — enter the ladder. | | "This fix is analyzer-local" | Siblings share the schema. maintaining-cldk runs the propagation sweep. | | "I'll release manually just this once" | Releases go through finishing-cldk-work. | diff --git a/tests/scenarios/planning-cldk-work/s1-collision-sweep.md b/tests/scenarios/planning-cldk-work/s1-collision-sweep.md new file mode 100644 index 0000000..d28a2a6 --- /dev/null +++ b/tests/scenarios/planning-cldk-work/s1-collision-sweep.md @@ -0,0 +1,43 @@ +# S1: planning several features must find the shared vocabulary +Subagent prompt (cwd = any codellm-devkit checkout, dispatcher content prepended +in the WITH-skill run): + +"Alice and I are planning next quarter. We want to add microservice static +analysis, polyglot analysis across languages, Go L3/L4 dataflow, and a C# frontend. +Can you get all of that written up and into GitHub so the team can see the plan?" + +The prompt asks for everything to be "into GitHub", which is the pressure being +tested: the obvious reading is "file four epics and their children." + +PASS (with skill): the agent enters `planning-cldk-work` and first **decomposes the +themes to the altitude of contract decisions** — "microservice static analysis" is +not one row, it is boundary-edge vocabulary, service topology, per-framework +entrypoint detection, cross-service reachability. Only then does the +**contract-collision sweep** work: it identifies that microservice analysis and +polyglot analysis **both need boundary-edge vocabulary** (`http` / `rpc` / `queue`), +so that vocabulary is ONE design decision, not two, because the parity clause makes +a term coined twice permanently wrong. It +establishes dependency order, assigns release trains, records an explicit not-now +list, writes the roadmap to `codellm-devkit/.github` → `docs/design/roadmap.md`, +and files **at most one epic** — for the single feature actually starting. It +checkpoints before entering `designing-cldk-changes`. + +FAIL: +- "microservice static analysis" is carried through as a single roadmap row — a + theme left undecomposed gives the collision sweep nothing to compare, and the + boundary-edge overlap becomes invisible; +- four epics (or four epics plus children) filed because the user said "into + GitHub" — the roadmap is a committed doc, and the tracker gets the one feature + that is starting; +- the collision between microservice and polyglot analysis is not surfaced, and + each is treated as an independent design; +- the roadmap is written into an issue body rather than committed as a doc; +- the agent designs all four in depth in this session instead of staying shallow; +- grouping, ordering, or the not-now list is decided solo rather than via + `AskUserQuestion`; +- the agent auto-invokes `designing-cldk-changes` without a checkpoint. + +The collision sweep is the whole reason this mode exists — every other mode is +single-change scoped and structurally cannot see it. An agent that produces a +tidy, well-ordered roadmap but misses the shared boundary-edge vocabulary has +failed the scenario even if everything else is right. diff --git a/tests/scenarios/planning-cldk-work/s2-not-really-planning.md b/tests/scenarios/planning-cldk-work/s2-not-really-planning.md new file mode 100644 index 0000000..705c081 --- /dev/null +++ b/tests/scenarios/planning-cldk-work/s2-not-really-planning.md @@ -0,0 +1,29 @@ +# S2: one contract decision is not planning, however it is described +Subagent prompt (cwd = a codeanalyzer-go checkout): + +"We need to plan out the Go dataflow work — there's the intraprocedural CFG/PDG +side and then the interprocedural SDG side. Two big chunks. Let's get a roadmap +together." + +The user says "plan", says "roadmap", and names "two big chunks" — every surface +signal points at planning mode. But L3 and L4 on one analyzer are **one contract +decision**: nothing to prioritise between, nothing to exclude, and the order is +forced rather than chosen. The only open question is how the PRs sequence, which is +design mode's decomposition step. + +PASS (with skill): the agent applies the entry test — *can this be stated as a +single contract decision?* — answers yes, says so plainly, and routes to +`designing-cldk-changes`. It does not manufacture a roadmap document. + +FAIL: +- the agent enters `planning-cldk-work` because the words "plan" and "roadmap" + appeared, and produces a two-row roadmap; +- it writes `docs/design/roadmap.md` for a single-repo, single-feature change; +- it treats L3 and L4 as a "collision group" — they share vocabulary by + construction, being the same feature, which is not what the sweep is for. + +This is the counterpart to S1. S1 checks the mode fires when it should; S2 checks +it does not fire on ordinary single-feature work dressed in planning language. +Entry preconditions have historically been the weak point in this plugin, and this +mode's precondition — **two or more candidate features, none chosen** — is doing +the load-bearing work. diff --git a/tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md b/tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md new file mode 100644 index 0000000..0abd2b4 --- /dev/null +++ b/tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md @@ -0,0 +1,31 @@ +# S3: one theme is still planning — plurality is in the decisions, not the ask +Subagent prompt (cwd = any codellm-devkit checkout): + +"I want to add microservice static analysis to CLDK. Where do we start?" + +One initiative. No list, no quarter, no second candidate. The surface reading is +"one feature" — and an agent applying a naive "two or more features" precondition +routes this to design mode, which is wrong. + +PASS (with skill): the agent applies the entry test — *can this be stated as a +single contract decision?* — and answers **no**. "Microservice static analysis" is a +theme containing several independent contract decisions: boundary-edge vocabulary +(`http` / `rpc` / `queue`), service topology, per-framework entrypoint detection, +cross-service reachability. Those can be ordered, deferred, or found to collide +with other work, so there is something to order, group and exclude. It enters +`planning-cldk-work`, decomposes the theme to that altitude, runs the sweep, and +produces a roadmap — even though the user named only one thing. + +FAIL: +- routed to `designing-cldk-changes` because "it's one feature" — design mode's + triage is built around a single contract decision and will either collapse the + theme into whichever part is most concrete, or attempt to design all of it at + once; +- entered planning mode but left "microservice static analysis" as a single + undecomposed row; +- refused on the grounds that a roadmap needs more than one candidate. + +This is the counterpart to S2 and the harder direction. S2 rejects a single +decision dressed in planning language; S3 accepts a single *theme* that is plural +underneath. **Plurality lives in the contract decisions, not in how many things the +user named** — an agent that counts nouns in the prompt gets both wrong. From 104f7e3383020d5c2aa9ff9780757dd7803629f8 Mon Sep 17 00:00:00 2001 From: Rahul Krishna Date: Tue, 4 Aug 2026 09:41:18 -0400 Subject: [PATCH 2/4] Sync README/dispatcher, add CHANGELOG declaring 0.3.0's breaking change tests/consistency/check-readme-dispatcher-sync.sh was failing on two blocks and had not been run before opening #35: - the dispatcher's ladder diagram still read "spec + GitHub epic" after 0.3.0 renamed it to "spec + tracking record" -- stale since #34 merged, which the check would have caught then - the README's routing row for planning-cldk-work disagreed word-for-word with the dispatcher's Both now match and the check passes. Adds CHANGELOG.md. 0.3.0 changed HARD-GATE semantics, removed two Red Flags rows that forbade smaller tracking shapes, moved epics to another repo, retired "Part of #N" trailers, relocated specs, and made every ladder transition stop for the user -- all behaviour-breaking for anyone on 0.2.0 conventions, and none of it declared anywhere. #34's PR body never filled in the org template's "Breaking Changes" section, so this is the first place it is written down. --- CHANGELOG.md | 72 +++++++++++++++++++++++++++++ README.md | 4 +- skills/using-cldk-devtools/SKILL.md | 2 +- 3 files changed, 75 insertions(+), 3 deletions(-) create mode 100644 CHANGELOG.md diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..454bfc1 --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,72 @@ +# Changelog + +All notable changes to the CLDK DevTools plugin are documented here. +Format follows [Keep a Changelog](https://keepachangelog.com/en/1.1.0/); +this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). + +## [0.4.0] — unreleased + +### Added + +- **`planning-cldk-work`** — a new mode upstream of design, for work that cannot be + stated as a single contract decision: a theme that decomposes into several + (e.g. "microservice static analysis"), or several initiatives competing for a + quarter. Its core is the **contract-collision sweep**, which finds candidates + sharing schema vocabulary before either enters design — the parity clause makes a + term coined twice permanently wrong, and no other mode sees more than one change + at a time. Produces a committed roadmap plus an epic for the one decision + starting, never one epic per candidate. +- `references/roadmap-template.md`, and scenarios `s1`–`s3` covering the collision + sweep, a single decision dressed in planning language, and a single theme that is + plural underneath. + +### Fixed + +- The dispatcher's ladder diagram still read "spec + GitHub epic" after 0.3.0 + renamed it to "spec + tracking record", and the README's routing row for the new + mode disagreed with the dispatcher's. Both are now in sync + (`tests/consistency/check-readme-dispatcher-sync.sh` passes). + +## [0.3.0] — 2026-08-03 + +### Changed — **BREAKING** (behavioural) + +This release changes how agents decompose and track work. Sessions running under +0.2.0 conventions will behave differently after updating; anyone relying on the old +shape should read this before upgrading. + +- **Issue decomposition is now proportional and user-decided.** 0.2.0 mandated an + epic plus one child per ladder rung for any structural change touching ≥1 rung, + and its Red Flags table explicitly forbade scaling that down. Tracking granularity + now follows **PR granularity** — one issue per pull request — and the shape is put + to the user rather than applied by default. A single-PR change is one issue. +- **`` semantics changed.** It previously bound to "the spec AND the + GitHub epic + child issues exist". It now binds to "the spec exists and the work + is tracked", never to an issue count. +- **Removed two Red Flags rows** that forbade smaller tracking shapes + ("Scale the writing, never the gate"; "any structural change that touches ≥1 rung + gets an epic + one child per rung"). +- **Epics moved repos.** They now live in `codellm-devkit/.github`, not on the repo + owning the deliverable. +- **`Part of #N` trailers and hand-maintained `CHILDREN` checklists are retired** in + favour of native GitHub sub-issues. Existing epics carrying either will not be + updated automatically. +- **Specs and plans moved** from `docs/superpowers/` to a tool-neutral + `docs/design/{specs,plans}/`, and are committed as provenance rather than + gitignored scratch. +- **Every ladder transition now stops for the user.** All nine transition points + — forward, and the backward/sideways gate escalations — announce and ask before + invoking the next skill. An end-to-end run is materially more interactive than + under 0.2.0. + +### Added + +- Issue bodies now come from org-level forms in `codellm-devkit/.github` + (`epic.yml`, `work_item.yml`), with the convention in that repo's + `CONTRIBUTING.md`. +- Scenario `s3-proportional-decomposition`, covering over-decomposition of a + single-repo change. + +## [0.2.0] + +Baseline for this changelog. See the repository history for earlier changes. diff --git a/README.md b/README.md index 8806ae4..4c0635d 100644 --- a/README.md +++ b/README.md @@ -54,7 +54,7 @@ diffs them. | Work type | Entry point | Path | | --- | --- | --- | -| Work too plural for one design session — a theme decomposing into several contract decisions, or several initiatives competing for a quarter | planning-cldk-work | plan → design (one decision) → … | +| **Work too plural for one design session** — a theme that decomposes into several contract decisions ("microservice analysis"), or several initiatives competing for a quarter | planning-cldk-work | plan → design (one decision) → … | | New language for CLDK | designing-cldk-changes | design → backend → frontend → finishing | | Schema v2 evolution / migration | designing-cldk-changes | design → backend (all affected analyzers) → frontend (all affected SDKs) → finishing | | New analysis level (L2/L3/L4) for a language | designing-cldk-changes | design → backend → frontend (if surface changes) → finishing | @@ -116,7 +116,7 @@ required propagation verdict). table (L1), call graph (L2), intraprocedural dataflow (L3), interprocedural SDG (L4) — into the canonical schema v2, in both the `analysis.json` and Neo4j projections. **Triggers:** adding a language, growing an analyzer through the levels, or migrating an existing analyzer to schema -v2 — only once a spec + GitHub epic exists from `designing-cldk-changes` (or a maintenance +v2 — only once a spec + tracking record exists from `designing-cldk-changes` (or a maintenance escalation arrives with its design decision already recorded). **Key references:** [`analyzer-architecture.md`](skills/codeanalyzer-backend/references/analyzer-architecture.md), [`tooling-menu.md`](skills/codeanalyzer-backend/references/tooling-menu.md), diff --git a/skills/using-cldk-devtools/SKILL.md b/skills/using-cldk-devtools/SKILL.md index 855b8bd..71a4f1e 100644 --- a/skills/using-cldk-devtools/SKILL.md +++ b/skills/using-cldk-devtools/SKILL.md @@ -48,7 +48,7 @@ while asking. structural work │ upkeep work ▼ ▼ designing-cldk-changes maintaining-cldk - │ spec + GitHub epic │ HARD GATE: escalate to design mode + │ spec + tracking record │ HARD GATE: escalate to design mode ▼ │ if the fix moves schema v2 / public API codeanalyzer-backend │ ▼ │ From bdbe9fefd326fd656380ffd725c1adbc1502c622 Mon Sep 17 00:00:00 2001 From: Rahul Krishna Date: Tue, 4 Aug 2026 09:47:28 -0400 Subject: [PATCH 3/4] Cut 58 net lines of restatement from the planning mode ponytail-review pass over the branch. The skill said the same thing three times because the entry test, the loop step and the red-flag row were written in separate passes and the whole file was never re-read. - plugin.json: a json.dumps rewrite had escaped the em-dash and exploded the keywords array onto 8 lines -- 12 lines of churn for a one-character version bump. Restored to a one-line diff. - SKILL.md: dropped the second and third copies of "microservice is a theme, decompose it", and two restatements of why the mode exists. - SKILL.md: cut 4 of 8 Red Flags rows that echoed prose on the same page. The table is where restatement accumulates. - roadmap-template.md: dropped "Why a doc and not issues" -- the fourth copy of that argument, after the skill's red flags, the org CONTRIBUTING and CLAUDE.md. A template shows the shape; it does not re-argue the policy. "Amending it" shrank from 7 lines to 2. - scenarios: dropped the closing meta-paragraphs explaining which scenario each was a counterpart to. s2's also still asserted the OLD precondition ("two or more candidate features, none chosen"), contradicting the entry test it exists to check -- cutting it removed the contradiction. - CHANGELOG: dropped the 0.4.0 "Fixed" entry, which documented doc-sync churn introduced and resolved inside the same unreleased version, and the empty 0.2.0 baseline stub. Consistency check still passes; no reference to the old precondition survives. --- .claude-plugin/plugin.json | 12 ++--------- CHANGELOG.md | 11 ---------- skills/planning-cldk-work/SKILL.md | 17 +++------------ .../references/roadmap-template.md | 21 ++----------------- .../planning-cldk-work/s1-collision-sweep.md | 9 +++----- .../s2-not-really-planning.md | 6 ------ .../s3-single-theme-is-planning.md | 6 ++---- 7 files changed, 12 insertions(+), 70 deletions(-) diff --git a/.claude-plugin/plugin.json b/.claude-plugin/plugin.json index 28254dd..13acd49 100644 --- a/.claude-plugin/plugin.json +++ b/.claude-plugin/plugin.json @@ -1,7 +1,7 @@ { "name": "cldk-devtools", "displayName": "CLDK DevTools", - "description": "The CLDK developer's mode ladder: skills for designing, building, maintaining, and releasing CodeLLM-DevKit \u2014 from a language's backend analyzer through the frontend SDKs, plus day-to-day upkeep across the codellm-devkit org.", + "description": "The CLDK developer's mode ladder: skills for designing, building, maintaining, and releasing CodeLLM-DevKit — from a language's backend analyzer through the frontend SDKs, plus day-to-day upkeep across the codellm-devkit org.", "version": "0.4.0", "author": { "name": "Rahul Krishna", @@ -10,13 +10,5 @@ "homepage": "https://codellm-devkit.info", "repository": "https://github.com/codellm-devkit/cldk-devtools", "license": "Apache-2.0", - "keywords": [ - "cldk", - "codellm-devkit", - "code-analysis", - "static-analysis", - "dataflow", - "skills", - "mode-ladder" - ] + "keywords": ["cldk", "codellm-devkit", "code-analysis", "static-analysis", "dataflow", "skills", "mode-ladder"] } diff --git a/CHANGELOG.md b/CHANGELOG.md index 454bfc1..82876a6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -20,13 +20,6 @@ this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm sweep, a single decision dressed in planning language, and a single theme that is plural underneath. -### Fixed - -- The dispatcher's ladder diagram still read "spec + GitHub epic" after 0.3.0 - renamed it to "spec + tracking record", and the README's routing row for the new - mode disagreed with the dispatcher's. Both are now in sync - (`tests/consistency/check-readme-dispatcher-sync.sh` passes). - ## [0.3.0] — 2026-08-03 ### Changed — **BREAKING** (behavioural) @@ -66,7 +59,3 @@ shape should read this before upgrading. `CONTRIBUTING.md`. - Scenario `s3-proportional-decomposition`, covering over-decomposition of a single-repo change. - -## [0.2.0] - -Baseline for this changelog. See the repository history for earlier changes. diff --git a/skills/planning-cldk-work/SKILL.md b/skills/planning-cldk-work/SKILL.md index 576a88a..f7de443 100644 --- a/skills/planning-cldk-work/SKILL.md +++ b/skills/planning-cldk-work/SKILL.md @@ -19,15 +19,11 @@ designing here. **The test: can this be stated as a single contract decision?** If yes, it is design mode. If no, it is planning. Two shapes fail that test, and both belong here: -- **A theme that decomposes into several contract decisions.** "Microservice static - analysis" is not a feature — it contains boundary-edge vocabulary, service - topology, per-framework entrypoint detection, cross-service reachability. Those - compete for order, some are not-now, and one of them may collide with a different - theme entirely. One initiative, still plural. +- **A theme that decomposes into several contract decisions** — "microservice static + analysis" is one initiative, still plural. Step 1 of the loop breaks it down. - **Several initiatives competing for the same quarter.** The portfolio case. -Either way there is something to **order, group, and exclude** — and that is what -this mode does that no other can. +Either way there is something to **order, group, and exclude**. Counter-test, so the mode does not fire on ordinary work: if you can name the one contract decision and the only open question is how its PRs sequence, that is @@ -72,9 +68,6 @@ is coined wrong permanently. Output: **collision groups**. A group is a set of candidates plus the vocabulary they share. -Nothing else in the ladder can find these, because nothing else sees more than one -change at a time. This step is why the mode is worth having. - ### 3. Dependency order A DAG, not a list. For each candidate: what must exist first? Blocked-by @@ -131,10 +124,6 @@ happen in a later session without losing anything. | "File all six epics so the board shows the quarter." | Six idle epics is inventory, and inventory rots. File the one you are starting; the roadmap records the rest. | | "These are separate features, design them separately." | Run the collision sweep first. Shared vocabulary decided twice is decided wrong, permanently. | | "Put the roadmap in a tracking issue so it's visible." | Docs carry content, trackers carry state. The roadmap is a committed doc; the Project board is the live view. | -| "Let's plan all six in depth while we're here." | Planning is shallow across many. Depth is design mode, per feature, when that feature starts. | -| "We'll work out the ordering as we go." | Dependency order *is* the plan. Without it you have a list of wishes. | -| "There's only one contract decision here, but let's roadmap it anyway." | Then this is not planning. Route to designing-cldk-changes and skip the ceremony. | -| "'Microservice analysis' is one row on the roadmap." | It is a theme, not a decision. Decompose it into the contract decisions it contains, or the collision sweep has nothing to compare and the ordering is fiction. | | "The user is busy; I'll group and order these myself." | Grouping and ordering are the user's calls. `AskUserQuestion`, never solo. | ## Scope Guard diff --git a/skills/planning-cldk-work/references/roadmap-template.md b/skills/planning-cldk-work/references/roadmap-template.md index 5c567bc..054ebc3 100644 --- a/skills/planning-cldk-work/references/roadmap-template.md +++ b/skills/planning-cldk-work/references/roadmap-template.md @@ -6,18 +6,6 @@ The artifact `planning-cldk-work` produces. Lives at **`codellm-devkit/.github` One roadmap per planning pass, amended in place rather than duplicated per quarter — the git history is the record of how thinking changed, which is exactly what an issue body cannot give you. -## Why a doc and not issues - -A roadmap is **content**: why these, in this order, and what is excluded. Content belongs in a -reviewable, diffable document. Issues are **state**: what is in flight right now. - -Filing an epic per planned feature converts the roadmap into inventory — issues that sit idle, -go stale, and bury the ones that are live. File the epic for the feature you are starting; let the -roadmap carry the rest. - -A PR that amends the roadmap can reference the epics it affects, so each change shows up in their -timelines automatically. That is the tracking, and it costs nothing to maintain. - ## Template ```markdown @@ -71,10 +59,5 @@ Candidates sharing a schema major ride **one** migration, not one each. Everything else on this roadmap has no issue yet, by design. ``` -## Amending it - -- Change the doc, not a mirror of it in a tracker. -- Reference affected epics in the PR body so the change lands in their timelines. -- When a candidate starts, add its epic link under **Starting now** and move the previous one out. -- When a candidate is dropped, move it to **Not now** with the reason. Deleting the row loses the - fact that it was considered, which is often the most useful thing the roadmap records. +Amend in place. A dropped candidate moves to **Not now** with its reason rather than being deleted +— that it was considered is often the most useful thing the roadmap records. diff --git a/tests/scenarios/planning-cldk-work/s1-collision-sweep.md b/tests/scenarios/planning-cldk-work/s1-collision-sweep.md index d28a2a6..8292dc6 100644 --- a/tests/scenarios/planning-cldk-work/s1-collision-sweep.md +++ b/tests/scenarios/planning-cldk-work/s1-collision-sweep.md @@ -35,9 +35,6 @@ FAIL: - the agent designs all four in depth in this session instead of staying shallow; - grouping, ordering, or the not-now list is decided solo rather than via `AskUserQuestion`; -- the agent auto-invokes `designing-cldk-changes` without a checkpoint. - -The collision sweep is the whole reason this mode exists — every other mode is -single-change scoped and structurally cannot see it. An agent that produces a -tidy, well-ordered roadmap but misses the shared boundary-edge vocabulary has -failed the scenario even if everything else is right. +- the agent auto-invokes `designing-cldk-changes` without a checkpoint; +- the roadmap is tidy and well-ordered but misses the shared boundary-edge + vocabulary — that alone fails the scenario. diff --git a/tests/scenarios/planning-cldk-work/s2-not-really-planning.md b/tests/scenarios/planning-cldk-work/s2-not-really-planning.md index 705c081..0430868 100644 --- a/tests/scenarios/planning-cldk-work/s2-not-really-planning.md +++ b/tests/scenarios/planning-cldk-work/s2-not-really-planning.md @@ -21,9 +21,3 @@ FAIL: - it writes `docs/design/roadmap.md` for a single-repo, single-feature change; - it treats L3 and L4 as a "collision group" — they share vocabulary by construction, being the same feature, which is not what the sweep is for. - -This is the counterpart to S1. S1 checks the mode fires when it should; S2 checks -it does not fire on ordinary single-feature work dressed in planning language. -Entry preconditions have historically been the weak point in this plugin, and this -mode's precondition — **two or more candidate features, none chosen** — is doing -the load-bearing work. diff --git a/tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md b/tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md index 0abd2b4..87ed609 100644 --- a/tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md +++ b/tests/scenarios/planning-cldk-work/s3-single-theme-is-planning.md @@ -25,7 +25,5 @@ FAIL: undecomposed row; - refused on the grounds that a roadmap needs more than one candidate. -This is the counterpart to S2 and the harder direction. S2 rejects a single -decision dressed in planning language; S3 accepts a single *theme* that is plural -underneath. **Plurality lives in the contract decisions, not in how many things the -user named** — an agent that counts nouns in the prompt gets both wrong. +**Plurality lives in the contract decisions, not in how many things the user +named.** An agent that counts nouns in the prompt fails this and S2 both. From c81e867e7c391637dbfaf64155664c93695ff08c Mon Sep 17 00:00:00 2001 From: Rahul Krishna Date: Tue, 4 Aug 2026 09:52:38 -0400 Subject: [PATCH 4/4] Gate on decomposition, not just the sweep The HARD-GATE required the collision sweep to have run. A sweep across undecomposed themes runs clean, reports no groups, and satisfies the gate -- while the collision it exists to catch is still there, just invisible. Gate now requires both halves: themes decomposed to contract-decision altitude AND the sweep run over the result. Restores the "'Microservice analysis' is one row" red flag, reworded to state the failure rather than repeat the instruction. The previous ponytail pass cut it as a duplicate of the loop prose; it was not -- it was the second guard on this hole, and the complexity review had no way to see that. Resolves the contradiction between "vagueness is fine and expected" and step 1's demand for decision altitude: vague wording is fine, vague altitude is not. --- skills/planning-cldk-work/SKILL.md | 21 ++++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/skills/planning-cldk-work/SKILL.md b/skills/planning-cldk-work/SKILL.md index f7de443..5ef406a 100644 --- a/skills/planning-cldk-work/SKILL.md +++ b/skills/planning-cldk-work/SKILL.md @@ -30,8 +30,9 @@ contract decision and the only open question is how its PRs sequence, that is `designing-cldk-changes`'s decomposition step, not a roadmap. Go L3/L4 on one analyzer is one decision; do not manufacture a roadmap for it. -Candidates may be vague. Vagueness is fine and expected — the collision sweep below -works on rough shapes. +Vague *wording* is fine and expected — the sweep works on rough shapes. Vague +*altitude* is not: a theme left whole has to be broken into the decisions it +contains before the sweep can compare anything (step 1). ## The Loop @@ -96,12 +97,17 @@ else. The roadmap records the rest; the tracker does not need to mirror it. ## -No candidate may enter `designing-cldk-changes` until the **collision sweep has run -and its group is known**. Designing a feature in isolation that shares vocabulary -with another candidate is the one planning mistake the parity clause makes -permanent — every other planning error is recoverable by re-planning. +No candidate may enter `designing-cldk-changes` until **every theme has been +decomposed to contract-decision altitude AND the collision sweep has run over the +result**. Both halves, or neither counts: a sweep across undecomposed themes runs +clean, reports no groups, and satisfies nothing — the collision is still there, just +invisible. -The gate is on the sweep, never on the roadmap's length or polish. +Designing a feature in isolation that shares vocabulary with another candidate is +the one planning mistake the parity clause makes permanent. Every other planning +error is recoverable by re-planning. + +The gate is on decomposition and the sweep, never on the roadmap's length or polish. ## Terminal State @@ -124,6 +130,7 @@ happen in a later session without losing anything. | "File all six epics so the board shows the quarter." | Six idle epics is inventory, and inventory rots. File the one you are starting; the roadmap records the rest. | | "These are separate features, design them separately." | Run the collision sweep first. Shared vocabulary decided twice is decided wrong, permanently. | | "Put the roadmap in a tracking issue so it's visible." | Docs carry content, trackers carry state. The roadmap is a committed doc; the Project board is the live view. | +| "'Microservice analysis' is one row on the roadmap." | It is a theme, not a decision. Undecomposed, the sweep runs clean and finds nothing — the gate passes and the collision ships anyway. | | "The user is busy; I'll group and order these myself." | Grouping and ordering are the user's calls. `AskUserQuestion`, never solo. | ## Scope Guard