the house

One set of rules, in every harness, on every machine.

A house is a directory you keep under version control. It holds the rules every agent should follow, the few skills every agent should always have, and named patterns for kinds of project.

What is in a house

house/
house.toml      # version, kernel skill list, project patterns, sourcing
RULES.md        # rules every harness loads on every machine
patterns/*.md   # extra rules for one kind of project (optional)
catalog.toml    # pinned sources of on-demand skills (see Catalog)
house.toml
schema = "spindle.house/v1"
version = "0.3.0"
skill_roots = ["../packages"]          # where the named skills live

[kernel]
skills = ["orient", "review"]          # linked into every harness

[patterns.data-publication]
description = "Static data sites"
rules = "patterns/data-publication.md"
skills = ["chart-review", "publish-gate"]

Keep the kernel small. Every always-on skill competes with the others for the model's attention. A skill belongs in the kernel only when most sessions in most projects would use it. Anything narrower belongs in a pattern, and anything occasional belongs in the catalog.

Install it on a machine

bash
$ spindle house init ~/src/my-skills/house
$ spindle house setup --dry-run      # the plan, nothing written
$ spindle house setup                # every harness found on this machine
$ spindle house status
house v0.3.0 at ~/src/my-skills/house
  claude  rules current v0.3.0; kernel 2/2 linked; 0 dead links
  codex   rules current v0.3.0; kernel 2/2 linked; 0 dead links

setup writes RULES.md into a managed block of each harness's always-loaded instruction file and links each kernel skill into its skill directory:

HarnessRulesKernel skills
Claude Code~/.claude/CLAUDE.md~/.claude/skills/
Codex~/.codex/AGENTS.md~/.agents/skills/
Hermes~/.hermes/SOUL.md~/.hermes/skills/spindle/
What setup will not touch Text outside the managed block is never edited. A skill link is created or retargeted only when it is missing, dead, recorded as installed by an earlier setup, or an older Spindle render. Anything else is reported as a conflict and left alone. --prune-dangling also removes dead symlinks from those skill directories, and spindle house remove undoes the setup for a harness.

Keep it current

After you edit the house, bump version. Then one command, suitable for a daily timer, brings a machine up to date:

bash
$ spindle house update
house updated; v0.3.0
21 already current, 3 changed
catalog: 270 skills from 7 sources

update fast-forwards the Git checkout that holds the house, and leaves it alone if that is not a clean fast-forward. It then reinstalls rules and kernel for the harnesses this machine already has set up and rebuilds the catalog index. --no-catalog skips the rebuild.

Point production machines at a dedicated clone of the house rather than a checkout you edit in. Then a half-finished edit never reaches a running agent, and the timer only ever moves to a commit you merged.

Projects carry their pattern

bash
$ cd ~/src/data-site
$ spindle house setup --here --pattern data-publication
$ spindle house status --here

This writes the pattern's rules into a managed block in AGENTS.md, and in CLAUDE.md when that file exists and does not import AGENTS.md. A missing CLAUDE.md is created as a one-line import. The pattern's skills are copied to .agents/skills/<name>, with a relative link from .claude/skills/<name>.

The copies are meant to be committed, so they work in worktrees, on other machines, and in dispatched jobs. .spindle/house.json records the pattern, the house version, and each skill's digest. A later setup --here updates from the house and refuses to overwrite a copy edited in the repository unless you pass --force.

Add --with-house-rules to embed the full house rules in the repository, for environments that never run the machine setup: a hosted agent, a container, a teammate's laptop.

Writing good house rules