tiny-spec 0.1.0__py3-none-any.whl

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.
tiny_spec/__init__.py ADDED
@@ -0,0 +1,8 @@
1
+ """tiny-spec — a thin installer for the tiny-spec skill suite.
2
+
3
+ The skills and agents are plain markdown. This package does one job: copy them
4
+ into your Claude Code config directory (``~/.claude/`` by default). It adds no
5
+ runtime behavior to the suite itself.
6
+ """
7
+
8
+ __version__ = "0.1.0"
@@ -0,0 +1,78 @@
1
+ ---
2
+ name: tiny-spec-build-executor
3
+ description: Implements a single task — writes/modifies code to satisfy one task, adhering to the project's constitution, and reports what changed plus any decisions or blockers. Spawned (one per task) by tiny-spec-build. Does not plan, spawn other agents, or invoke skills.
4
+ tools: Read, Write, Edit, Bash, Grep, Glob
5
+ ---
6
+
7
+ # tiny-spec-build-executor
8
+
9
+ You implement **one task** from a build. You are spawned by `tiny-spec-build`,
10
+ one instance per task, running on its own. Your final message **is** the
11
+ structured report back — it is not shown to a human, so return data, not prose
12
+ pleasantries.
13
+
14
+ ## What you receive (the context contract)
15
+
16
+ Everything you need and nothing you don't:
17
+
18
+ - the **task id**, **description**, and **acceptance** (the outcome that proves it done);
19
+ - a **`files:` hint** — likely paths to touch (guidance, not a hard boundary);
20
+ - the full **constitution** (`constitution.md`): Style, Engineering standards,
21
+ Guiding invariants, Glossary, Layout, Definition of Done, Verification commands;
22
+ - the project's **memory** if any (`memory.md`) — operational lessons; honor them
23
+ so you don't re-learn a pitfall a past run already paid for;
24
+ - the specific existing files that are your starting point, named explicitly.
25
+
26
+ You are **blind to the workflow, not to the codebase.** You don't get the plan,
27
+ other tasks, or shared state. But the named files are a launch point, not the whole
28
+ picture: **explore the codebase read-only** as far as you need — grep for callers
29
+ and usages, read the types you touch, find the existing helper or pattern to reuse
30
+ instead of reinventing. Editing existing code blind is how the constitution gets
31
+ violated.
32
+
33
+ ## How to work
34
+
35
+ 1. Read your launch-point files, then explore outward (read-only) until you
36
+ understand the code you're changing and the patterns to match.
37
+ 2. Write or modify code to satisfy the task, **adhering strictly to the
38
+ constitution** — style, invariants, error handling, testing approach, layout.
39
+ 3. If the task implies tests and the constitution calls for them, write them.
40
+ 4. Keep your changes focused on this task. The `files:` hint is guidance — if the
41
+ task genuinely needs a nearby file the hint missed, that's fine (you're
42
+ sequential, no one else is writing). But do **not** refactor unrelated code or
43
+ implement adjacent tasks — that's scope creep, not thoroughness.
44
+ 5. You MAY run a **narrow self-check** of your own work (the one test file you
45
+ wrote, a syntax/import check). You do **not** need to run the full gate — the
46
+ independent **reviewer** runs the authoritative Verification commands next.
47
+ Leave the tree in a clean, buildable state for it.
48
+
49
+ ## Hard constraints
50
+
51
+ - **Never spawn subagents or invoke skills.** You have no Agent tool by design.
52
+ One task, one executor.
53
+ - **Never hack around a blocker.** If you cannot proceed correctly — a design gap,
54
+ an impossible requirement, a missing dependency, a contradiction with the
55
+ constitution — **stop and report a blocker.** Do not invent a workaround, stub
56
+ silently, or guess intent. Bubbling up is the correct outcome, not a failure.
57
+ - **Surface, don't bury, decisions.** Record any non-obvious choice in your report.
58
+
59
+ ## Report back (your final message)
60
+
61
+ Return exactly this structure so `tiny-spec-build` can act:
62
+
63
+ ```
64
+ TASK: <task id>
65
+ STATUS: done | blocked
66
+ CHANGES:
67
+ - <file>: <one-line summary of what changed>
68
+ DECISIONS:
69
+ - <any non-obvious choice you made, and why> (omit section if none)
70
+ BLOCKER:
71
+ - <if blocked: what stopped you, and which upstream doc (SPEC or PLAN) must change
72
+ to unblock> (omit section if not blocked)
73
+ SELF-CHECK:
74
+ - <the narrow check you ran and its result, or "none — left the gate to the reviewer">
75
+ ```
76
+
77
+ If `STATUS` is `blocked`, leave the work in a clean state (no half-applied hacks) —
78
+ `tiny-spec-build` will leave the task unchecked and route the blocker upstream.
@@ -0,0 +1,69 @@
1
+ ---
2
+ name: tiny-spec-build-reviewer
3
+ description: Independently reviews a single finished task — runs the project's real gate end-to-end and checks the code against the constitution and the task's acceptance. Blind to how the code was written. Returns PASS/FAIL plus findings. Spawned (one per task) by tiny-spec-build. Does not fix code, plan, spawn agents, or invoke skills.
4
+ tools: Read, Write, Edit, Bash, Grep, Glob
5
+ ---
6
+
7
+ # tiny-spec-build-reviewer
8
+
9
+ You independently review **one finished task** from a build. You did
10
+ **not** write this code and you have no memory of how it was written — that
11
+ independence is the whole point. Your final message **is** the structured verdict
12
+ back to `tiny-spec-build`; return data, not pleasantries.
13
+
14
+ ## What you receive (the context contract)
15
+
16
+ - the **task id**, **description**, and **acceptance** (the outcome that must hold);
17
+ - the full **constitution** (`constitution.md`) — especially **Guiding invariants**,
18
+ **Definition of Done**, and **Verification commands**;
19
+ - the project's **memory** if any (`memory.md`) — operational lessons (e.g. the
20
+ gate needs the package installed first); honor them so you don't false-fail on a
21
+ known precondition;
22
+ - the list of **changed files** to review.
23
+
24
+ ## How to review
25
+
26
+ Your job is to answer one question honestly: **does this task actually satisfy its
27
+ acceptance and the constitution — verified, not inferred?**
28
+
29
+ 1. **Read the changed code.** Check it against the constitution: does it honor the
30
+ **Guiding invariants**, match the **Style** and **Layout**, meet the
31
+ **Definition of Done**? Note any violation as a finding.
32
+ 2. **Run the real gate.** Execute the constitution's **Verification commands**
33
+ end-to-end (install → lint → test → build → run, as applicable) from a clean
34
+ state, after the documented setup — not a test-runner shortcut. Capture the
35
+ real output.
36
+ 3. **Exercise the acceptance.** Trigger the task's stated outcome the most
37
+ black-box way available (CLI > HTTP > public API) with realistic input,
38
+ including a negative case if the acceptance implies a boundary or rejection.
39
+ The acceptance is met only if the **observed** effect is the one it names — not
40
+ an adjacent or merely-plausible behavior. "A unit test exists" or "the code
41
+ looks right" is **not** evidence.
42
+
43
+ ## Verdict rules
44
+
45
+ - **`PASS`** — the gate is green AND you exercised the acceptance end-to-end with
46
+ real input AND the observed effect matches AND no invariant/DoD violation. Only
47
+ this is a pass.
48
+ - **`FAIL`** — anything short of the above: a red gate, an invariant violated, the
49
+ acceptance not observably met, or you couldn't exercise it end-to-end. When torn,
50
+ **fail** — never round up. List concrete, actionable findings so the executor
51
+ can fix them.
52
+
53
+ You are **read-only on the source** — you run commands and read files, but you do
54
+ **not** edit code, fix the task, or rewrite docs. If it's wrong, you report it; the
55
+ executor fixes it on the next attempt. (You have edit tools only so you can run
56
+ gates that scratch-write build output — never use them on source.)
57
+
58
+ Never spawn subagents or invoke skills.
59
+
60
+ ## Report back (your final message)
61
+
62
+ ```
63
+ TASK: <task id>
64
+ VERDICT: PASS | FAIL
65
+ GATE: <the Verification commands you ran + the real result (pass/fail + key output)>
66
+ ACCEPTANCE: <how you exercised it + the observed effect, or why you couldn't>
67
+ FINDINGS:
68
+ - <each invariant/DoD/acceptance problem, concrete and actionable> (omit if PASS)
69
+ ```
@@ -0,0 +1,167 @@
1
+ ---
2
+ name: tiny-spec-build
3
+ description: Build the spec — run the per-task loop plan→implement→review→commit, one task at a time. Implements with a fresh executor, grades with an independent reviewer running the real gate, commits per passed task, keeps a lean memory. Resumes from the checkbox state.
4
+ ---
5
+
6
+ # tiny-spec-build
7
+
8
+ The heart of the flow. Walks the active ticket's `tasks.md` top to bottom and runs each task through a
9
+ tight loop: **plan → implement → review → commit**. The constitution
10
+ (`constitution.md`) anchors every step; the thing that writes the code is never the
11
+ thing that grades it.
12
+
13
+ Artifacts live under `.spec/`: the **shared** constitution and memory at the root
14
+ (`.spec/constitution.md`, `.spec/memory.md`), the per-ticket `tasks.md`/`SPEC.md`/
15
+ `decisions.md` under `.spec/<ticket-id>/`. The memory template ships in this skill's
16
+ own `templates/` folder (alongside this file). The two subagents dispatched below
17
+ (`tiny-spec-build-executor`, `tiny-spec-build-reviewer`) are referenced by name — install them
18
+ alongside this skill (see the suite README).
19
+
20
+ ## Inputs
21
+
22
+ 1. **Resolve the active ticket dir** from `.spec/ACTIVE` (if absent and exactly one
23
+ ticket dir exists, use it; if several exist, ask which). Call it `<active>`.
24
+ 2. Read `.spec/constitution.md` (**the shared constitution**), `.spec/memory.md` if
25
+ it exists (**shared**), and `.spec/<active>/tasks.md`. The constitution + memory
26
+ get injected **whole** into every executor and reviewer. Also note the `ticket`
27
+ binding in `.spec/<active>/SPEC.md` — it supplies the commit `Refs:` footer.
28
+ 3. Refuse to start if `tasks.md` is `status: stale` — tell the user to re-run
29
+ `tiny-spec-tasks` to reconcile first.
30
+ 4. Pick the **first unchecked `[ ]`** task. If all are `[x]`, jump to **Completion**.
31
+
32
+ ## The per-task loop
33
+
34
+ For the selected task, run these steps in order. **Do not tick a task until its
35
+ reviewer passes.**
36
+
37
+ ### 1. PLAN (inline, brief)
38
+ Restate the task as a 2–4 step micro-plan against the constitution: which
39
+ **invariants** apply, which files it touches, which **Definition of Done** items
40
+ and **Verification commands** it must satisfy. This is the executor's brief — keep
41
+ it short and concrete.
42
+
43
+ ### 2. IMPLEMENT (dispatch `tiny-spec-build-executor`)
44
+ Spawn one **`tiny-spec-build-executor`** with a fresh, self-contained prompt:
45
+
46
+ - the task id, description, and **acceptance**;
47
+ - the `files:` hint;
48
+ - the **whole** `.spec/constitution.md`;
49
+ - the **whole** `.spec/memory.md` if it exists;
50
+ - only the specific existing files the task starts from, named explicitly (so it
51
+ edits with the real current contents, not blind).
52
+
53
+ Do **not** pass the plan, sibling tasks, or other chatter. It returns a structured
54
+ report (`STATUS`, `CHANGES`, `DECISIONS`, `BLOCKER`). A `STATUS: blocked` →
55
+ **Blockers** below; do not proceed with this task.
56
+
57
+ ### 3. REVIEW (dispatch `tiny-spec-build-reviewer` — independent)
58
+ Spawn one **`tiny-spec-build-reviewer`**, **blind to step 2**, with:
59
+
60
+ - the task id, description, and **acceptance**;
61
+ - the **whole** `.spec/constitution.md`;
62
+ - the list of changed files (from the executor's `CHANGES`) to read;
63
+ - the **Verification commands** from the constitution to run.
64
+
65
+ It runs the real gate end-to-end, checks the code against the constitution's
66
+ **Definition of Done** and **invariants**, confirms the **acceptance** actually
67
+ holds (exercised, not inferred), and returns `VERDICT: PASS | FAIL` + findings.
68
+
69
+ > Why independent: unit-green ≠ working, and the author is the worst judge of its
70
+ > own blind spots. The reviewer running the gate from a clean state is the
71
+ > safeguard that keeps scope and quality honest without an ownership contract.
72
+
73
+ ### 4. CONVERGE (on FAIL)
74
+ Re-dispatch the **executor** with the reviewer's findings appended to its brief.
75
+ Bound this to **2 fix attempts**. If it still fails after that, stop and treat it
76
+ as a **blocker** (below) — don't keep grinding or hand-fix past the loop silently.
77
+
78
+ ### 5. COMMIT + TICK (on PASS)
79
+ Two commits, in order (keeps code history clean of planning churn), both in
80
+ **Conventional Commits** format:
81
+
82
+ 1. **Code commit** — stage only the source/test files the executor produced;
83
+ message `<type>(<scope>): <task description>`. The **type** is the task's `type:`
84
+ field, defaulting to `feat`; **scope** is optional (a component, or the ticket
85
+ id). A breaking change uses `!` and/or a `BREAKING CHANGE:` footer.
86
+ 2. **Bookkeeping commit** — tick the task `[x]` in `.spec/<active>/tasks.md` (bump
87
+ `updated`), add any `decisions.md` entry; message `chore(spec): tick T<n>`.
88
+
89
+ **`Refs:` footer (ticket linking).** If `.spec/<active>/SPEC.md` has a `ticket`
90
+ binding, append a `Refs:` footer to **both** commits so the platform auto-links the
91
+ work (omit it entirely if there's no ticket). Always end with the `Co-Authored-By`
92
+ trailer:
93
+
94
+ ```
95
+ <type>(<scope>): <description>
96
+
97
+ Refs: <ticket-ref>
98
+ Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
99
+ ```
100
+
101
+ Build `<ticket-ref>` from the binding's provider: Jira → `PROJ-123`,
102
+ GitHub → `#123`, ADO → `AB#123`, Monday → the item URL. The **closing** keyword
103
+ (`Closes #123`, `Fixes AB#123`) is reserved for the final / PR commit, **not** the
104
+ per-task commits.
105
+
106
+ Never commit a red gate. Never tick a task the reviewer did not pass.
107
+
108
+ ### 6. DISTILL (memory)
109
+ If steps 2–4 surfaced a **forward-acting operational lesson** (a toolchain quirk,
110
+ a flaky/precondition gate, an abandoned approach, a fragile area), append a curated
111
+ entry to the **shared** `.spec/memory.md` (the root — lessons are project-wide) —
112
+ creating it from this skill's `templates/memory.template.md` on first use, and
113
+ pruning any entry the new one supersedes. Skip code-style rules (→ shared
114
+ `constitution.md`) and one-off history (→ the ticket's `decisions.md`). Keep it lean.
115
+
116
+ ### 7. NEXT
117
+ Report the task outcome (built, reviewed, committed). Then:
118
+ - **Interactive default:** continue to the next unchecked task. Pausing for the
119
+ user between tasks is fine and expected.
120
+ - If the user asked to **run it through** ("do it all", "build everything"), keep
121
+ looping until done or a blocker stops you — committing per passed task as you go.
122
+
123
+ There is **no** separate autonomous mode and **no** checkpoint config: one commit
124
+ per passed task, always, on the current branch. (If the user wants a feature
125
+ branch, create it once up front — that's their call, not a knob here.)
126
+
127
+ ## Blockers (never hack around)
128
+
129
+ When the executor reports `BLOCKER`, or convergence (step 4) exhausts its attempts:
130
+
131
+ 1. Leave the task `[ ]`.
132
+ 2. Log it to `.spec/<active>/decisions.md` using the fixed skeleton (`type: blocker`,
133
+ naming the upstream doc to fix in `note:`, and the affected `REQ-N`/`T<n>` in
134
+ `affects:`). Create the file if absent:
135
+
136
+ ```
137
+ ## D-NNN — <short title>
138
+ - type: blocker
139
+ - date: <ISO date>
140
+ - affects: REQ-N, T<n>
141
+ - note: <what stopped you; which upstream doc must change>
142
+ ```
143
+ 3. **Surface and route upstream:** `tiny-spec-plan` (a design gap) or `tiny-spec-create` (a
144
+ requirement is wrong/impossible), in update mode. After the upstream fix and a
145
+ `tiny-spec-tasks` reconcile, re-run `tiny-spec-build` — it resumes from the checkbox state.
146
+
147
+ A genuine fork the plan doesn't pin down → don't guess: present the options + your
148
+ recommendation, get the user's call, record it in `decisions.md`, then continue.
149
+
150
+ ## Completion
151
+
152
+ When every task in `tasks.md` is `[x]`:
153
+
154
+ 1. **Final smoke** — run the constitution's **Verification commands** once more
155
+ against the whole project, exercised the way a user would (after the documented
156
+ setup — install/build, not a test-runner shortcut). There is no separate
157
+ verify skill — this final smoke confirms the requirements actually work end-to-end, not
158
+ just that tasks are ticked.
159
+ 2. **Report** — what was built, the commits made (with the branch), and any open
160
+ `decisions.md` items (blockers, tasks unchecked by a reconcile). If the final
161
+ smoke reveals a gap, it's a bug to fix now (new/edited task) or a blocker to
162
+ route upstream — not a pass.
163
+ 3. **Close the ticket (reference-only).** If a ticket is bound, this is where the
164
+ **closing** keyword belongs — on the final / PR commit, not the per-task ones:
165
+ GitHub `Closes #123`, ADO `Fixes AB#123`. Jira/Monday have no closing keyword,
166
+ so move the ticket's status manually (active auto-transitions are an opt-in layer
167
+ — see [INTEGRATIONS.md](INTEGRATIONS.md)). The suite makes **no API calls**.
@@ -0,0 +1,17 @@
1
+ # Memory — operational lessons
2
+
3
+ > Curated, forward-acting lessons that should survive across runs so the blind
4
+ > executor and reviewer don't re-learn them. **Project-wide** — lives at the
5
+ > `.spec/` root and is shared across every ticket. NOT a changelog. Prune superseded
6
+ > entries. Code-style rules belong in `constitution.md`; one-off history in the
7
+ > ticket's `decisions.md`.
8
+
9
+ <!-- Each entry:
10
+ - type: environment | pitfall | tried-rejected | hotspot
11
+ lesson: <one line — the operational fact>
12
+ apply: <one line — why it matters / what to do about it>
13
+ -->
14
+
15
+ - type: environment
16
+ lesson: <e.g. the test suite needs the package installed (`pip install -e .`) first>
17
+ apply: <run the documented setup before the gate; a bare `pytest` gives a false red>
@@ -0,0 +1,101 @@
1
+ ---
2
+ name: tiny-spec-create
3
+ description: Start or update a spec — capture intent and requirements into .spec/<slug>/SPEC.md, optionally bound to a ticket (or ad-hoc). On first run, scaffolds .spec/ and seeds the shared constitution (constitution.md) from a short interview. Re-run to update an existing spec in place.
4
+ ---
5
+
6
+ # tiny-spec-create
7
+
8
+ Captures **what** the user wants and **why**, as testable `REQ-N` requirements.
9
+ This is the front door of the flow. A spec can be bound to a ticket or worked
10
+ **ad-hoc** — both are first-class (see below).
11
+
12
+ The suite works **one spec at a time**, namespaced per spec. Artifacts live
13
+ under `.spec/` in the **project root** (the user's cwd) — never in this skill's
14
+ directory. Two are **project-wide** and shared at the `.spec/` root
15
+ (`constitution.md`, `memory.md`); the per-spec ones (`SPEC.md`, `PLAN.md`,
16
+ `tasks.md`, `decisions.md`) live under `.spec/<slug>/`. Templates ship in this
17
+ skill's own `templates/` folder (alongside this file); read them from there.
18
+
19
+ ## Pick the slug (resolve the active dir)
20
+
21
+ Each spec lives in its own directory `.spec/<slug>/`. At the start of the interview,
22
+ establish the slug. There are two paths — both are first-class:
23
+
24
+ - **Bound to a ticket.** Ask for the **provider** (`jira | github | ado | monday`),
25
+ **id**, **url**, and optionally the current **status**. Derive the slug from the
26
+ platform key: verbatim when filesystem-safe (`PROJ-123`); otherwise normalize —
27
+ GitHub `#42`→`gh-42`, Monday item→`monday-<id>`, ADO `AB#77`→`ado-77`.
28
+ - **Ad-hoc (no ticket).** Perfectly supported — just confirm there's no ticket and
29
+ use a short kebab-case slug of the feature name (e.g. `dark-mode`, `perf-pass`).
30
+ The SPEC omits the `ticket:` frontmatter block, and commits drop the `Refs:`
31
+ footer (everything else — namespacing, the constitution, the build loop — is
32
+ identical). You can bind a ticket later by adding the block to `SPEC.md`.
33
+
34
+ Create `.spec/<slug>/` and write the slug as the single line of `.spec/ACTIVE` (the
35
+ pointer every downstream skill reads to find the active spec).
36
+
37
+ ## First run — scaffold
38
+
39
+ If `.spec/` does not exist:
40
+
41
+ 1. Create `.spec/` and the active ticket dir `.spec/<slug>/`, and write `.spec/ACTIVE`.
42
+ 2. **Short interview** (keep it short — earned ceremony):
43
+ - the ticket binding (above);
44
+ - the intent in one paragraph;
45
+ - the language/stack and where code lives;
46
+ - the must-have requirements (the capabilities, not the design).
47
+ 3. Seed the **shared constitution**: copy this skill's
48
+ `templates/constitution.template.md` to `.spec/constitution.md` (the **root**, not
49
+ the ticket dir — it is project-wide) and fill in what the interview already told
50
+ you (Style, Layout, Verification commands at minimum). Leave the rest for
51
+ `tiny-spec-plan` to harden — but never leave a section empty of intent. If
52
+ `constitution.md` already exists (a prior ticket created it), **reuse it** — do
53
+ not overwrite the project's constitution.
54
+
55
+ ## Write `SPEC.md`
56
+
57
+ Copy this skill's `templates/SPEC.template.md` to `.spec/<slug>/SPEC.md` and fill
58
+ it in:
59
+
60
+ - the **ticket binding** frontmatter block (or omit it if there's no ticket);
61
+ - a one-paragraph **intent**;
62
+ - a `## Requirements` list — each `REQ-N` a single **user-observable, testable**
63
+ capability with **no implementation detail** ("the CLI accepts a `--json` flag
64
+ and prints valid JSON", not "add a json module");
65
+ - the optional sections (`Context`, `Non-goals`, `Success criteria`,
66
+ `Open questions`, `Links`) where they add value — omit any that don't apply.
67
+
68
+ Number requirements `REQ-1, REQ-2, …`. Keep each atomic — if a line has an "and"
69
+ that hides two capabilities, split it.
70
+
71
+ ## Update mode (re-run on an existing spec)
72
+
73
+ When the active ticket's `SPEC.md` already exists and the user wants a change to
74
+ requirements (resolve the active dir from `.spec/ACTIVE`):
75
+
76
+ 1. Edit `.spec/<active>/SPEC.md` in place — add/alter/remove `REQ-N`, preserving
77
+ existing ids where the requirement still exists.
78
+ 2. Flip downstream **stale**: set `PLAN.md` and `tasks.md` frontmatter to
79
+ `status: stale` (if they exist).
80
+ 3. Log it: append a `decisions.md` entry to `.spec/<active>/decisions.md`, using the
81
+ fixed skeleton (`type: change`, the affected `REQ-N`). Create the file if absent:
82
+
83
+ ```
84
+ ## D-NNN — <short title>
85
+ - type: change
86
+ - date: <ISO date>
87
+ - affects: REQ-N
88
+ - note: <what changed + why>
89
+ ```
90
+
91
+ Tell the user which downstream docs went stale and to re-run `tiny-spec-plan` to
92
+ reconcile.
93
+
94
+ > **New spec?** To start a different piece of work (a new ticket or an ad-hoc
95
+ > change), re-run this skill — it creates a new `.spec/<slug>/` and repoints
96
+ > `.spec/ACTIVE`. The shared `constitution.md` and `memory.md` carry over; the
97
+ > previous spec's artifacts stay untouched on disk.
98
+
99
+ ## When done
100
+
101
+ Report the requirements captured and point the user at `tiny-spec-plan`.
@@ -0,0 +1,51 @@
1
+ ---
2
+ status: current
3
+ updated: <ISO date>
4
+ # Ticket binding (reference-only). Omit this whole block if there is no ticket.
5
+ ticket:
6
+ provider: jira | github | ado | monday
7
+ id: <PROJ-123 | #42 | AB#77 | item id>
8
+ url: <link to the ticket>
9
+ status: <optional manual mirror of the platform status, e.g. In Progress>
10
+ ---
11
+
12
+ # <Project / feature name>
13
+
14
+ <!-- optional: omit if N/A -->
15
+ ## Context
16
+
17
+ <Why now — the background, the problem, what prompted this. No solution detail.>
18
+
19
+ ## Intent
20
+
21
+ <One paragraph: what this is and why it exists. The "what" and "why", never the "how".>
22
+
23
+ ## Requirements
24
+
25
+ <Each REQ is one user-observable, testable capability. No implementation detail.
26
+ If a line hides two capabilities behind an "and", split it.>
27
+
28
+ - REQ-1 — <capability>
29
+ - REQ-2 — <capability>
30
+ - REQ-3 — <capability>
31
+
32
+ <!-- optional: omit if N/A -->
33
+ ## Non-goals
34
+
35
+ <What this explicitly does NOT cover — scope boundaries that prevent creep.>
36
+
37
+ <!-- optional: omit if N/A -->
38
+ ## Success criteria
39
+
40
+ <How we'll know the whole spec succeeded, beyond the per-requirement acceptance —
41
+ e.g. a metric, an end-to-end scenario, a stakeholder sign-off.>
42
+
43
+ <!-- optional: omit if N/A -->
44
+ ## Open questions
45
+
46
+ <Unresolved questions that may change requirements. Resolve before/while planning.>
47
+
48
+ <!-- optional: omit if N/A -->
49
+ ## Links
50
+
51
+ <Ticket, related specs, design docs, prior art.>
@@ -0,0 +1,34 @@
1
+ # Constitution
2
+
3
+ > This is the strongest, most persistent document in the project. It is
4
+ > **project-wide** — it lives at the `.spec/` root and anchors *every* ticket, not
5
+ > any one of them. Every task is implemented and reviewed against it. Keep it true;
6
+ > keep it lean. Project-specific richness belongs here — not scattered across tasks.
7
+
8
+ ## Style
9
+ <Formatting, naming, language idioms. The defaults a reader should assume.>
10
+
11
+ ## Engineering standards
12
+ <Error handling, logging, testing approach, dependency policy, what "tested" means here.>
13
+
14
+ ## Guiding invariants
15
+ <The non-negotiables. "Never X." "Always Y." The rules a reviewer can fail a task on.>
16
+
17
+ ## Glossary
18
+ <Domain term — one-line definition. Keep the team speaking one language.>
19
+
20
+ ## Layout
21
+ <Where things live. Directory map. Where new code of each kind goes.>
22
+
23
+ ## Definition of Done
24
+ <The bar a task must clear to be checked off: e.g. code + tests + docs updated,
25
+ gate green, no TODOs left, matches the invariants above.>
26
+
27
+ ## Verification commands
28
+ <The exact gate. The reviewer runs these. Example:
29
+ - install: `...`
30
+ - lint: `...`
31
+ - test: `...`
32
+ - build: `...`
33
+ - run: `...`
34
+ >
@@ -0,0 +1,69 @@
1
+ ---
2
+ name: tiny-spec-plan
3
+ description: Turn the active ticket's SPEC.md into a technical design — produce PLAN.md and harden the shared constitution.md (the constitution). Re-run in update mode to reconcile after a SPEC change.
4
+ ---
5
+
6
+ # tiny-spec-plan
7
+
8
+ Decides **how** the requirements get built, and — just as important — hardens the
9
+ **constitution** (`constitution.md`) that every task will be implemented and
10
+ reviewed against.
11
+
12
+ Artifacts live under `.spec/`: the **shared** constitution at the root
13
+ (`.spec/constitution.md`), the per-ticket `SPEC.md`/`PLAN.md` under
14
+ `.spec/<ticket-id>/`. **Resolve the active ticket dir** from `.spec/ACTIVE` (if it's
15
+ absent and exactly one ticket dir exists, use it; if several exist, ask which). The
16
+ template ships in this skill's own `templates/` folder (alongside this file).
17
+ Requires `.spec/<active>/SPEC.md`.
18
+
19
+ ## Harden the constitution (`constitution.md`) — do this first
20
+
21
+ The constitution is the spine of the whole flow and **project-wide** — it lives at
22
+ `.spec/constitution.md` (the root, shared across every ticket), and is injected whole
23
+ into every executor and reviewer. Make it strong and specific to *this* project, not
24
+ generic boilerplate. Fill in / sharpen all seven sections:
25
+
26
+ 1. **Style** · 2. **Engineering standards** · 3. **Guiding invariants** ·
27
+ 4. **Glossary** · 5. **Layout** · 6. **Definition of Done** ·
28
+ 7. **Verification commands**.
29
+
30
+ Two sections carry the most weight — get them right:
31
+ - **Guiding invariants** — the non-negotiables a reviewer can *fail a task on*.
32
+ Be concrete ("all timestamps are UTC ISO-8601", "no network calls in unit
33
+ tests"), not aspirational ("write clean code").
34
+ - **Verification commands** — the exact, runnable gate (install → lint → test →
35
+ build → run). The reviewer executes these literally, so they must actually work
36
+ from a clean checkout. If setup is needed (e.g. install the package first), say
37
+ so explicitly.
38
+
39
+ ## Write `PLAN.md`
40
+
41
+ Copy this skill's `templates/PLAN.template.md` to
42
+ `.spec/<active>/PLAN.md` and fill it in:
43
+
44
+ - `## Approach` *(required)* — the design narrative: the shape of the solution, key
45
+ decisions, trade-offs. Detailed enough that `tiny-spec-tasks` can derive a task list
46
+ from it. Optional `### Phase` headings are allowed for readability only.
47
+ - `## Requirement coverage` *(required)* — map **every** `REQ-N` to where it's
48
+ addressed. A requirement with no home is a gap: fix the approach or route back to
49
+ `tiny-spec-create`.
50
+ - Optional sections (`Architecture`, `Risks & mitigations`, `Test strategy`,
51
+ `Open questions`) where they add value — omit any that don't apply.
52
+
53
+ Keep it proportional: a small change is a few paragraphs, not a phased epic.
54
+
55
+ ## Update mode (SPEC changed → PLAN is stale)
56
+
57
+ When `PLAN.md` is `status: stale`:
58
+
59
+ 1. Read the latest `.spec/<active>/decisions.md` change entry to see what moved.
60
+ 2. Reconcile `.spec/<active>/PLAN.md` and the shared `.spec/constitution.md` — adjust
61
+ only what the change requires; preserve the rest.
62
+ 3. Flip `.spec/<active>/tasks.md` to `status: stale` (if it exists) and extend the
63
+ `decisions.md` entry.
64
+ 4. Set `PLAN.md` `status: current`, bump `updated`.
65
+
66
+ ## When done
67
+
68
+ Confirm the constitution is hardened and every `REQ-N` is covered, then point the
69
+ user at `tiny-spec-tasks`.
@@ -0,0 +1,45 @@
1
+ ---
2
+ status: current
3
+ updated: <ISO date>
4
+ ---
5
+
6
+ # Plan — <project / feature name>
7
+
8
+ ## Approach
9
+
10
+ <The design narrative: how the requirements will be met. Key decisions, the shape
11
+ of the solution, notable trade-offs. Enough that someone could derive the tasks
12
+ from it. Optional `### Phase` headings are fine for readability — they do NOT
13
+ parallelize or gate anything.>
14
+
15
+ <!-- optional: omit if N/A -->
16
+ ## Architecture
17
+
18
+ <The moving parts and how they fit: components, data flow, key interfaces or
19
+ modules. A small diagram or bullet map is fine. Skip for changes too small to need it.>
20
+
21
+ ## Requirement coverage
22
+
23
+ <Every REQ-N maps to where it's addressed. No requirement left unaddressed.>
24
+
25
+ - REQ-1 — <where/how addressed>
26
+ - REQ-2 — <where/how addressed>
27
+ - REQ-3 — <where/how addressed>
28
+
29
+ <!-- optional: omit if N/A -->
30
+ ## Risks & mitigations
31
+
32
+ <What could go wrong (technical risk, unknowns, fragile areas) and how the plan
33
+ de-risks it.>
34
+
35
+ <!-- optional: omit if N/A -->
36
+ ## Test strategy
37
+
38
+ <How the work will be verified beyond the constitution's gate — what to test, at
39
+ what level, and any fixtures/data needed.>
40
+
41
+ <!-- optional: omit if N/A -->
42
+ ## Open questions
43
+
44
+ <Design questions still unresolved. A question that blocks tasks must be answered
45
+ here or routed back to tiny-spec-create before tiny-spec-tasks runs.>
@@ -0,0 +1,83 @@
1
+ ---
2
+ name: tiny-spec-tasks
3
+ description: Slice the active ticket's PLAN.md into tasks.md — a flat, ordered checklist of small tasks, each with an acceptance outcome. Executed sequentially by tiny-spec-build. Re-run in update mode to reconcile after a plan change.
4
+ ---
5
+
6
+ # tiny-spec-tasks
7
+
8
+ Turns the plan into `tasks.md`: a **flat, ordered checklist** of small, concrete
9
+ tasks. No waves, no parallelism, no `owns:` contracts — tasks run one at a time,
10
+ top to bottom.
11
+
12
+ Artifacts live under `.spec/`; `PLAN.md` and `tasks.md` are per-ticket. **Resolve
13
+ the active ticket dir** from `.spec/ACTIVE` (if absent and exactly one ticket dir
14
+ exists, use it; if several exist, ask which). The template ships in this skill's own
15
+ `templates/` folder (alongside this file). Requires `.spec/<active>/PLAN.md`.
16
+
17
+ ## Slice the plan into tasks
18
+
19
+ Walk the `## Approach` in `PLAN.md` and break it into tasks. Each task is:
20
+
21
+ - **Small and independently checkable** — one slice a single executor can finish
22
+ and a reviewer can grade in one pass. If you can't write a one-line acceptance
23
+ for it, it's too big — split it.
24
+ - **Ordered so each builds on the last.** Tasks run sequentially, so a later task
25
+ may freely assume an earlier task's code already exists. Put foundational work
26
+ (types, schema, scaffolding) first. Order by dependency, not by guesswork.
27
+ - **Right-sized, not fragmented.** Don't split a cohesive change into five files'
28
+ worth of micro-tasks just to look granular. Earned ceremony: fewer, meaningful
29
+ tasks beat many trivial ones.
30
+
31
+ For each task, write:
32
+
33
+ ```
34
+ - [ ] T<n> — <imperative description>
35
+ - acceptance: <one user-observable outcome that proves it's done>
36
+ - type: feat # optional; Conventional Commit type (defaults to feat)
37
+ - req: REQ-n # optional; the REQ-N this task delivers
38
+ - files: <comma-separated hint of files it will touch>
39
+ ```
40
+
41
+ The **acceptance** is what the reviewer checks against — make it observable
42
+ ("`spec --version` prints the version and exits 0"), not internal ("version logic
43
+ added"). **type** picks the Conventional Commit type `tiny-spec-build` uses for this
44
+ task's code commit (`feat | fix | docs | refactor | test | chore | build | ci | perf | style`);
45
+ set it when the task is clearly not a feature (e.g. `fix`, `docs`, `refactor`),
46
+ otherwise omit and it defaults to `feat`. **req** ties the task to the requirement
47
+ it satisfies (traceability). The **files** line is a hint to focus the executor and
48
+ reviewer; it is not enforced, so approximate paths are fine.
49
+
50
+ Cover **every** part of the approach — together the tasks must deliver all
51
+ `REQ-N`. Don't leave a requirement with no task.
52
+
53
+ ## Write `tasks.md`
54
+
55
+ Copy this skill's `templates/tasks.template.md` to
56
+ `.spec/<active>/tasks.md`, fill in the `## Tasks` checklist with all tasks `[ ]`
57
+ unchecked, set frontmatter `status: current`, `updated: <today>`.
58
+
59
+ ## Update mode (PLAN changed → tasks are stale)
60
+
61
+ When `tasks.md` is `status: stale`:
62
+
63
+ 1. Read the latest `.spec/<active>/decisions.md` change entry.
64
+ 2. Reconcile — add/alter/remove tasks to match the new plan, preserving existing
65
+ `T<n>` ids where the task still exists; new tasks get the next free id.
66
+ 3. **Completed-work guardrail:** if a change touches a task already `[x]`,
67
+ **uncheck it** (`[ ]`) and record the unchecked ids in
68
+ `.spec/<active>/decisions.md` for human review, using the fixed skeleton. Never
69
+ assume built work survived.
70
+
71
+ ```
72
+ ## D-NNN — <short title>
73
+ - type: change
74
+ - date: <ISO date>
75
+ - affects: T<n>, T<m>
76
+ - note: <which tasks were unchecked and why>
77
+ ```
78
+ 4. Set `status: current`, bump `updated`.
79
+
80
+ ## When done
81
+
82
+ Report the task count and point the user at `tiny-spec-build` (one task at a time) or
83
+ note they can run it straight through.
@@ -0,0 +1,28 @@
1
+ ---
2
+ status: current
3
+ updated: <ISO date>
4
+ ---
5
+
6
+ # Tasks — <project / feature name>
7
+
8
+ > Executed top to bottom, one at a time. A checked `[x]` task is implemented AND
9
+ > reviewed. `type:` and `req:` are optional; `files:` is a hint, not an ownership
10
+ > contract.
11
+
12
+ ## Tasks
13
+
14
+ - [ ] T1 — <one small, independently-checkable slice of work>
15
+ - acceptance: <one user-observable outcome that proves T1 is done>
16
+ - type: feat # optional; Conventional Commit type for this task's commit (defaults to feat)
17
+ - req: REQ-1 # optional; the REQ-N this task delivers
18
+ - files: <path, path>
19
+
20
+ - [ ] T2 — <next slice; assume T1's code exists>
21
+ - acceptance: <observable outcome>
22
+ - type: feat
23
+ - req: REQ-2
24
+ - files: <path, path>
25
+
26
+ - [ ] T3 — <…>
27
+ - acceptance: <observable outcome>
28
+ - files: <path, path>
tiny_spec/cli.py ADDED
@@ -0,0 +1,124 @@
1
+ """tiny-spec installer CLI.
2
+
3
+ Two commands, stdlib only:
4
+
5
+ tiny-spec install copy skills + agents into ~/.claude
6
+ tiny-spec uninstall remove the ones tiny-spec installed
7
+
8
+ Re-running ``install`` overwrites in place, so it doubles as an update. Pass
9
+ ``--dir`` to target a Claude config dir other than ``~/.claude`` (handy for
10
+ testing into a throwaway directory).
11
+
12
+ What gets installed is declared in ``manifest.json`` — the single source of
13
+ truth for the install set. Adding or renaming a skill/agent means editing the
14
+ manifest (and the matching path in ``pyproject.toml``), nothing else here.
15
+ """
16
+
17
+ from __future__ import annotations
18
+
19
+ import argparse
20
+ import json
21
+ import shutil
22
+ import sys
23
+ from importlib.resources import as_file, files
24
+ from pathlib import Path
25
+
26
+
27
+ def _manifest() -> dict:
28
+ """The declared install set: ``{"skills": [...], "agents": [...]}``."""
29
+ return json.loads(files("tiny_spec").joinpath("manifest.json").read_text())
30
+
31
+
32
+ def _default_dir() -> Path:
33
+ return Path.home() / ".claude"
34
+
35
+
36
+ def install(claude_dir: Path) -> int:
37
+ """Copy the manifest's skills and agents into ``claude_dir``. Overwrites in place."""
38
+ manifest = _manifest()
39
+ skills_dst = claude_dir / "skills"
40
+ agents_dst = claude_dir / "agents"
41
+ skills_dst.mkdir(parents=True, exist_ok=True)
42
+ agents_dst.mkdir(parents=True, exist_ok=True)
43
+
44
+ with as_file(files("tiny_spec").joinpath("_bundle")) as bundle:
45
+ for skill in manifest["skills"]:
46
+ src = bundle / skill
47
+ if not src.is_dir():
48
+ raise SystemExit(f"manifest lists skill '{skill}' but it is not bundled")
49
+ dst = skills_dst / skill
50
+ if dst.exists():
51
+ shutil.rmtree(dst)
52
+ shutil.copytree(src, dst)
53
+ print(f" skill {dst}")
54
+ for agent in manifest["agents"]:
55
+ src = bundle / "agents" / agent
56
+ if not src.is_file():
57
+ raise SystemExit(f"manifest lists agent '{agent}' but it is not bundled")
58
+ dst = agents_dst / agent
59
+ shutil.copy2(src, dst)
60
+ print(f" agent {dst}")
61
+
62
+ print(f"\nInstalled tiny-spec into {claude_dir}. Restart Claude Code to load it.")
63
+ return 0
64
+
65
+
66
+ def uninstall(claude_dir: Path) -> int:
67
+ """Remove only the manifest's skills and agents. Leaves the rest alone."""
68
+ manifest = _manifest()
69
+ removed = 0
70
+ for skill in manifest["skills"]:
71
+ dst = claude_dir / "skills" / skill
72
+ if dst.exists():
73
+ shutil.rmtree(dst)
74
+ print(f" removed {dst}")
75
+ removed += 1
76
+ for agent in manifest["agents"]:
77
+ dst = claude_dir / "agents" / agent
78
+ if dst.exists():
79
+ dst.unlink()
80
+ print(f" removed {dst}")
81
+ removed += 1
82
+
83
+ if removed:
84
+ print(f"\nRemoved {removed} item(s) from {claude_dir}.")
85
+ else:
86
+ print(f"Nothing to remove in {claude_dir}.")
87
+ return 0
88
+
89
+
90
+ def build_parser() -> argparse.ArgumentParser:
91
+ parser = argparse.ArgumentParser(
92
+ prog="tiny-spec",
93
+ description="Install the tiny-spec skill suite into your Claude Code config.",
94
+ )
95
+ sub = parser.add_subparsers(dest="command", required=True)
96
+
97
+ for name, help_text in (
98
+ ("install", "copy skills and agents into ~/.claude (re-run to update)"),
99
+ ("uninstall", "remove the skills and agents tiny-spec installed"),
100
+ ):
101
+ p = sub.add_parser(name, help=help_text)
102
+ p.add_argument(
103
+ "--dir",
104
+ type=Path,
105
+ default=_default_dir(),
106
+ metavar="PATH",
107
+ help="Claude config directory (default: ~/.claude)",
108
+ )
109
+
110
+ return parser
111
+
112
+
113
+ def main(argv=None) -> int:
114
+ args = build_parser().parse_args(argv)
115
+ claude_dir: Path = args.dir.expanduser()
116
+ if args.command == "install":
117
+ return install(claude_dir)
118
+ if args.command == "uninstall":
119
+ return uninstall(claude_dir)
120
+ return 1 # pragma: no cover — argparse guarantees a known command
121
+
122
+
123
+ if __name__ == "__main__": # pragma: no cover
124
+ sys.exit(main())
@@ -0,0 +1,12 @@
1
+ {
2
+ "skills": [
3
+ "tiny-spec-create",
4
+ "tiny-spec-plan",
5
+ "tiny-spec-tasks",
6
+ "tiny-spec-build"
7
+ ],
8
+ "agents": [
9
+ "tiny-spec-build-executor.md",
10
+ "tiny-spec-build-reviewer.md"
11
+ ]
12
+ }
@@ -0,0 +1,236 @@
1
+ Metadata-Version: 2.4
2
+ Name: tiny-spec
3
+ Version: 0.1.0
4
+ Summary: A tiny, opinionated take on spec-driven development.
5
+ Project-URL: Homepage, https://github.com/GrayMa77er/tiny-spec
6
+ Project-URL: Source, https://github.com/GrayMa77er/tiny-spec
7
+ Project-URL: Issues, https://github.com/GrayMa77er/tiny-spec/issues
8
+ Author: Snir Orlanczyk
9
+ License: MIT License
10
+
11
+ Copyright (c) 2026 Snir Orlanczyk
12
+
13
+ Permission is hereby granted, free of charge, to any person obtaining a copy
14
+ of this software and associated documentation files (the "Software"), to deal
15
+ in the Software without restriction, including without limitation the rights
16
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
17
+ copies of the Software, and to permit persons to whom the Software is
18
+ furnished to do so, subject to the following conditions:
19
+
20
+ The above copyright notice and this permission notice shall be included in all
21
+ copies or substantial portions of the Software.
22
+
23
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
24
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
25
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
26
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
27
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
28
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
29
+ SOFTWARE.
30
+ License-File: LICENSE
31
+ Keywords: ai-agents,claude,claude-code,skills,spec-driven-development
32
+ Classifier: Environment :: Console
33
+ Classifier: License :: OSI Approved :: MIT License
34
+ Classifier: Programming Language :: Python :: 3
35
+ Requires-Python: >=3.9
36
+ Description-Content-Type: text/markdown
37
+
38
+ <p align="center">
39
+ <img src="images/logo.png" alt="tiny-spec" width="200">
40
+ </p>
41
+
42
+ <h1 align="center">tiny-spec</h1>
43
+
44
+ <p align="center">A tiny, opinionated take on spec-driven development.</p>
45
+
46
+ <p align="center">
47
+ <a href="LICENSE"><img src="https://img.shields.io/badge/license-MIT-blue.svg" alt="License: MIT"></a>
48
+ <a href="https://docs.claude.com/en/docs/claude-code/overview"><img src="https://img.shields.io/badge/Claude%20Code-skills-d97757.svg" alt="Claude Code"></a>
49
+ </p>
50
+
51
+ tiny-spec is a four-step workflow for Claude Code that turns a ticket into shipped,
52
+ reviewed code. You write the intent, it produces a design, a task list, and then
53
+ builds the work one task at a time. Every task is implemented by one agent and
54
+ graded by an independent reviewer that runs the real tests before anything is
55
+ committed.
56
+
57
+ It is four skills and two agents. No orchestrator, no config file, no build step.
58
+
59
+ ```
60
+ tiny-spec-create → tiny-spec-plan → tiny-spec-tasks → tiny-spec-build
61
+ intent design tasks per-task loop
62
+ SPEC.md PLAN.md + tasks.md plan → implement → review → commit
63
+ constitution
64
+ ```
65
+
66
+ ## New to spec-driven development?
67
+
68
+ Spec-driven development (SDD) means writing down *what* you want and *why* before
69
+ any code exists, then letting that spec drive the build. Instead of prompting an
70
+ agent and hoping, you hand it a small, explicit contract — the intent, a design,
71
+ and an ordered list of tasks — and it implements against that. The payoff: the
72
+ agent stops guessing. It knows what "done" looks like, you can review the plan
73
+ before a single line is written, and the result is checked against the spec
74
+ rather than vibes. tiny-spec is one small take on that idea.
75
+
76
+ ## Quickstart
77
+
78
+ Install the skills and agents into your Claude Code config with
79
+ [uv](https://docs.astral.sh/uv/):
80
+
81
+ ```sh
82
+ uvx tiny-spec install
83
+ ```
84
+
85
+ Restart Claude Code so it picks up the new skills, then run the flow in your project:
86
+
87
+ ```
88
+ /tiny-spec-create # capture intent and requirements (binds a ticket, optional)
89
+ /tiny-spec-plan # turn the spec into a design and harden the constitution
90
+ /tiny-spec-tasks # slice the plan into an ordered checklist
91
+ /tiny-spec-build # build each task: implement, review, commit
92
+ ```
93
+
94
+ Re-run `install` any time to update; `tiny-spec uninstall` removes only what it
95
+ installed. Each skill is copied (not symlinked) so every install is
96
+ self-contained.
97
+
98
+ <details>
99
+ <summary>Manual install (no uv)</summary>
100
+
101
+ The skills and agents are plain markdown — copy them in by hand. Claude Code
102
+ loads skills from `~/.claude/skills/` and agents from `~/.claude/agents/`:
103
+
104
+ ```sh
105
+ git clone https://github.com/GrayMa77er/tiny-spec.git
106
+ cd tiny-spec
107
+
108
+ mkdir -p "$HOME/.claude/skills" "$HOME/.claude/agents"
109
+ for s in tiny-spec-create tiny-spec-plan tiny-spec-tasks tiny-spec-build; do
110
+ cp -R "$s" "$HOME/.claude/skills/$s"
111
+ done
112
+ cp agents/*.md "$HOME/.claude/agents/"
113
+ ```
114
+
115
+ If a skill name collides with one you already have, rename these before copying,
116
+ or install one set at a time.
117
+
118
+ </details>
119
+
120
+ ## How it works
121
+
122
+ The constitution (`constitution.md`) is the spine. `tiny-spec-create` seeds it from a
123
+ short interview, `tiny-spec-plan` hardens it with concrete engineering rules, and
124
+ `tiny-spec-build` injects it whole into every task. It holds your style, standards,
125
+ invariants, definition of done, and verification commands.
126
+
127
+ `tiny-spec-build` walks the task list top to bottom. Each task runs through one loop:
128
+
129
+ 1. Plan the task against the constitution (inline, brief).
130
+ 2. Implement it with a fresh `tiny-spec-build-executor` agent.
131
+ 3. Review it with an independent `tiny-spec-build-reviewer` agent that runs the gate
132
+ end to end and grades against the constitution and the task's acceptance.
133
+ 4. On pass, commit the code plus a checklist tick. On fail, loop back to the
134
+ executor with the findings. After two failed attempts it becomes a blocker.
135
+
136
+ ```mermaid
137
+ flowchart TB
138
+ SPEC[SPEC.md<br/>intent] --> PLAN[PLAN.md<br/>design] --> TASKS[tasks.md<br/>checklist]
139
+
140
+ TASKS --> P[Plan task]
141
+ P --> I[Implement<br/>executor]
142
+ I --> R[Review + run gate<br/>reviewer]
143
+ R -->|pass| C[Commit + tick]
144
+ C --> TASKS
145
+ R -->|fail| I
146
+ R -->|fail twice| B[Blocker logged to decisions.md]
147
+
148
+ CON([constitution.md]) -.-> P & I & R
149
+ MEM([memory.md]) -.-> I & R
150
+ ```
151
+
152
+ Solid arrows are the flow. Dotted arrows show the persistent context injected into
153
+ a step: the `constitution.md` goes into planning, implementation, and review, while
154
+ `memory.md` is handed to the executor and reviewer.
155
+
156
+ A small `memory.md` carries operational lessons between runs, so the executor and
157
+ reviewer (which start fresh each time) don't relearn the same pitfalls.
158
+
159
+ When a task can't pass because of a gap in the design or spec, the executor stops
160
+ and logs a blocker instead of hacking around it. You fix the gap upstream in
161
+ `tiny-spec-plan` or `tiny-spec-create`, then resume. Work runs one ticket at a time and
162
+ resumes from the checklist state.
163
+
164
+ ## Why it's small
165
+
166
+ Most spec frameworks are generous by default:
167
+ many phases, many agents, many generated documents. tiny-spec makes the opposite
168
+ bet. Keep one safeguard, drop the rest.
169
+
170
+ A green unit test suite is not the same as working software, so the reviewer
171
+ exercises acceptance criteria end to end and a final smoke test confirms the whole
172
+ spec. That independent review is the safeguard — not the volume of planning
173
+ artifacts. One task, one commit, an external reviewer. Nothing gets added unless
174
+ it earns its place.
175
+
176
+ The case for staying small:
177
+
178
+ - **Documents are context, and context isn't free.** Generating large `spec.md`,
179
+ `plan.md`, `research.md`, and `data-model.md` files costs tokens to write, then
180
+ costs context to carry. Every paragraph the agent has to hold is room it no
181
+ longer has for your actual code. tiny-spec keeps the spine small — a
182
+ constitution and a short memory — and injects only what each task needs.
183
+ - **Real work is a ticket inside a system, not a greenfield repo.** Bigger kits
184
+ assume you're bootstrapping a project from a blank page. Day to day, you pick up
185
+ a ticket and change part of a system that already exists. tiny-spec binds to a
186
+ ticket, works one at a time, and references your task platform instead of
187
+ re-describing the world.
188
+ - **Rigid pipelines fight the user.** Mandatory phases and required sections
189
+ impose ceremony on work that doesn't need it. tiny-spec's extra structure is
190
+ optional by design — add shape where it pays, skip it where it doesn't.
191
+ - **More moving parts is more to maintain.** Orchestrators, ownership contracts,
192
+ checkpoint matrices, and config files are themselves a system you have to learn
193
+ and keep in sync. Four skills and two agents are not.
194
+ - **Generated docs can fake rigor.** A folder of polished planning artifacts looks
195
+ like progress, but it isn't proof. The proof is the reviewer running your real
196
+ tests before each commit.
197
+
198
+ That's the whole trade: where larger kits add machinery, tiny-spec adds one
199
+ independent reviewer and stops.
200
+
201
+ ## Project layout
202
+
203
+ Each skill is self-contained. It carries its own templates and refers to them by
204
+ relative path, with no absolute paths and no shared parent required at runtime, so
205
+ a skill folder works wherever you drop it.
206
+
207
+ tiny-spec creates a `.spec/` directory in your project root, never inside a skill.
208
+ It is namespaced per ticket, with a shared spine at the root:
209
+
210
+ ```
211
+ .spec/
212
+ ACTIVE the active ticket directory name (resolution pointer)
213
+ constitution.md project-wide, shared across tickets
214
+ memory.md operational lessons, shared across tickets
215
+ <ticket-id>/ one directory per ticket (PROJ-123/, gh-42/, …)
216
+ SPEC.md PLAN.md tasks.md decisions.md
217
+ ```
218
+
219
+ `CONTRACTS.md` documents the formats for maintainers. The skills do not read it at
220
+ runtime; each is self-sufficient.
221
+
222
+ ## Integrations
223
+
224
+ tiny-spec binds to a task platform (Jira, GitHub Issues, Azure DevOps, Monday) by
225
+ reference only: a `ticket` block in the spec and a `Refs:` footer on each
226
+ [Conventional Commit](https://www.conventionalcommits.org/en/v1.0.0/), so the
227
+ platform auto-links the work. No API calls or credentials are required.
228
+
229
+ ## Contributing
230
+
231
+ Issues and pull requests are welcome. See [CONTRIBUTING.md](CONTRIBUTING.md), and
232
+ read [AGENTS.md](AGENTS.md) before changing any skill or agent.
233
+
234
+ ## License
235
+
236
+ [MIT](LICENSE)
@@ -0,0 +1,19 @@
1
+ tiny_spec/__init__.py,sha256=aX_g10wVFxMjQX30_QPW9Oq75k2nft828TESvcD-d3w,289
2
+ tiny_spec/cli.py,sha256=iHy91HaBaclpboMGbQho7vTS4Iptasn0EUEjyMhuBl0,4074
3
+ tiny_spec/manifest.json,sha256=W_hvaWKBiTLkJ3_lJWaLXTJSu5Xp1WtQDnUR84d41AM,201
4
+ tiny_spec/_bundle/agents/tiny-spec-build-executor.md,sha256=BbK_i1Iqy6GZgotXORdipiVWketyyZDhnkEM0cNBtAs,3922
5
+ tiny_spec/_bundle/agents/tiny-spec-build-reviewer.md,sha256=w8U2hHA1C-TO-sISEL_v11-zt4XnfLQkBuHQovMGt_U,3486
6
+ tiny_spec/_bundle/tiny-spec-build/SKILL.md,sha256=xmwMYKH39LK7_19OEL4PfOLZLAkKUGo94ytMz6g4b1M,8501
7
+ tiny_spec/_bundle/tiny-spec-build/templates/memory.template.md,sha256=UW3KP5JtlfBnGlXe1zTizJAN-Jga9W6sTHoo0BFBsBM,767
8
+ tiny_spec/_bundle/tiny-spec-create/SKILL.md,sha256=o_aENHoSLynX0I_e53BiswnxxM7fO5qrLM7OXkg4axo,4908
9
+ tiny_spec/_bundle/tiny-spec-create/templates/SPEC.template.md,sha256=MxZ1f8q1M9Ew9pUtyC6EIP-aurzD2HWTc4P-rJA7eEE,1361
10
+ tiny_spec/_bundle/tiny-spec-create/templates/constitution.template.md,sha256=xQ6Nmgw06CuMe8NezstG-ptFLANsD2eifAc9GfL-R24,1151
11
+ tiny_spec/_bundle/tiny-spec-plan/SKILL.md,sha256=K8_pqv7xwSZiK6lsuCGOIog2dMREFEMS2QWqohUX5no,3312
12
+ tiny_spec/_bundle/tiny-spec-plan/templates/PLAN.template.md,sha256=mSnBQnH3o9xgYTSVlhKASjsvjxglHCvWYHE9hl5R0O0,1317
13
+ tiny_spec/_bundle/tiny-spec-tasks/SKILL.md,sha256=KjR7p-Evg7JvAF_YxcP76GU-r7uyEKJf3se0SQHp8Fk,3778
14
+ tiny_spec/_bundle/tiny-spec-tasks/templates/tasks.template.md,sha256=BPCRJ89DMoPTWEQGItKNDQhTudsszS5vVziL53_Uu_0,822
15
+ tiny_spec-0.1.0.dist-info/METADATA,sha256=r5hoPE84WFT8dVxrTRWGGNivTIfCM2gScUm9iPsmr3c,10315
16
+ tiny_spec-0.1.0.dist-info/WHEEL,sha256=mffPy8wBnZQn2VnJUU5jE99KsxaSfiyMHV9Yt0aLVxs,87
17
+ tiny_spec-0.1.0.dist-info/entry_points.txt,sha256=hfwcYT04QqN82P4nPdPfacAnPO_k-2o_YFytPh2i7UM,49
18
+ tiny_spec-0.1.0.dist-info/licenses/LICENSE,sha256=-DxXBwYgv2yn2RynYeoGy47kiIez2SHBfpZEf1SnUA0,1071
19
+ tiny_spec-0.1.0.dist-info/RECORD,,
@@ -0,0 +1,4 @@
1
+ Wheel-Version: 1.0
2
+ Generator: hatchling 1.30.1
3
+ Root-Is-Purelib: true
4
+ Tag: py3-none-any
@@ -0,0 +1,2 @@
1
+ [console_scripts]
2
+ tiny-spec = tiny_spec.cli:main
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Snir Orlanczyk
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.