SDD, but for interfaces. Two autonomous multi-agent pipelines on one engineering spine: one researches the market, designs, builds and deploys a landing that converts — the other designs and builds the application UI that comes after it. Neither looks AI-generated.
You say "armame una landing para X" → the skill runs a real market study, then research → strategy → architecture → copy → design → build → motion → polish → SEO → review → deploy.
You say "diseñá el dashboard" or "agregá la vista de facturas" → it reads your project, negotiates a typed contract with your backend, and ships screens with every state — loading, empty, error, permission, overflow — full keyboard, measured contrast.
You say "esta app está fatal, arreglala" → it audits page by page and component by component, scores the codebase, builds a safety net, and remediates in verified waves: dead code deleted, hardcoded values killed, duplicates collapsed, bugs fixed, every missing state built.
Landings: real market research · multi-page · unique sections per theme · alive · SEO + GEO · deploy to a live URL
Apps: adopts your repo · typed backend contract · every state built · keyboard-first · WCAG AA measured
Rescue: audits a badly-built app, then remediates in verified waves — dead code, hardcoding, duplication, bugs
Both: zero technical debt · change at the root · a closed review loop that never fakes a PASS
Pick the option that matches where you are. Each is basically one step.
Run these one at a time in the Claude Code prompt — paste one line, press Enter, then the next. Do NOT paste all three together (they'd concatenate into one broken command):
1. add the marketplace:
/plugin marketplace add https://github.com/propiter/landing-craft.git
2. install the plugin:
/plugin install landing-craft@landing-craft
3. activate it:
/reload-plugins
⚠️ Use the fullhttps://….gitURL (not the shortowner/repoform, which can fail with an SSH "Host key verification failed" error). And one command per line — pasting the three at once is the usual cause of a "Malformed URL" error.
This works the same on Windows. After installing, the commands are namespaced:
/landing-craft:landing, /landing-craft:app, …
curl -fsSL https://raw.githubusercontent.com/propiter/landing-craft/main/install.sh | bashirm https://raw.githubusercontent.com/propiter/landing-craft/main/install.ps1 | iexThe two terminal installers copy the whole stack — 9 skills, 27 sub-agents and 21 commands —
and auto-detect Claude Code, OpenCode and Cursor, installing to each (OpenCode reads
~/.claude/skills/ natively). They fetch Impeccable too. If run in a real terminal they also
offer an optional Firecrawl setup (URL + optional API key — the key is not required for
self-hosted) and write it where each tool reads it, including OpenCode (which does not read
~/.claude/settings.json). Piped non-interactively (curl … | bash)? It's skipped cleanly — set
FIRECRAWL_URL in your env later.
You get plain commands: /landing, /app, … After running one, restart Claude Code or run
/reload-plugins to activate them. No admin rights, nothing runs in the background; re-run
anytime to update.
Which should I use? The Claude Code plugin (first option) is the cleanest — cross-platform and auto-updates. The terminal scripts are handy if you'd rather one command outside Claude.
Landings — a site that has to convince a stranger once:
/landing "una landing para mi SaaS" # ★ flagship: research → build → DEPLOY (live URL)
/landing-init # detect env + tooling, bootstrap
/landing-new "a project-management app for remote teams" # planning only → review the plan
/landing-build # build + motion + polish + SEO
/landing-review # render @ 390/768/1440, score, fix
/landing-continue # resume from the last completed phase
/landing-status # where the pipeline is (read-only)
/landing-ship "<your product>" # full auto (no deploy)
/landing-audit # ★ diagnose an EXISTING site — read-only
/landing-rescue # ★ audit THEN remediate it, in wavesApps — an interface that has to serve a returning user a hundred times a day:
/app "el dashboard de facturación" # ★ flagship: detects your project, plans, builds, reviews
/app-init # read the ground: mode, stack, design system, contract source
/app-new "<lo que querés>" # planning only → review IA + design system before code
/app-build # contract → build → states → motion → polish
/app-screen "la vista de facturas" # ★ ONE screen into a live app, surgically
/app-contract # ★ re-sync after the backend changes
/app-audit # ★ diagnose an existing app — READ-ONLY verdict + plan
/app-rescue # ★ audit THEN remediate a badly-built app, in waves
/app-review # render every screen × state, score, fix (max 3)
/app-continue # resume from the last completed phase
/app-status # where it is (read-only)You don't need to know marketing — that's the research agents' job. You don't need to hand it a
spec either: /app reads your repo and figures out the mode itself.
A landing has to convince a stranger once. An app has to serve a returning user a hundred
times a day. Those are different design problems, so they get different pipelines — but the same
engineering doctrine (craft-core): zero technical debt, change at the root, tokens first, and a
closed review loop that never returns a fake PASS.
research ─► strategy ─► architecture ─┬─► copy ───┐
(market study) └─► design ─┴─► build (multi-page) ─► motion ─► polish ─┐
build ─► seo ──────────────────────┴─► review ⭯ ─► deploy
| # | Phase | Sub-agent | What it guarantees |
|---|---|---|---|
| 0 | Research | landing-research |
Autonomous market study — scrape competitors, keywords, audience, alive refs, the GAP |
| 1 | Strategy | landing-strategy |
Positioning, ICP, core promise, offer (grounded in research) |
| 2 | Architecture | landing-architecture |
The page map (multi-page) + the UNIQUE per-theme section plan |
| 3 | Copy | landing-copy |
Research-backed conversion copy; the 5-second test passes |
| 4 | Design | landing-design |
A signature visual + real imagery — the anti-"made with AI" phase |
| 5 | Build | landing-build |
Multi-page Next.js + Tailwind, mobile-first, accessible |
| 6 | Motion | landing-motion |
Scroll-reactive motion at the chosen intensity, reduced-motion safe |
| 7 | Polish | landing-polish |
Craft pass — type, spacing, contrast (measured), responsive, states |
| 8 | SEO + GEO | landing-seo |
Meta, OG, JSON-LD, CWV + built to be CITED by AI engines — AI-welcoming robots.ts, llms.txt+llms-full.txt, entity schema from REAL data, freshness, AI-referral analytics |
| 9 | Review ⭯ | landing-review |
Closed-loop audit — the 5 bars + contrast + wiring + hardening + GEO gates, routed back and re-reviewed (max 3), honest about any remainder |
| 10 | Deploy | landing-deploy |
GitHub + Vercel; installs the CLI & guides first login; syncs .env → Vercel |
The five bars: not AI-generated · it sells (what/who/why/next in 5s) · intuitive · crafted · ALIVE (real imagery, a signature visual, scroll-reactive motion, warmth).
init ─► product ─► ia&flows ─┬─► system ──┐
(mode + ground) │ ├─► screens ─┐
└─► contract ┘ ▼
(the SEAM) build ─┬─► states ⭐ ─┐
├─► motion ────┼─► review ⭯
└─► polish ────┘
| # | Phase | Sub-agent | What it guarantees |
|---|---|---|---|
| 0 | Init | app-init |
Detects the mode — adopt your existing project · greenfield · one screen · contract sync — plus stack, existing design system, auth/roles, and where the backend contract lives. Never assumes greenfield |
| 1 | Product | app-product |
What it does, the roles, the jobs ranked by frequency, a teardown of the reference-class UIs in the category |
| 2 | IA & flows | app-ia |
Navigation model + why, the FULL screen inventory (incl. auth/settings/404/403), entity model, route map with URL state, the permission matrix, flows with their failure branches |
| 3 | System | app-system |
Three token layers (light + dark), UI type scale, density modes, the component inventory with its state matrix, and the Signature token |
| 4 | Contract ⭐ | app-contract |
The backend seam — derives types from your real schema, or specifies app/contract.md for the backend side; hostile mock + http adapters behind one switch |
| 5 | Screens | app-screens |
The app shell + a layout spec per screen, each with its full state matrix and its empty/error microcopy |
| 6 | Build | app-build |
Shell once, primitives, then screens — wired to the contract. In Adopt mode it matches your project and never converts the stack |
| 7 | States ⭐ | app-states |
Every screen × loading/empty/error/permission/offline/overflow, actually built and reachable + the stress tests |
| 8 | Motion | app-motion |
Feedback and continuity only — nothing over 300ms, optimistic UI, no scroll-jacking, reduced-motion safe |
| 9 | Polish | app-polish |
Keyboard model, focus management, ARIA patterns, measured AA in both themes, density, 320px → 200% zoom |
| 10 | Review ⭯ | app-review |
Renders every screen × state at 320/768/1440, light + dark; the 6 bars + states/a11y/contract/motion/hardening gates; routed and re-reviewed (max 3) |
The six bars: not AI-generated · learnable in 60s · fast to OPERATE (keyboard) · COMPLETE — every state · survives stress (10k rows, 60-char names, nulls, 320px) · crafted but quiet.
app-craft is the frontend half of a full-stack effort. Your backend either already exists, is being built in parallel, or doesn't exist yet. All three work, because there is one explicit, typed contract that is the seam:
src/lib/data/
contracts/ ← zod schema + types + Repository interface ← the SEAM
adapters/mock/ ← 10k rows · zero rows · nulls · every enum · latency · forced errors
adapters/http/ ← your real backend, responses validated at the boundary
index.ts ← ONE switch decides which is live
- If a schema exists, it DERIVES — Drizzle · Prisma · tRPC · OpenAPI · GraphQL · Supabase · server actions. Field names, types and nullability come from the source of truth, never guessed.
- If it doesn't, it SPECIFIES — writes
app/contract.md(entities, operations, permissions, error shapes, open questions) for whoever builds the backend, and runs on a hostile mock meanwhile. You are never blocked. - When the backend lands,
/app-contractre-derives the types — andtsctells you exactly which views to patch. Zero UI changes if nothing broke, because no component ever imported anything but the contract. - The review gate checks for drift — no
fetch, no ORM, noprocess.envin a component, both adapters satisfy the interface, every error kind rendered.
Works for both pipelines — /app-rescue for an application, /landing-rescue for a marketing
site. Same method, different judgment: an app is scored on its states, keyboard and architecture;
a site on the five bars, its wiring (dead CTAs, forms that POST nowhere, analytics that never
mounts) and its SEO/GEO.
An app generated in one shot — duplicated components, hardcoded values everywhere, dead files
nobody dares delete, any as a type system, only the happy path, real bugs. /app-rescue fixes it
module by module, page by page, component by component.
First it judges, then it decides. In normal Adopt mode the rule is "you're a guest — match the
project". When the conventions are the disease, matching them propagates it. So the rescue
never picks by taste: app-audit scores the codebase across 10 dimensions — types, duplication,
hardcoding, architecture, dead weight, states, security, a11y, correctness, craft — and the score
decides: adopt · rescue · or a rewrite is cheaper than this rescue, said out loud with
the evidence.
Then it builds a safety net — before touching anything. Refactoring untested code isn't improving it, it's breaking it quietly. Wave 0 is always: strict TS on (the error list is the bug backlog), lint, a green build, route smoke tests, and Playwright visual baselines — every page × 320/768/1440 × light/dark, with data and time frozen. That's how "todavía se ve bien" becomes measured instead of claimed.
Then it remediates in waves, verified between each, one commit per wave:
| 1 | Delete dead weight | Proven unused only — tool output and symbol grep and string grep and a framework-convention check. Watch for dynamic imports and string-referenced components. Uncertain = not deleted, reported instead. |
| 2 | Tokens | Extract the real palette/scale and repoint every hardcoded value. Kills "quemado" globally in one pass — and must change appearance by zero pixels, which the visual diff proves |
| 3 | De-duplicate | One Button, one Header, one Table. Every caller refactored, every copy deleted, in the same wave |
| 4 | Architecture | Logic out of JSX into lib · data behind the contract · typed env · god files split · import cycles broken · client/server boundary fixed. Behaviour preserved |
| 5 | Correctness | Bugs fixed as their own commits, and every missing state built |
| 6 | A11y & craft | Keyboard, focus, ARIA, measured AA in both themes, responsive to 320px and 200% zoom. The one wave that changes appearance on purpose — diffs reviewed by eye, baselines re-recorded, and said so |
| 7 | Performance | Bundle, code-splitting, N+1, images — measured before and after |
Between every wave: tsc · lint · build · smoke · visual diff = 0. A red gate is fixed before
the next wave starts, so any breakage is always attributable to one wave — and any wave can be
reverted on its own.
Dead code is found with real tools (knip, depcheck, madge, jscpd), never by eye. And the
report always ends with what it did NOT touch and why — out of blast radius, unverifiable, or
a behaviour question for you. A rescue that claims total victory is a rescue nobody should believe.
/app-audit /landing-audit # read-only: score, evidence, verdict, ordered plan
/app-rescue /landing-rescue # audit, then execute it in verified waves on a branchThe tell is different for each pipeline, so each has its own doctrine.
Landings fail by being soulless: text + a fake UI panel on a dark gradient, one cold hue, hero→3-cards→CTA in textbook order, one load-fade and nothing reacts after. The fix is a signature visual, real imagery, warmth, and scroll-reactive motion.
Apps fail by being the kit: slate/zinc neutrals · Inter at defaults · 8px radius on
everything · a Card with a 1px slate-200 border around every region · the DataTable straight from
the docs · a muted indigo primary · uniform density · and only the happy path. That last one is
the loudest — a missing empty state is evidence the thing was never used by a person.
The fix, in the order that actually works: tokens move every screen at once; component edits move one screen at a time. So headless primitives (Radix/Base UI) for behaviour and ARIA, a 100% custom token layer for looks, and one signature token the kit doesn't ship — a shadow, a grain, an easing curve — named and applied everywhere. If you can't name it, review fails you.
Not flat, not chaotic — a dial. Default medium, auto-escalating to rich for bold niches
(creative, consumer, launch, portfolio), never dropping to subtle on its own, reaching ultra
only for spectacle-native niches. Ask for menos / más / ultra and it adjusts (and remembers).
- subtle (ask for it) — hero reveal, scroll fades, button micro-interactions.
- medium (default) — + Lenis smooth scroll, section reveals, card hover depth, counters, CTA glow.
- rich (auto for bold niches) — + GSAP scroll-scrub/parallax, magnetic buttons, 3D-tilt, spotlight/beams.
- ultra (spectacle-native, else ask) — WebGL backgrounds, cursor-driven scenes, scroll-3D. CWV-green and reduced-motion safe.
Apps are different on purpose. A landing is seen once by a stranger; an app screen is seen four
hundred times by the same person. So app motion is feedback and continuity only — ≤120ms on
hover/focus, nothing over 300ms, transform/opacity only, optimistic UI where it's safe, and
no smooth-scroll library, no scroll-jacking, no count-ups. Anything charming on view #1 is
friction on view #40.
Landing Craft is the orchestrator, and the installer bundles every skill it composes — so nothing fails because a dependency is missing. You never install pieces separately.
- The spine:
craft-core— the shared doctrine (zero debt, change-at-the-root, the review loop, tokens-first, never-refactor-what-you-can't-verify) plus the seven references both pipelines use:hardening.md(security headers · validated endpoints · typed env · CI · strict TS · atomic components),contrast-check.md(the measured WCAG gate),animation-levels.md,assets.md,remediation.md(the rescue method + health verdict),safety-net.md(smoke tests- visual baselines),
codebase-hygiene.md(dead code · nothing hardcoded · built to scale).
- visual baselines),
- Bundled (Apache-2.0):
motion-craft,marketing-strategy,brand-voice,seo-geo,design-review-loop,web-assets(image/OG/favicon generation — installs Playwright if missing). - Fetched on install (optional aesthetic engine, Apache-2.0):
Impeccable by Paul Bakaus — pulled from its source so it
stays current, not forked. Skip it with
LANDING_CRAFT_IMPECCABLE=0.
If a piece is ever missing, the agents degrade gracefully (e.g. the design/polish phases apply the craft rules by hand instead of calling Impeccable).
landing-craft/
├── skills/
│ ├── craft-core/ the shared spine — hardening · contrast-check · animation-levels · assets
│ │ · remediation · safety-net · codebase-hygiene
│ ├── landing-craft/ the landing orchestrator + playbook · market-research · site-architecture
│ │ · alive-not-generic · instrumentation
│ ├── app-craft/ the app orchestrator + app-not-generic · ia-and-flows · design-system
│ │ · app-shell · screen-patterns · states-and-edges · interaction-a11y
│ │ · data-contract · adopt-existing · app-motion
│ └── motion-craft · marketing-strategy · brand-voice · seo-geo · design-review-loop · web-assets
├── agents/ 27 specialist sub-agents (14 landing-* · 13 app-*)
├── commands/ 21 commands (/landing… · /app…)
└── install.sh · install.ps1 cross-platform one-command install (Claude · OpenCode · Cursor)
Built on the shoulders of open source (all Apache-2.0):
- Impeccable by Paul Bakaus — the aesthetic engine, fetched at install time.
- Bundled skills:
motion-craft,marketing-strategy,brand-voice,seo-geo,design-review-loop,web-assets.
Apache 2.0 © propiter. Built to be used, shared, and improved.