Forge is a Claude Code plugin that lets any engineer drive an entire React+TypeScript component library by talking to Claude — recommend the right component, add a prop, scaffold a new one, retire an old one, or score the whole thing. Every change ships as a real GitHub PR with docs that regenerate from source, so the design system can't drift.
See the sourceForge is a Claude Code plugin that lets an engineer talk their component library into shape — recommend a component with real props, add a prop non-breaking, scaffold a new house-style component, or score the whole library against a written standard — and every write ends by regenerating docs from source and opening a real PR.
The pain: every component library, six months in, has docs that lie. Someone shipped a loading prop; Storybook doesn't know. A team renamed a variant; the design token page still shows the old name. New engineers waste days reading a spec that no longer matches the code. Forge stops that decay by inverting the flow: you don't write docs after the code — every edit, create, and delete regenerates the doc for that component from source, in the same commit. The docs literally cannot drift because the same action that changes the code rewrites its section.
The signal came from watching it happen at OmnisAI. Storybook lagged real PRs by weeks, and new engineers kept rebuilding primitives that already existed because they couldn't find them in a spec that no longer matched the code. The instinct is to add more doc discipline — more review, more reminders. I concluded the opposite: discipline decays, so the only durable fix is to make drift structurally impossible. That decision — regenerate from source in the same commit — is the whole product, and it came from the failure mode, not a feature list.
Design-system docs — Storybook, MDX, whatever — are written after the fact. An engineer ships a component or a new prop, and later someone (maybe them, usually nobody) updates the doc. The two are always slightly out of sync, and the gap widens with every merge. Six months in, the spec and the code disagree on names, defaults, and even which components exist, and every new engineer hits it on day one.
Forge's bet is that the answer isn't better docs — it's not writing them separately at all. There's one markdown brain, DESIGN-SYSTEM.md, and every write skill ends by regenerating the touched component's section from real source. Skills read it before they answer, so they cannot recommend a prop that doesn't exist or a component that isn't in the library. When a new Toast lands, /forge:use knows about it the next second. The docs and the code are one artifact, updated by the same action.
One skill per real design-system task, plus a matching slash command. They all read the same brain and the same written standard, so the answers are consistent whether an engineer types /forge:audit or says "score the library."
Answers "which component for a confirm dialog?" or "what props does Button take?" — only from the brain. Cannot invent props. Returns a wiring snippet lifted from real stories.
Adds a typed prop with a safe default, keeps old props as @deprecated aliases, updates JSDoc + tests + brain section, opens a real PR. Never renames in place.
Reads 2–3 sibling components for style, scaffolds tsx + css + tests, references only tokens (no raw hex/px), adds the brain section, opens a PR. New components are born standard-compliant.
Greps every call site, defaults to marking @deprecated and keeping it exported, hard-deletes only after explicit "yes break it" confirmation. Consumers can't be surprised.
Scores every component against the standard: naming, token vocabulary, size scale, prop completeness. Emits a ranked fix list ready to hand back to edit-component.
Every edit/create/delete ends by running sync_design_system.py — the component's brain section is rewritten from source in the same commit as the code. There is no "update the docs" step to forget.
A per-repo forge.config.json declares package name, components directory, tokens CSS, PR base branch, naming rule. Point Forge at any React+TS library and it adapts.
component-standard.md encodes naming, tokens, a11y gates, deprecation policy, prop completeness by type. Skills load it every run; audits score against it.
Nothing hides behind a service. The plugin installs at the user level; each write is deterministic — the skills read the standard, mutate real files, run a Python script to regenerate the brain, and shell out to gh to open the PR. Here's the whole path for a typical /forge:edit:
The skill reads forge.config.json, the written component-standard.md, and standing-guidance.md (durable corrections). It refuses to work on a component that isn't in the brain.
Opens the target component's tsx, css, stories and tests. Opens 2–3 stylistically-nearest siblings so the change matches house style, not generic React defaults.
Adds new props with safe defaults; keeps old names as @deprecated aliases. Never renames in place. Migrates raw hex/px to tokens opportunistically. Fixes dead props if it sees any.
Runs sync_design_system.py. The component's ## Name block in DESIGN-SYSTEM.md is rewritten from the just-changed source — props, defaults, JSDoc, tokens referenced, usage snippet from stories.
open_pr.sh branches (forge/edit/<name>-<slug>), stages only the files Forge touched via --paths (never git add -A), commits, pushes, runs gh pr create. If gh is missing, it prints exact commands rather than fail silently.
Docs update mechanically; corrections stick as durable rules. Forge separates the two on purpose so neither depends on the other holding.
After every edit/create/delete, sync_design_system.py rewrites the touched component's brain section from real source. Zero prose. No LLM involved.
docs = source, alwaysWhen a reviewer says "we always X, never Y," record_guidance.py appends a scoped rule to standing-guidance.md. Every future skill run reads it.
the mistake stops recurringopen_pr.sh --paths stages only files Forge touched. A local .env, WIP scratch file, or private key cannot get swept into a PR.
safe on shared machinesforge.config.json declares package name, component dir, tokens file, PR base, naming rule. One installed plugin adapts to any React+TS library.
install once, use anywhereThe task itself takes ten seconds either way. What varies is everything around it — the doc drift, the review latency, the token debt, the sibling inconsistency. Left is the usual roundtrip; right is one command:
// 1. Open Button.tsx, add prop interface ButtonProps { /* … */ loading?: boolean; } // 2. Update the CSS — hope you match // the sibling's spinner class conv. // 3. Update the Storybook MDX doc // (usually skipped — "later") // 4. Update the design-token file // if you used a new color // 5. Open a PR. Reviewer bounces // because the naming is off. // 6. Fix. Push. Merge. Docs still lag.
$ /forge:edit add loading to CommonButton // Forge: // ✓ read standard + sibling siblings // ✓ add prop non-breaking (default false) // ✓ update JSDoc + stories // ✓ regenerate brain section // ✓ commit + push + gh pr create // You get: → PR #42 · main ← forge/edit/commonbutton-… // Docs already accurate. Reviewer // reviews. Merge.
The honest trade-off: Forge cannot judge taste. It won't tell you a Toast is the wrong pattern or that a prop should be a variant instead. It can enforce naming, tokens, a11y baselines and non-breaking rules — the mechanical stuff that eats a review. Taste stays with the reviewer; drift stops.
These are real runs from the pilot — same engine, four different verbs:
Recommends the right primitive, quotes exact props from the brain, returns a wiring snippet lifted from real stories. No invented props.
Scores every component against the standard. Ranked fix queue with actionable items — hand them back to edit-component one at a time.
Reads the two closest siblings, scaffolds house-style tsx + css + tests, adds a brain section with verified props, opens the PR.
Greps every call site, defaults to non-breaking deprecation. Hard-deletes only after explicit confirmation.
Anyone can auto-generate React components. The decisions that make Forge trustworthy in a real repo were about what it refuses to do:
No framework, no build step for the plugin itself. Plain JSON manifests, markdown SKILL files, and Python/bash scripts a reviewer can read top to bottom. Every file has one job:
The whole install is public. Two /plugin commands from any Claude Code session, one forge init in the target repo, done:
# 1. In any Claude Code session — two separate submits: /plugin marketplace add OmnisAIOrg/OmnisDesign-OS /plugin install forge@OmnisAIOrg-OmnisDesign-OS # 2. In the component-library repo, tell Claude: "initialize forge for this repo" # forge_init.py auto-detects paths, writes forge.config.json, # regenerates the brain from source. One-time. # 3. Now just talk: "add a loading prop to Button" # /forge:edit "create a Toast component" # /forge:create "which component for a confirm dialog?" # /forge:use "audit the library" # /forge:audit
Forge v1.0.0 is installed at OmnisAI, tested end-to-end with a real component library, and has shipped four real PRs during the pilot — every one non-breaking, every one with source-verified docs updated in the same commit. The plugin passes claude plugin validate and installs from github with a single command.
The leverage is the point: this isn't a tool only I use. Any engineer on the team drives the whole 59-component library in plain language — no design-system gatekeeper in the loop — and every change ships as a reviewable PR. It turns a one-person standard into something the whole team maintains without me, which is the difference between output and leverage.
CommonButton standardization, Divider, Drawer, and OTPInput — all non-breaking, all with brain sections regenerated in the same commit. Zero manual doc updates.
End-to-end tests hit the demo pages for every Forge-generated component. Zero console errors on any surface. Also caught two pre-existing library bugs (InputField hydration, Calendar SVG attrs) which Forge fixed on the way.
Seven parallel agents edge-tested each script (single-line interfaces, unicode, empty repos, path traversal). All confirmed bugs fixed. Security-reviewed: scoped staging, injection-safe config read, no secret handling anywhere.
Each of these was one prompt, then Forge did the rest — code, tests where present, brain section, PR body:
Added Button alias, colorType axis, canonical sm|md|lg. All non-breaking. Existing consumers unaffected.
New component from scratch. Token-referencing CSS, ARIA role="separator", keyboard-accessible. House-style matched from siblings.
Filled a hole in the design system — added missing spacing, radius, and type-scale tokens. 461 off-vocabulary references catalogued for future migration.
Two new house-style components. OTPInput has auto-advance, numeric guard, aria-labelled cells. Drawer opens with role="dialog" and escape-to-close.
Every prior attempt at this, mine included, wrote docs after the code and watched them rot. I stopped patching that and inverted the flow: the same action that changes a component regenerates its doc in the same commit, so drift is structurally impossible. The honest gap that remains: the plugin runs real git and shell, so a careless action could leak secrets or push to the wrong place — that's why writes are scoped to staging and destructive ops need explicit confirmation. It's contained, not fully solved.
What I'd do differently: I validated it on one library — OmnisAI's — so the standard is opinionated toward that house style. Before calling it general, I'd run it against a second, differently-structured library to find exactly where the "one standard" assumption breaks.