Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
153 changes: 153 additions & 0 deletions AGENTS_INSTALL_INSTRUCTIONS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,153 @@
# Agent Install Instructions for VibeShed

**Audience:** an AI coding agent (Claude Code, Cursor, etc.) that a user has asked to install VibeShed.

Follow these steps in order. Prompt the user at each decision point — do not silently pick paths for them.

## 1. Confirm prerequisites

Run these checks and report any missing tool to the user before continuing:

```sh
python3 --version # need >= 3.9
pipx --version # preferred installer; if missing, fall back to: pip install --user vibeshed
uv --version # optional, only for faster venv + deps install
git --version # needed if you install the Claude Code plugin from a git clone
```

If `python3` is < 3.9 or missing, stop and tell the user — VibeShed requires Python 3.9+.

## 2. Install the CLI

```sh
pipx install vibeshed
```

Fallback without `pipx`:

```sh
python3 -m pip install --user vibeshed
```

Verify:

```sh
vibeshed --help
```

## 3. Ask the user where the VibeShed project should live

Ask, do not guess. A sensible default to offer: `~/vibeshed-projects/default`. Let the user override.

Once they pick a path, call it `$PROJECT_PATH` from here on.

## 4. Scaffold the project

```sh
vibeshed init "$PROJECT_PATH"
cd "$PROJECT_PATH"
```

This creates `registry.yaml`, `jobs/`, `shared/`, `AGENTS.md`, `CLAUDE.md`, `PRINCIPLES.md`, and `.vibeshed/manifest.json`.

## 5. Create the project virtual environment

`vibeshed run` spawns scripts with `$PROJECT_PATH/.venv/bin/python` when it exists, so jobs see the deps listed in `requirements.txt`. Create it:

```sh
# Preferred:
uv venv && uv pip install -r requirements.txt
# Fallback:
python3 -m venv .venv && .venv/bin/pip install -r requirements.txt
```

Verify the interpreter VibeShed will actually use:

```sh
vibeshed doctor
```

If `doctor` warns about a missing `.venv`, go back and fix it before moving on.

## 6. Install the Claude Code plugin

This gives the user `/vibeshed:run` and `/vibeshed:set-project` inside Claude Code.

**Option A — local clone of this repo:**

```sh
# If the vibeshed source repo isn't already checked out somewhere:
git clone https://github.com/vibeshed/vibeshed.git ~/src/vibeshed
```

Then, inside Claude Code, ask the user to run:

```
/plugin install ~/src/vibeshed/plugin
```

(Adjust the path to wherever they cloned.)

**Option B — point at an existing checkout:**

If the user already has this repo checked out, tell them the absolute path to the `plugin/` directory and have them run `/plugin install <that-path>` in Claude Code.

After install, confirm both commands appear:

```
/vibeshed:set-project
/vibeshed:run
```

## 7. Point the plugin at the project

Inside Claude Code, have the user run:

```
/vibeshed:set-project <absolute-path-to-project>
```

This writes `~/.config/vibeshed/project` so `/vibeshed:run` works from any working directory.

The env var `VIBESHED_PROJECT` overrides the config file if the user wants a per-shell override.

## 8. Create a first job and verify the loop

```sh
cd "$PROJECT_PATH"
vibeshed new hello
```

Edit `jobs/hello/scripts/main.py` and `jobs/hello/sequence.md` with the user. Then validate and run:

```sh
vibeshed validate
vibeshed run hello
```

Or, from Claude Code anywhere on the system:

```
/vibeshed:run hello
```

Confirm `logs/hello/runs.json` records a SUCCESS entry.

## 9. Hand off

Tell the user:

- Jobs live in `$PROJECT_PATH/jobs/<slug>/`.
- Framework files (`shared/`, `CLAUDE.md`, etc.) are tracked in `.vibeshed/manifest.json` — use `vibeshed update` to pull framework updates with three-way merge.
- `registry.yaml`, `jobs/`, `state/`, `logs/`, and `.env` are 100% theirs.
- Read `$PROJECT_PATH/PRINCIPLES.md` for the four rules every job follows.

## Troubleshooting checklist

Run in order if anything is off:

1. `vibeshed --version` — is the CLI installed and new enough?
2. `vibeshed doctor` (inside `$PROJECT_PATH`) — any red flags?
3. `vibeshed validate` — is the registry and job structure consistent?
4. `cat ~/.config/vibeshed/project` — is the plugin pointed at the right project?
5. `echo $VIBESHED_PROJECT` — is an env var overriding the config file unexpectedly?
17 changes: 17 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,23 @@ VibeShed is for **vibe-coding automations** with an agent in the loop. Every job
pipx install vibeshed
```

Asking an agent to set this up for you? Point it at [`AGENTS_INSTALL_INSTRUCTIONS.md`](AGENTS_INSTALL_INSTRUCTIONS.md) — a step-by-step walkthrough that installs the CLI, scaffolds a project, and wires up the Claude Code plugin.

## Claude Code plugin

The [`plugin/`](plugin/) directory ships a Claude Code plugin with two commands:

- `/vibeshed:set-project <abs-path>` — pin which VibeShed project to target.
- `/vibeshed:run <slug> [-- --key value ...]` — run a job by slug from anywhere.

Install it inside Claude Code:

```
/plugin install /absolute/path/to/vibeshed/plugin
```

See [`plugin/README.md`](plugin/README.md) for details.

## Quickstart

```sh
Expand Down
17 changes: 17 additions & 0 deletions plugin/.claude-plugin/plugin.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
{
"name": "vibeshed",
"description": "Run VibeShed automations from Claude Code with /vibeshed:run.",
"version": "0.1.0",
"author": {
"name": "VibeShed"
},
"homepage": "https://github.com/vibeshed/vibeshed",
"repository": "https://github.com/vibeshed/vibeshed",
"license": "MIT",
"keywords": [
"vibeshed",
"automation",
"agents",
"cli"
]
}
35 changes: 35 additions & 0 deletions plugin/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
# VibeShed Claude Code Plugin

Slash commands for running [VibeShed](https://github.com/vibeshed/vibeshed) jobs from Claude Code.

## Commands

| Command | Purpose |
| --- | --- |
| `/vibeshed:set-project <abs-path>` | Record which VibeShed project to target. |
| `/vibeshed:run <slug> [-- --key value ...]` | Run a job by slug, forwarding passthrough args. |

## Install

From inside Claude Code, with this repo checked out locally:

```
/plugin install /absolute/path/to/vibeshed/plugin
```

Or reference the git repo if your Claude Code build supports it.

## Project resolution

`/vibeshed:run` picks a project in this order:

1. `$VIBESHED_PROJECT` (env var).
2. `~/.config/vibeshed/project` (written by `/vibeshed:set-project`).
3. The current working directory, if it has `registry.yaml` and `.vibeshed/manifest.json`.

## Prerequisites

- `vibeshed` CLI on `PATH` (`pipx install vibeshed`).
- A scaffolded project (`vibeshed init <path>`).

See [`AGENTS_INSTALL_INSTRUCTIONS.md`](../AGENTS_INSTALL_INSTRUCTIONS.md) in the repo root for the full install walkthrough — intended to be read and executed by an agent.
59 changes: 59 additions & 0 deletions plugin/commands/run.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
---
description: Run a VibeShed job by slug with passthrough params.
argument-hint: "<job-slug> [-- --param value ...]"
allowed-tools: ["Bash", "Read"]
---

# /vibeshed:run

Run the VibeShed job identified by the slug in `$ARGUMENTS`. This command targets the VibeShed project recorded by `/vibeshed:set-project` (or the `VIBESHED_PROJECT` env var, or — as a last resort — the current working directory if it is itself a VibeShed project).

**Arguments:** `$ARGUMENTS`

Parse `$ARGUMENTS` as `<slug> [extra args...]`. Everything after the slug is the passthrough argument list for `scripts/main.py`. If the user wrote a literal `--` separator, strip it — `vibeshed run` already inserts one.

## Resolve the project path

Try these in order and stop at the first one that exists and contains both `registry.yaml` and `.vibeshed/manifest.json`:

1. `$VIBESHED_PROJECT` environment variable.
2. The path stored in `~/.config/vibeshed/project` (single line, absolute path). Read it with:
```bash
test -f ~/.config/vibeshed/project && cat ~/.config/vibeshed/project
```
3. The current working directory.

If none resolve, stop and tell the user:
> No VibeShed project configured. Run `/vibeshed:set-project <absolute-path>` first, or export `VIBESHED_PROJECT=<absolute-path>`.

From here on, refer to the resolved path as `$PROJECT`. Every `vibeshed` invocation below MUST run with `cwd=$PROJECT` — pass it via `cd "$PROJECT" && vibeshed ...` in a single Bash call.

## Steps

1. **Confirm the slug is registered.**
```bash
cd "$PROJECT" && vibeshed list
```
If the slug from `$ARGUMENTS` is not in the list, stop. Suggest `vibeshed new <slug>` to the user if they meant to create it.

2. **Read the job's contract.** Read `$PROJECT/jobs/<slug>/sequence.md` — the **Inputs** section lists expected params and env vars. Also read `$PROJECT/registry.yaml` and find the entry for `<slug>`; note any `dependencies.env_vars`.

3. **Check env vars.** For each var in `dependencies.env_vars`, run `printenv <VAR>` (in the resolved project shell). If any are unset, stop and ask the user to provide values before proceeding. Never hardcode secrets.

4. **Fill in missing params.** Compare the params the user supplied in `$ARGUMENTS` against the **Inputs** list in `sequence.md`. If any required params are missing, ask the user — one question per missing param.

5. **Run the job.**
```bash
cd "$PROJECT" && vibeshed run <slug> --trigger agent --agent-id claude-code -- <passthrough-args>
```
Forward everything the user supplied after the slug as `<passthrough-args>`. Do not wrap or interpret those args.

6. **Report the outcome.**
- On exit 0: summarize the SUCCESS line and the log file path the CLI printed.
- On non-zero exit: run `cd "$PROJECT" && vibeshed logs <slug> -n 50` and show the tail, then surface the error message from `runs.json`.

## Notes

- Do not run `scripts/main.py` directly. The CLI enforces `timeout_minutes` and records results in `logs/<slug>/runs.json`; bypassing it hides failures.
- Do not modify `registry.yaml`, `jobs/`, `state/`, or `logs/` while executing a run.
- If `vibeshed doctor` surfaces a `.venv` warning, tell the user but do not attempt to create the venv automatically — they may have a reason for the current interpreter choice.
38 changes: 38 additions & 0 deletions plugin/commands/set-project.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
---
description: Point /vibeshed:run at a specific VibeShed project directory.
argument-hint: "<absolute-path-to-vibeshed-project>"
allowed-tools: ["Bash"]
---

# /vibeshed:set-project

Record the absolute path of a VibeShed project so `/vibeshed:run` can target it from anywhere.

**Argument:** `$ARGUMENTS`

## Steps

1. **Resolve to an absolute path.** If `$ARGUMENTS` is empty, stop and ask the user for the path. Expand `~` via the shell. Example:
```bash
PROJECT_PATH="$(cd "$ARGUMENTS" 2>/dev/null && pwd)"
```
If `PROJECT_PATH` is empty, the directory does not exist — stop and tell the user.

2. **Verify it is a VibeShed project.** Both files must exist:
- `$PROJECT_PATH/registry.yaml`
- `$PROJECT_PATH/.vibeshed/manifest.json`

If either is missing, stop and tell the user:
> `$PROJECT_PATH` does not look like a VibeShed project. Run `vibeshed init <path>` there first.

3. **Persist the path.**
```bash
mkdir -p ~/.config/vibeshed
printf '%s\n' "$PROJECT_PATH" > ~/.config/vibeshed/project
```

4. **Confirm and list.** Run `cd "$PROJECT_PATH" && vibeshed list` to show the user which jobs are now reachable via `/vibeshed:run`.

## Notes

- `VIBESHED_PROJECT` in the environment takes precedence over this config file — mention that if the user seems to be hitting a different project than they expect.
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ build-backend = "hatchling.build"

[project]
name = "vibeshed"
version = "0.1.2"
version = "0.2.0"
description = "Vibe Coding Framework for Personal Automations — agent-agnostic CLI for vibe-coded jobs with passthrough params, exit-code results, and enforced timeouts."
readme = "README.md"
license = { file = "LICENSE" }
Expand Down
2 changes: 1 addition & 1 deletion src/vibeshed/__init__.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
__version__ = "0.1.2"
__version__ = "0.2.0"
Loading