Break a large epic doc into implementation-ready feature specs (team contracts) and optionally further into sub-specs (one shippable PR per sub-spec, sized for an AI coding harness like hoangsa). Use whenever the user says "break down epic", "split epic", "decompose epic", "write feature specs", "write sub-specs", "epic → spec", "epic to stories", "make this epic AI-codeable", "spec out this epic", Vietnamese equivalents ("chia epic", "viết spec", "tách epic thành spec"), or complains that stories are too small and epics are too big for AI coding agents. Also trigger when the user uploads an epic doc and asks how to hand it to engineering, or when discussing FE/BE handoff contracts, team-split implementation planning, SMART decomposition, sub-spec authoring, Notion task tracking, or Plan Split recommendations for hoangsa. Adapts to different user personas — non-tech PMs delegating to engineering teams get guided FE/BE splits with handoff contracts, while technical users get flexible splitting options (by service, domain, layer, or custom). Optionally integrates UI designs from Figma or Pencil to ensure FE specs match design system components and screen flows. Optionally writes sub-specs into Notion via the Notion MCP. Produce a small number (default 3, up to 5) of feature specs per epic, each with a TypeScript handoff contract and acceptance criteria, then optionally decompose each feat spec into 3–5 sub-specs (cap `.A` through `.E`) — the output is designed to be fed directly to AI coding agents so teams can ship in parallel.
How this skill is triggered — by the user, by Claude, or both
Slash command
/epic-to-feature-specs:epic-to-feature-specsThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
Transforms an epic document (a phase-sized goal with many user stories) into a two-layer decomposition:
Transforms an epic document (a phase-sized goal with many user stories) into a two-layer decomposition:
.A through .E) — shippable-PR-level units sized for an AI coding harness like hoangsa. Each sub-spec ships one cohesive surface as one PR, written as a Notion page so the team can track it on a board. Sub-specs that exceed the AI's working-context sweet spot (~250k tokens) get a Plan Split annotation that hoangsa uses to plan two sequential cook sessions.The core problem this solves: epics are too big (agent loses the thread, scope creeps, technical decisions drift), feat specs are still too big to hand to a single AI session (the 35-story feat spec doesn't fit one bounded agent run), and stories are too small (agent implements in isolation, misses shared code paths, re-litigates decisions). The sub-spec layer is the missing rung — bundles stories that ship together, freezes the technical contracts at the right level, and preserves just enough context for a bounded agent session.
Where this skill stops: the sub-spec layer. Everything below that — DESIGN-SPEC.md, TEST-SPEC.md, plan.json, task context packs — belongs to hoangsa's /hoangsa:menu and /hoangsa:prepare commands. This skill produces what hoangsa ingests via EXTERNAL-TASK.md; it does not duplicate hoangsa's work.
1. Each spec must be SMART-independent. Specific, Measurable, Achievable, Relevant, Time-bound — and crucially, measurable without its siblings existing. If Spec B needs Spec A done before B can be tested, the cut is wrong. Use mocked contracts so every spec is independently verifiable.
2. The handoff contract is load-bearing. When teams are split (e.g. FE/BE), the contract is what lets them work in parallel. It must be typed (TypeScript or equivalent), frozen before either side codes, and canonical in one place that AI agents can read.
3. Decisions already made stay made. Feature specs carry a "Decisions Already Made" section so agents don't re-argue provider choices, state libraries, or data layer picks. This is the single biggest reason agents drift mid-implementation.
4. Max 5 specs per epic. 3 is default. 5 is the ceiling. More fragmentation than 5 is a signal the epic itself should be split.
5. Adapt to the user, not the other way around. Different users need different splitting strategies. A non-tech PM delegating to an FE/BE team needs clear ownership boundaries and handoff contracts. A technical lead breaking down their own work needs flexible cuts by service, domain, or value slice. The skill detects which persona is at play and adjusts accordingly.
6. FE specs must be grounded in designs when available. If UI designs exist (Figma, Pencil, or other tools), the FE spec must reference them — mapping screens to components, citing design tokens, and linking acceptance criteria to specific design states. This prevents the "technically correct but doesn't match the design" failure mode.
7. Sub-specs use stub-first as the default cutting principle. When decomposing a feat spec into sub-specs, the first sub-spec is the structural skeleton — provider chain, navigation root, base services — shipping stubs for everything siblings will fill in. Each later sub-spec replaces stubs from earlier sub-specs without touching the integration site. Every sub-spec's Out of Scope section MUST name its sibling sub-specs by ID (7.1.C, 7.2, etc.) — anonymous deferrals fail SMART independence.
8. The skill stops at the sub-spec layer; hoangsa owns everything below. Do not generate DESIGN-SPEC.md, TEST-SPEC.md, plan.json, or task context packs — those are hoangsa's outputs. Do not emit token-budget numbers into Plan Split sections — hoangsa runs hoangsa-cli budget estimate for that. The skill's job is to produce the right-shaped input that hoangsa's /hoangsa:menu can ingest cleanly via EXTERNAL-TASK.md.
Follow these steps in order. Use the AskUserQuestion tool to gather inputs — do not assume.
Before asking about team structure or technical details, determine who you're working with. This shapes everything downstream — the questions you ask, the cutting strategy, and the level of technical detail in the specs.
Ask the user (use AskUserQuestion):
Store the persona. It determines:
| Persona | Default team split | Contract depth | Design integration | Technical detail level |
|---|---|---|---|---|
| PM / non-technical | FE + BE (guided) | Full handoff contracts with prose companion | High — map designs to specs | Business-facing acceptance criteria |
| Technical lead | User-defined (flexible) | Typed interfaces only (skip prose companion unless requested) | Medium — reference designs, user extracts details | Implementation-level acceptance criteria |
| Solo developer | Single team (no split) | Internal seams only | Light — link to designs | Full technical detail, code-level notes |
Now ask the remaining context questions, adapted to the persona:
For all personas:
.md files (e.g. product_docs/specs/{epic}/, .hoangsa/sessions/{branch}/, docs/specs/).For PM / non-technical persona — add:
Team structure — present options:
Explain: "FE team gets one spec per epic covering all presentation work. BE team gets the remaining specs split by service or pipeline stage. A typed handoff contract connects them."
Contract storage location — where TypeScript contract files live (e.g. contracts/ at repo root).
Language for the contract — default TypeScript. Offer alternatives only if the user's stack clearly isn't TS.
For Technical lead persona — add:
How do you want to split? — present options:
If they pick "by team boundary", follow the PM flow for team structure questions. Otherwise, ask them to describe the boundaries they want.
Contract format — TypeScript interfaces (default), Go types, Python protocols, JSON Schema, or "just markdown descriptions".
For Solo developer persona — add:
Preferred split approach — present options:
Do you want typed contracts between specs? — Yes (helps AI agents stay bounded) / No (lightweight, just markdown boundaries).
Do not improvise these inputs. A wrong assumption here corrupts every spec downstream.
After gathering context, check for available UI designs. This step is critical for any epic that has user-facing features.
Auto-detect design tools: Before asking the user, check which design MCPs are available:
mcp__figma__* or mcp__e8eed802-* / mcp__plugin_design_figma__*)mcp__pencil__*)If design MCP(s) are detected, ask:
"I can see you have {Figma/Pencil} connected. Do you have UI designs for this epic I should reference? If so, please share the file URL or key, and I'll pull component details, screen flows, and design tokens directly into the FE spec."
If no design MCP is detected, ask:
"Do you have UI designs for this epic (Figma, Pencil, screenshots, or any other format)? Providing designs helps ensure the FE spec matches your intended UI — I can map screens to components and reference specific design states in acceptance criteria."
Present options:
When designs are provided, extract the following:
If a Figma MCP is available and the user provides a Figma URL/key:
get_file or get_file_nodes to retrieve the page/frame structureget_file_components to list reusable components used in the designsget_file_styles to extract design tokens (colors, typography, spacing)get_image to capture screenshots of key screens for referenceget_screenshot (Dev Mode MCP) if available for higher-fidelity capturesIf a Pencil MCP is available:
open_document and get_editor_state to understand the document structureget_screenshot to capture key screensget_variables to extract design tokenssearch_all_unique_properties to identify component patternsget_guidelines to pull design system rulesIf screenshots or other static assets are provided:
Store the extracted design context for use in Step 4 (drafting specs).
Read the epic file. Identify:
Then mentally group the stories by implementation cohesion — which stories touch the same files, the same service, the same state machine? Groupings become candidate specs.
If UI designs were provided in Step 2.5, also identify:
When mismatches are found, do NOT silently resolve them. Use AskUserQuestion to surface each mismatch (or batch related mismatches) with a concrete recommendation so the user can decide quickly. For each mismatch, present:
Record all mismatch resolutions in Section 5.5 of the feature spec template. Unresolved mismatches block the spec from reaching "Frozen" status.
See references/cutting-strategies.md for the full decision tree. The strategy depends on the persona detected in Step 1:
PM / non-technical persona:
Technical lead persona:
references/cutting-strategies.md.Solo developer persona:
If uncertain, ask the user rather than guessing. The wrong cut is the most expensive mistake this skill can make.
Use templates/feature-spec.md as the starting structure. Fill each spec with:
references/smart-checklist.md)If UI designs were gathered in Step 2.5, every spec that includes user-facing work MUST include a "UI Design Reference" section (see templates/feature-spec.md Section 5). This section contains:
Screen-to-story mapping — a table linking each screen/frame from the design to the user stories it covers in this spec. Include the design frame name/ID and a brief description.
Component inventory — list every design system component used in this spec's screens. For each component, note:
Button/Primary/Disabled, Card/Expanded)Design tokens referenced — colors, typography, spacing values from the design that the spec's UI must use. Extracted from the design tool's styles/variables.
State-to-screen mapping — for each state in the handoff contract (or domain logic), which design screen/variant shows that state. This is critical for FE acceptance criteria:
idle → "Inbox/Default" frameprocessing → "Inbox/Processing" frame (shows spinner)failed → "Inbox/Error" frame (shows retry button)complete → redirects to "Library/NoteDetail" frameDesign gaps and open questions — screens or states that have no design coverage yet, or designs that are ambiguous. Each gap gets an owner and deadline.
For PM / non-technical persona: this section is especially important — it's the bridge between "what the designer intended" and "what the developer builds". Include screenshot references or frame links wherever possible.
For Technical lead persona: focus on the component inventory and state mapping. They'll extract implementation details themselves.
For Solo developer persona: include design links and a lightweight component list. Skip the detailed token extraction unless they request it.
Skip this step if the user is a solo developer who opted out of typed contracts.
For each spec that crosses a team boundary (or an internal seam the user wants enforced), produce a TypeScript contract file using templates/handoff-contract.ts. The contract defines:
status: string fields; they force exhaustive rendering)Critical rule: the contract is coarser than the internal state it represents. If BE has internal stages (e.g. whisper-running, structuring, dlq-retry), those should collapse to a single processing state at the contract boundary. The contract is a seam, not a mirror.
For PM / non-technical persona: Also produce a prose BE-HANDOFF.md (see templates/be-handoff-narrative.md) that documents the contract in human-readable form for Notion review. The .ts file is canonical; the .md is explanation.
For Technical lead persona: Skip the prose companion unless explicitly requested. They can read the .ts file directly.
For each spec, run through references/smart-checklist.md. The most important test:
"Can this spec's acceptance criteria be verified with sibling specs mocked out?"
If no, cut differently. Typical fixes:
Additional validation when designs are present:
Write each spec to the agreed storage path using the naming convention:
spec-{epic-number}.{spec-number}-{team}-{short-title}.md
Examples:
spec-3.1-fe-processing-surface.mdspec-3.2-be-upload-transcription.mdspec-3.3-be-structuring-note-creation.mdFor non-team-boundary splits (technical lead or solo developer who split by service/layer/slice), adapt the naming:
spec-3.1-api-auth-endpoints.mdspec-3.2-worker-transcription-pipeline.mdspec-3.1-slice-happy-path.mdWrite contract files to the agreed contracts path:
contracts/{feature-area}.ts
Example: contracts/processing.ts
Also produce a short mermaid diagram showing spec → spec dependencies, so the team can see the ordering at a glance. Include it in the epic's existing .md file as an appendix or in a new SPECS-OVERVIEW.md in the spec folder.
Output to the user, adapted to their persona:
For PM / non-technical persona:
For Technical lead persona:
For Solo developer persona:
After presenting feat specs, prompt the user whether to decompose them further into sub-specs. Use AskUserQuestion:
"Your feat specs are ready. Each one is sized as a team contract (~20–35 stories on average). To hand them to an AI coding agent (e.g. hoangsa), each feat spec needs to be decomposed into 3–5 sub-specs — one per shippable PR, ~5–15 stories each, written as a Notion page. Want me to do that now?"
Present options:
If the user picks "no", stop here. The skill is done.
If the user picks "yes", proceed to Step 11. Before drafting, read references/sub-spec-cutting.md, references/plan-split-patterns.md, and templates/sub-spec.md in full so the AI agent has the patterns and the template loaded.
For each feat spec the user picked, run the following sub-workflow:
Ask the remaining context questions via AskUserQuestion:
notion-fetch on that URL first to discover the actual property schema, then notion-create-pages to create one page per sub-spec.<feat-spec storage>/sub-specs/. Confirm or change.spec-X.Y.{letter}-<slug>.md with .A through .E. Cap at 5 per feat spec.Read the feat spec's §3 Scope subsections, story list, and (if present) §5 UI Design Reference. Apply the cutting strategy from references/sub-spec-cutting.md:
.A and note no siblings.Then propose the boundaries to the user via AskUserQuestion. Present the proposed sub-spec list as: 7.1.A — <scope>, 7.1.B — <scope>, etc., with a one-line cohesion rationale for each. Ask: "Does this split look right, or would you like to adjust the boundaries?"
If the user proposes a different cut, accept it. The wrong cut is the most expensive mistake the skill can make at this layer.
If the proposed cut would need 6+ sub-specs to fit the work, escalate to the user: "This feat spec wants 6+ sub-specs. The .A–.E ceiling means we should either split the feat spec itself first, or pick the 5 most cohesive groupings and merge the rest. Which do you prefer?"
For each sub-spec, use templates/sub-spec.md as the starting structure. Fill in:
Parent spec (path + section list of the parent feat spec), Contracts (path to consumed contract, or "none consumed directly"), Stories (comma-separated story IDs inherited from the parent).7.1.C, 7.2, etc.). Anonymous deferrals fail SMART independence.<contract>.ts. If none, write "No contracts consumed — this sub-spec is structural."/hoangsa:menu maps each AC 1:1 to a [REQ-xx] marker. Do NOT group ACs under story headings.Run the heuristic from references/plan-split-patterns.md (file count × per-type weight). The heuristic is internal-only — never written into the output.
If the heuristic sum is clearly above 250k, emit a §7 Plan Split section in the sub-spec, choosing the pattern:
If the heuristic is comfortably below the threshold, omit the §7 Plan Split section entirely. Absence means "plan as one hoangsa session."
When emitting the Plan Split section, follow the template in templates/sub-spec.md §7 exactly. Two rules:
REQ-11 (logic only) in Plan-1, REQ-11 (UI) in Plan-2) reads as a coverage gap without it.For each sub-spec:
Write the markdown copy to <sub-spec storage>/spec-X.Y.{letter}-<slug>.md. This is the canonical copy that lives in git.
Write the Notion page (if Notion integration was chosen in 11a) using notion-create-pages. Discover the database's property schema via notion-fetch first; map only properties that actually exist:
| Default mapping (only if property exists in the database) | Source |
|---|---|
| Task name | "Spec X.Y.{letter} — " |
| Description | Sub-spec §1 Context, first sentence |
| Effort level | Heuristic from file count: Low (<5), Medium (5–15), High (>15) |
| Priority | Inherit from epic, or default High |
| Status | Always "Draft" |
| Tags | Inherit from parent feat spec team tag |
| Task type | Default "Feature request" |
The page body is the full sub-spec markdown.
List the sub-spec markdown paths and Notion page URLs. For each sub-spec note:
/hoangsa:menu when you're ready to implement."Also produce or update the dependency graph (mermaid) to include sub-spec → sub-spec relationships so the team can see the ordering at a glance.
When a spec crosses a team boundary, follow these rules to prevent drift (the #1 failure mode of parallel teams):
.ts contract file lives in one repo (the BE-owning repo is a good default). Other repos either import it as a package, sync via a small script, or copy-paste with a CI diff check. Do not rely on memory or Notion alone — AI agents need a file they can read.processing, BE knows whether it's in Whisper-stage or DLQ-retry. Leaking internal states into the contract couples the teams and defeats the purpose.See references/team-split-patterns.md for variants: FE/BE, FE/BE/Mobile, single team with service boundaries, solo developer, etc.
Note: For solo developers and single-team setups, the contract discipline is lighter — contracts serve as internal seams for AI agents rather than team coordination tools. The "freeze before coding" and "co-review" rules don't apply, but "one source of truth" and "coarser than internals" still help agents stay bounded.
AC1, AC2, …) with each AC tagged with its parent story ID. Story-grouped ACs break hoangsa's 1:1 AC → REQ mapping..E. If the work needs 6+ sub-specs, the parent feat spec itself is probably too big — escalate to the user before overflowing..A omits provider stubs, every subsequent sub-spec (.B, .C, .D, .E) has to add the provider chain back to _layout.tsx, creating merge conflicts. The skeleton sub-spec MUST ship stubs.hoangsa-cli budget estimate is the authority on tokens — anchoring hoangsa on our number is garbage-in.REQ-11 (logic only) / REQ-11 (UI)) reads as a coverage gap without it.DESIGN-SPEC.md, TEST-SPEC.md, or plan.json. Those belong to hoangsa. The skill stops at the sub-spec layer.You're done at the feat-spec layer when:
You're done at the sub-spec layer (Step 11) when:
<sub-spec storage>/; if Notion integration was chosen, Notion pages are created with discovered propertiesIf the user wants a worked example or a single spec drafted in full detail, offer to draft Spec X.1 end-to-end (the FE-heavy one when teams are split — it's the hardest to get right, so stress-test it first). For sub-spec examples, offer to draft Sub-spec X.1.A (the skeleton — same reasoning).
Feat-spec layer:
templates/feature-spec.md — the full feat spec template (includes UI Design Reference section)templates/handoff-contract.ts — TypeScript contract startertemplates/be-handoff-narrative.md — prose companion for Notion reviewreferences/cutting-strategies.md — decision tree for cutting epics into feat specs (persona-aware)references/team-split-patterns.md — FE/BE, FE/BE/Mobile, single-team, solo-developer variantsSub-spec layer (new in v0.3):
templates/sub-spec.md — the sub-spec template (mirrors feat spec template, tighter scope, REQ-ready ACs, optional Plan Split section)references/sub-spec-cutting.md — decision tree for cutting feat specs into sub-specs (FE / BE / fallback)references/plan-split-patterns.md — when and how to emit a Plan Split section for hoangsaShared:
references/smart-checklist.md — the SMART-independence validation (applies to both feat specs and sub-specs)Guides creation, editing, and verification of skills for AI coding agents using test-driven development with subagent scenarios. Use when authoring or debugging skills.
npx claudepluginhub unknown-studio-dev/epic-to-feature-specs --plugin epic-to-feature-specs