From vibe-taker
Plant a captured bundle from the shelf into the current repo. Detects target stack, picks code-lift (high match) or spec-driven (low match) or declines (hard mismatch). Always shows the diff before any write.
How this skill is triggered — by the user, by Claude, or both
Slash command
/vibe-taker:plantThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
> Implements [`spec.md > Plant Flow Architecture`](../../docs/spec.md#plant-flow-architecture) and [`prd.md > Epic: Plant`](../../docs/prd.md#epic-plant).
Implements
spec.md > Plant Flow Architectureandprd.md > Epic: Plant.
The mostly-mechanical half — once the bundle schema is locked, plant reads, detects, decides, stages, confirms, writes. The mandatory checkpoint is the diff [y/N]. No file is written without explicit user confirmation.
skills/guide/SKILL.md — voice, hygiene, references catalog.skills/guide/references/bundle-schema.md — what the bundle's contract.json carries.skills/guide/references/stack-match.md — the decision tree, framework families, decline message.skills/guide/references/error-contract.md — class-0/1/2 outcome shapes.Then execute the phases below in order.
Form: /vibe-taker:plant <name> [--version=vX].
<name> — required. The bundle slug.--version=vX — optional. If absent, plant uses index.json.bundles[i].latest_version.Reject any other flags in v1 (no --yes, no --shelf-path per KTD-6/KTD-7). Print:
[exit 1] Unknown flag `<flag>`. v1 supports: `<name>` [--version=vX]
Read ~/.vibe-taker/library/index.json. If absent or unparseable JSON, exit class-2:
[exit 2] Library index missing or corrupt at ~/.vibe-taker/library/index.json. Re-capture a feature to rebuild, or restore from backup.
Validate the index against skills/guide/schemas/index.schema.json. Same class-2 path on validation failure with the schema error appended.
Find the entry whose name == <input-name> (exact, case-sensitive). On absent:
[exit 1] No bundle named '<name>' on the shelf. Run `/vibe-taker:list` to see what's available.
Resolve version:
If --version=vX was passed, look up the matching entry in versions[]. On absent:
[exit 1] Bundle `<name>` exists but version `<vX>` not found. Available: <comma-separated versions>.
If --version was absent, use latest_version.
Read ~/.vibe-taker/library/<name>/<version>/contract.json. Parse JSON.
Validate the contract against skills/guide/schemas/contract.schema.json. On validation failure, exit class-2:
[exit 2] Bundle `<bundle-path>/contract.json` failed schema validation: <error>. Hand-edit the file or re-capture the source.
Carry contract.language, contract.framework, contract.interface_kind, contract.entry_points, contract.env_vars into the working state for downstream phases.
Walk the current working directory (and one level up if cwd has nothing) for manifests, in priority order:
| Manifest | Implies | Framework derivation |
|---|---|---|
package.json (with "type": "module" OR .ts files anywhere in cwd tree) | Node — TypeScript or JavaScript | Read dependencies for highest-signal dep: express/fastify/hapi/koa (web/server), react/vue/svelte (web/client), next/nuxt (web/fullstack), yargs/commander/oclif (CLI). |
pyproject.toml / requirements.txt / setup.py | Python | Read deps for fastapi/flask/django (web), pandas/jupyter (data), click/typer/explicit argparse usage in entry points (CLI). |
Cargo.toml | Rust | [dependencies] lookup for actix-web/rocket (web), clap (CLI). |
go.mod | Go | require block: gin/echo (web), cobra/urfave/cli (CLI). |
*.csproj / *.sln | C# | XML <PackageReference> lookup. |
Gemfile | Ruby | Gemfile parse for rails/sinatra. |
composer.json | PHP | require lookup. |
If multiple manifests co-exist (monorepo), pick the one closest to cwd (cwd wins over parent). Carry target.language, target.framework, target.framework_family.
If no manifest detected in cwd or one level up: set target.language = null, target.framework = null. The decision tree handles this as the no-manifest fallback.
Apply the table from stack-match.md:
match_level = compute_match(contract.language, contract.framework, target.language, target.framework, target.framework_family)
Where:
contract.language == target.language AND same framework family. Mode: code-lift. (v1 ships zero adapters; same-language same-family code-lift keeps the source's framework choice.)contract.language == target.language, different framework family. Mode: spec-driven.contract.language != target.language (and target.language is not null). Mode: decline.target.language is null (no manifest). Mode: spec-driven with notice.The chosen mode and match_level are named in the diff header (Phase 7).
Triggered when match_level == "hard". No file is written.
Print verbatim, substituting <source-lang> (= contract.language), <target-lang> (= target.language), <bundle-path> (= ~/.vibe-taker/library/<name>/<version>/):
vibe-taker bundles capture <source-lang>; your target repo is <target-lang>. v1 doesn't auto-port across languages — too lossy. Here's the architecture sketch (<bundle-path>/architecture.md) and reference code (<bundle-path>/reference/); port manually, or capture a <target-lang>-native version of this feature into a new bundle.
Exit class-1.
Triggered when match_level == "fallback". Print before continuing into spec-driven mode (Phase 6 in item 8):
No manifest detected in target — falling back to spec-driven re-implementation. Reference code in <bundle-path>/reference/ for guidance.
Then proceed to Phase 6 (item 8) with mode = spec-driven, match_level = fallback.
When Phases 1-3 leave us in code-lift (high) or spec-driven (low or fallback), the diff (rendered in Phase 7, item 8) is preceded by:
Mode: <code-lift | spec-driven>
Stack match: <high | low | hard-decline | fallback>
Bundle: <name> <version> · source: <contract.language>/<contract.framework or none>
Target: <target.language or "no manifest">/<target.framework or "—">
This is what the user reads before answering the [y/N] prompt.
Triggered when mode == "code-lift" (high match).
Determine where files land in the target. Follow the target's existing convention:
pyproject.toml + a src/<package>/ layout → place files under src/<package>/<feature>/. Read <package> from [project].name (PEP 621) or [tool.poetry].name (Poetry).pyproject.toml + flat layout (no src/) → place files under <package>/<feature>/.requirements.txt (no pyproject.toml) → place files at root with <feature>/ subdir.src/ → src/<feature>/.src/ → <feature>/ at root.src/<feature>/ (always src/ in Cargo crates).<feature>/ package at root or under internal/<feature>/ if internal/ exists.<Feature>/ (PascalCase) folder under the .csproj directory.<feature>/ at root.<feature> is the bundle's slug (contract.name). For single-file bundles where the entire feature is one file, place that file at <feature>.<ext> rather than under a folder.
Walk every .py / .ts / .tsx / .js / .jsx / .rs / .go file being placed.
Python:
from . and from <source-package>.<...> → rewrite to target package.
reference/<src-tree>/pyproject.toml if captured; else infer from entry_points).[project].name / [tool.poetry].name of the target's pyproject.toml.Node:
import './<rel>' and import '../<rel>' — keep relative (path is preserved by the tree placement).import 'src/<...>' or import '@<alias>/<...>' — adjust to target's tsconfig.json#paths if present, else rewrite to a target-relative form.require('<source-pkg>/<...>') for the source's own package name → target package name.Rust:
crate:: references stay (crate-relative). use <source-crate>::<...> rewrites to target crate.Go:
<source-mod>/<...> rewrite to <target-mod>/<...> from go.mod's module line.Adapter coverage: v1 ships zero in-language framework adapters (no Click→Typer, no Express→Fastify, etc.). When a framework call site doesn't translate cleanly inside the same family, fall back to spec-driven mode for that file specifically — render the file as a fresh re-implementation rather than a literal copy. Per-file fallback keeps the rest of the code-lift intact.
Build a unified diff against the target's current state:
+++ block with full content.Stage in memory or in a session-only .vibe-taker-staging/ directory under cwd. Do not commit the staging directory; .gitignore covers it.
Continue to Phase 8 (diff render + confirm).
Triggered when mode == "spec-driven" (low match or fallback).
<bundle>/architecture.md — components, data flow, key files.<bundle>/contract.json — exact I/O surface to match in the target.<bundle>/notes.md — why and gotchas; preserve tradeoffs in the target.<bundle>/reference/ files — for shape and intent, as a guide, not a copy source. Don't lift literal code; re-derive in the target's framework conventions.contract.inputs.contract.outputs.contract.env_vars (rename target-side conventions if any apply).Continue to Phase 8.
[y/N] checkpointThe single mandatory user-confirmation point. PRD Plant story 1: "No file is written without explicit user confirmation." No --yes flag in v1 (KTD-7).
Print the unified diff to stdout. Format:
Mode: <code-lift | spec-driven>
Stack match: <high | low | fallback>
Bundle: <name> <version> · source: <contract.language>/<contract.framework or none>
Target: <target.language>/<target.framework or "—"> at <cwd>
--- Files to be written ---
(<N> files; <total-bytes> bytes)
<unified diff per file, in dependency-friendly order: contracts/types first, entry points last>
--- Env vars from bundle (provide before running) ---
<list of contract.env_vars with load_bearing flag>
--- Notes carried from bundle ---
<bundle's notes.md > Gotchas section, verbatim>
Make it scannable. Long diffs are fine; the user is making a binary decision but should have the full picture.
Print on its own line:
Apply this diff? [y/N]
On n, empty input, or any non-y answer:
No file is written.
Print:
No files written.
Clean up .vibe-taker-staging/ if it was used.
Exit class-0 (the user declined cleanly; this is success, not failure).
On y:
<target-path>.tmp.mv <target-path>.tmp <target-path>..tmp files already written (delete them) and exit class-2 with the failed path..vibe-taker-staging/ directory under cwd.Per-file .tmp + mv makes each individual write atomic on POSIX (and on Windows with NTFS for same-volume moves). The whole-plant operation is not atomic — it's a sequence of per-file atomic moves. If something dies between file 3 and file 4, files 1-3 are landed and 4-N aren't. This is acceptable in v1: the [y/N] confirmation already gives the user the full picture; mid-flight crashes are vanishingly rare for filesystem ops; and a partial plant is still partial valid code (each file individually is consistent).
PRD Plant story 5. Pattern #13 (ecosystem-aware composition).
After a successful apply (Phase 8.4):
Check whether mcp__626Labs__manage_decisions is in the agent's runtime tool list.
If absent — succeed silently. No retry, no error, no warning. The plant is already a success.
If present — call:
action: log
body:
title: "Planted <name> <version> into <cwd-basename>"
description: |
Source: <contract.source_repo> (<contract.source_path>)
Target: <cwd>
Mode: <code-lift | spec-driven>
Stack match: <high | low | fallback>
tags: ["vibe-taker", "plant", "<contract.language>"]
projectId: <bound-project-id-if-current-repo-bound-else-null>
bound-project-id: read git config --get remote.origin.url from cwd; if a remote exists, optionally call mcp__626Labs__manage_projects with action findByRepo to get the project ID. If no remote or no match, set projectId: null and tag the decision with the cwd basename.(dashboard log failed; plant succeeded) and exit class-0 anyway.Class-0 outcome after a y on the diff.
✓ Planted <name> <version> into <cwd>
<N> files written.
Mode: <code-lift | spec-driven> · Stack match: <high | low | fallback>
Env vars to set before running:
<list of load-bearing env vars from contract>
Source: <contract.source_repo> (<contract.source_path>)
<(dashboard log succeeded | plant logged to 626Labs Dashboard | dashboard not connected)>
Exit class-0.
All exits include a one-line recovery action per error-contract.md:
y → class-0 with the summary above.n) → class-0; "no files written."The diff is the load-bearing checkpoint. Until the user types y, no file in cwd is touched.
npx claudepluginhub estevanhernandez-stack-ed/vibe-taker --plugin vibe-takerProvides behavioral guidelines to reduce common LLM coding mistakes, focusing on simplicity, surgical changes, assumption surfacing, and verifiable success criteria.
Searches, retrieves, and installs Agent Skills from prompts.chat registry using MCP tools like search_skills and get_skill. Activates for finding skills, browsing catalogs, or extending Claude.
Creates, edits, and optimizes skills for Claude Code, including drafting, evaluating with test prompts, iterating on performance, and improving skill descriptions for better triggering accuracy.