Skip to main content
Glama
README.md
# Insitu

Insitu gives an AI client a vault of reusable guidance and composes the right piece for the project it is sitting in.

Not a wiki, not a bulletin, and not a model of a codebase. It does not run git and it does not use the network.

Insitu is a portable MCP server. One vault holds the reusable pieces of how an agent should work with you. A project map names which of those pieces apply in this folder. The server composes them into a protocol and writes that core into files the host already loads.

The vault holds five kinds of thing:

- **Articles.** Standing guidance (tone, method, review, identity that changes how the agent operates). One markdown file each.
- **Roles.** Named packs of articles and skills a kind of project includes as a unit (`node`, `repo`, and the like).
- **Projects.** A map per working folder: core articles, on-demand articles, imported packs, and skills.
- **Skills.** Procedures the host should expose as `/name`. Carried by a role or mapped on the project. Copied into host skill directories on `materialize`. Not concatenated into the protocol.
- **Packs.** Versioned capabilities authored outside the vault (system-development, multi-platform, and the like). Installed onto a shelf, then imported by a project.

You already have directions for how an agent should work with you. The pain is reuse. The same guidance needs to show up in more than one place, but not the same set every time. Copies drift. A new repo starts without the ones you meant to bring. You notice after the agent has already gone the wrong way.

Size reports on articles and on the composed protocol tell you when to trim. Skills have their own size summary. They do not go into the protocol token count.

## How it works

- An **article** is one markdown file of standing guidance.
- A **role** is a named, ordered pack of articles and skills a project can include as a unit.
- A **project map** selects articles as core (always loaded) or on-demand (pulled when the work needs them), plus imported packs and mapped skills.
- A **protocol** is composed, never a catalog row. `materialize` writes `PROTOCOL.md` plus host adapters so the core is in the session. `resolve_protocol` inspects the same composition.
- A **skill** is a procedure the host discovers as `/name`. `materialize` copies composed skills into `.grok/skills/`, `.claude/skills/`, and `.cursor/skills/`.
- A **pack** is a versioned bundle on the vault shelf (`library/<id>/<version>/`). `install_capability` / `install_article` pull it and write this map. A single-article install may land in `core` or `on_demand`.

## Install

Requires Python 3.11+ and [uv](https://docs.astral.sh/uv/).

```bash
git clone https://github.com/srmackey/insitu.git
cd insitu
uv sync
uv run pytest
```

`uv run insitu` starts the server on stdio through FastMCP 2. There is no published package. Clone and run from the checkout.

### Vault

One vault per process, resolved in this order:

1. `INSITU_HOME`
2. `--vault /path/to/vault`
3. `~/.insitu`

A vault is folders on disk (`articles/`, `skills/`, `provenance/`, `projects/`, optional `roles/`, `library/`, and `config/`). This repo ships a sample vault:

```bash
uv run insitu --vault examples/vault
```

Keep a personal vault outside the checkout.

### Add the server to a host

See `install/mcp.json.examples.md` for Cursor, Claude Code, and Grok. Cursor and Claude Code use JSON. Grok uses TOML. Typical JSON shape:

```json
{
  "mcpServers": {
    "insitu": {
      "command": "uv",
      "args": ["run", "--directory", "/path/to/insitu", "insitu"],
      "env": { "INSITU_HOME": "/path/to/your/vault" }
    }
  }
}
```

### Routers (once, user-global)

A router tells the host that Insitu exists. It is not the project protocol. It also says: rematerialize the generated pack if it is missing or stale; retrieve the multi-platform pack and write other missing host files.

| Host | Copy from | Copy to |
|------|-----------|---------|
| Cursor | `install/routers/cursor.mdc` | `~/.cursor/rules/insitu-router.mdc` |
| Claude | `install/routers/claude.md` | `~/.claude/rules/insitu-router.md` |
| Grok | `install/routers/grok.md` | `~/.grok/rules/insitu-router.md` |

Optional: paste `install/AGENTS.md` into a constitution file by hand. `materialize` never writes `AGENTS.md`, `CLAUDE.md`, or `CLAUDE.local.md`.

Enable host adapters in the vault with `config/surfaces.yaml` (`grok`, `claude`, `cursor`). From an existing project checkout, call `materialize`. That writes `PROTOCOL.md` plus adapter files under `.grok/rules/`, `.claude/rules/`, and `.cursor/rules/`, and generated skill copies under `.grok/skills/`, `.claude/skills/`, and `.cursor/skills/` for each mapped skill. If the folder is missing, the call is refused (`working_folder_missing`); it does not create one.

## Working with an agent

Once the server, vault, and router are in place, you talk to the agent in the project folder. Insitu keys the project off that folder's name.

**First time in a checkout.** Ask the agent to materialize this project's protocol. That writes `PROTOCOL.md`, the host adapter files, and mapped skill copies. Constitutions and other host files this host loads are not that output; the router retrieves the multi-platform pack and writes those if they are missing. Later sessions load the core on their own. Do not edit the generated protocol or skill files. Change an article, skill, or the project map in the vault, then materialize again.

**Day to day.** The core is already in the session. Treat it as binding. Mapped skills are already in the host skill directories; treat `/name` as binding. Some articles are only *on-demand*: listed, not loaded. When the work needs one, ask the agent to pull it. You can name the guidance ("use summary-first") instead of a path.

**A new project.** Ask what articles, roles, skills, and packs exist. Pick the set this project should carry. Install a capability if this folder should use a whole pack. Then materialize. The point is a deliberate subset, not a paste of everything.

**When something feels off.** If the protocol is missing, stale, or heavier than it should be, ask the agent for Insitu status of this folder (`project_status`) or to inspect the composition and the size report. Rematerialize after you trim or change membership.

**Add or update.** If you find yourself repeating instructions, name and create a new article (or a skill, if it should be a `/name` procedure). Link it to one or more roles or projects. Instructions not working as expected? Find the articles or skills in use and update the right one.

## Tools

Forty-five tools. The list, the hint set on each one, and what it returns are in [docs/tools.md](docs/tools.md).

On initialize the server returns a short operating note: session start is `resolve_protocol` to inspect, and `materialize` writes the composed protocol. That note lives in the server. This page does not repeat it.

Every mutating tool takes `working_folder`. A **bound** chair (the default) may
write only the map whose key matches that folder's basename; an **admin** chair
may name another.

Articles, roles, and skills belong to no single map, so they are gated by reach
instead: creating is always allowed, and editing or deleting one is refused once
a map other than yours composes it. Editing a role is the sharp case, since its
membership reaches every map that carries it. A vault with no
`config/operators.yaml` runs pre-init: writes go through as before and the
result says how to fix it.

```
insitu init --admin <project-key>   # register the first admin; refuses if one exists
insitu operators                    # show the config
insitu                              # start the MCP server (unchanged)
```

## Trust boundary

- Transport is stdio. The host starts a local process as the user who launched it.
- The process reads and writes the vault (`INSITU_HOME`, or `~/.insitu`).
- `materialize` also writes generated files into the working folder the caller names, and only when that folder already exists.
- It does not run git, it does not start a shell, and it does not use the network.
- It does not take a credential.

The same boundary, and how to report a vulnerability, is in [SECURITY.md](SECURITY.md). How the system is structured is in [DESIGN.md](DESIGN.md). What moved between versions is in [CHANGELOG.md](CHANGELOG.md).

## Develop

```bash
uv sync
uv run pytest
uv run insitu
```

## License

MIT. See `LICENSE`.

TDQS

C2.9/5.0

Scored across 44 tools

Disambiguation3/5

The resource-action pattern makes most tools clearly distinct, but several near-duplicate pairs exist: where_used vs where_used_skill, link_stanza vs install_stanza, link_skill vs install_skill, and get_project vs project_status. The descriptions draw clear lines (native vs pack, stanza vs skill), but an agent must read carefully to avoid misselection.

Naming Consistency4/5

The core CRUD naming (list/get/create/update/delete + resource) is highly consistent across projects, stanzas, roles, and skills, and the pack install/uninstall family follows a clear pattern. Deviations like grant, revoke, operators, validate, materialize, and the noun-verb project_status break the convention, and where_used_skill is suffixed inconsistently relative to the generic where_used.

Tool Count2/5

At 44 tools, this server is well into the 'too many' range per the calibration, even though each tool appears justified by the breadth of the domain. An agent must navigate a large surface spanning projects, stanzas, roles, skills, packs, admin, and utilities.

Completeness4/5

Every core resource has full lifecycle coverage — create/get/list/update/delete for projects, stanzas, roles, and skills — plus linking and pack import/export for external content. Minor gaps (no why-log read tool, no findings or review-policy management surface) prevent a 5, but core workflows have no dead ends.

Maintenance

ActivityMaintained
ResponsivenessNo issues