agentleFS
nathan-vmnathan-vm/subforge-mcp/CLAUDE.md

subforge-mcp

CLAUDE.md0 starsChanged 57 days agoMITView on GitHub

MCP server exposing every kind of local LM Studio model over stdio — LLMs (chat/delegate_task), embedding models (rank_by_similarity) and decision models (decide/ask_decision/eval_decisions) — plus consent-gated load/unload. Single package, no monorepo.

  • Reads credentials
  • Installs packages

The file

We split this CLAUDE.md into the rules it gives an agent

1 rule. About 0 are common, 1 is distinctive, and 0 are very specific to this project.

  • ≈0

    Common · estimate

    Many files like this have a rule of this kind.

  • ≈1

    Distinctive · estimate

    This author's own choices. Worth a look.

  • 0

    Very specific

    Tied to their project's names, files or tools. Probably skip.

  • Common
  • Distinctive
  • Very specific
  1. Distinctive:

    Trunk-based: All work lands on main via PR, squash-merged.

    line 19

≈ “Common” is an estimate: at least 1 in 5 of the 26,980 CLAUDE.md files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.

Keep what fits and drop the rest. Your version, ready for your agents.
Files
CLAUDE.md

subforge-mcp

MCP server exposing every kind of local LM Studio model over stdio — LLMs (chat/delegate_task), embedding models (rank_by_similarity) and decision models (decide/ask_decision/eval_decisions) — plus consent-gated load/unload. Single package, no monorepo.

Commands

pnpm install
pnpm run build       # tsc -> dist/
pnpm test            # node:test, runs tests/*.test.ts directly against src/
pnpm run test:live   # tests/decision-live.test.ts against a real LM Studio (decision model must be loaded)
pnpm run typecheck   # tsc -p tsconfig.test.json (src + tests, noEmit)
pnpm run lint         # oxlint --type-aware
pnpm run lint:fix

Conventions

  • Trunk-based. All work lands on main via PR, squash-merged. No long-lived branches.
  • Conventional Commits required on PR titles (feat: ..., fix: ..., feat!: ... / BREAKING CHANGE: for majors) — enforced by .husky/commit-msg locally and the pr-title-lint CI workflow. semantic-release reads this history on main to pick the next version, so a mislabeled type/PR title directly produces the wrong release.
  • Version is derived, not hand-edited. package.json#version and CHANGELOG.md are written by semantic-release on merge (.github/workflows/release.yml) — never bump them by hand. src/index.ts reads the version at runtime from package.json rather than hardcoding it.
  • Tests import src/*.ts directly (not dist/) — Node's native TS support runs them without a build step. Keep tests/helpers.ts mocks in sync with any change to the ToolExtra shape in src/index.ts.
  • No implicit LM Studio model loads. Every inference endpoint (/v1/chat/completions, /v1/embeddings, /v1/systemone) JIT-loads an unloaded model, so every tool that calls one checks first: requireLoadedModel (chat, delegate_task, rank_by_similarity) or resolveDecisionModel (decision tools), which also reject a model of the wrong type. load_model is the only tool that loads one, and only behind an MCP elicitation prompt. Don't add a code path that loads a model without going through that. unload_model is intentionally the one operation not gated behind elicitation — freeing memory is low-risk and reversible, unlike consuming it — so its lack of a consent prompt is deliberate, not an oversight.
  • Decision tools never throw. decide / ask_decision / eval_decisions catch everything and return { ok: false, error: { code, message } } with probability 0 — callers gate on probability, so a failure must never look like an answer. eval_decisions stops at the first fatal error (LM Studio down, timeout, wrong/unloaded model) instead of waiting out every case. See docs/adr/0003.
  • Imports inside src/ use .ts extensions (./decisions.ts) so tests can run the sources directly; rewriteRelativeImportExtensions turns them into .js in dist/.
  • delegate_task never runs outside dir. All three of its file tools (read_file/list_dir/edit_file) go through safeResolvePath — don't add a code path that lets the loop touch anything outside the caller-supplied directory, and never add a shell/Bash tool to its tool definitions. Tests for it use the withTempDir fixture in tests/helpers.ts, which creates and cleans up a real temp directory for exercising real filesystem reads/edits.

CI shape

  • ci.yml (PRs + push to main): lint / test / typecheck in parallel, then outdated (allowed to fail) and audit (blocking) once those pass.
  • pr-title-lint.yml: rejects non-Conventional-Commit PR titles.
  • release.yml (push to main only): build, then semantic-release (version, changelog, GitHub release, npm publish). Checks out with a RELEASE_TOKEN secret (fine-grained PAT, Contents read/write) instead of the default token, because main's branch ruleset requires a PR for every update and the default github-actions[bot] identity can't bypass it — the PAT authenticates as a repo admin, who's on the ruleset's bypass list.

Dependabot config (dependabot.yml + its auto-merge workflow) lives on the separate dependabot-config branch, not on main — see that branch's own PR.

Agentic workflow

This repo uses a fixed set of Claude Code sub-agents (.claude/agents/) entered through matching skills (.claude/skills/). A SessionStart hook loads orchestrator's guidance automatically — new sessions default to delegating rather than implementing inline. See docs/adr/0001 for why.

SkillUse it forCalls
orchestratorDefault entry point for any non-trivial feature/fix/refactor. Plans, dispatches, reviews, integrates.planner, developer, code-review, qa
planner"What would it take to do X" — a read-only, file-grounded task breakdown, no code written.none
developerImplementing one concrete, already-scoped task, in its own worktree (.worktrees/<branch>).none
code-reviewReviewing that same worktree once the developer subagent reports finished — zero developer context, never mid-development. /code-review <branch> works standalone too. See docs/adr/0002.none
qaRuntime smoke-testing a user/tool-facing change (new/changed MCP tool behavior). Skip for refactors and internal-only changes.none

Model/effort policy: each sub-agent's .claude/agents/*.md defaults to Sonnet or Haiku at effort: medium or lower. The orchestrator may freely pick Sonnet vs. Haiku per task within that envelope (via the Agent call's model override) — no approval needed. Going past the envelope (Opus, or effort above medium) always requires asking the user first; it's a cost/blast-radius decision, not a judgment call to make silently.

Architecture decisions land in docs/adr/ (one file per decision, docs/adr/template.md to start a new one) — check there before assuming why something is structured a certain way.

MCP servers

.mcp.json declares a project-scoped github MCP server for anyone who clones this repo without the GitHub MCP already configured globally. It reads its token from ${SUBFORGE_GITHUB_TOKEN} (never hardcode a token into .mcp.json — it's committed). Set it locally with a PAT scoped to this repo, e.g. export SUBFORGE_GITHUB_TOKEN=$(gh auth token).

Tooling

  • rtk condenses local command output for the assistant; it's configured at the user's global Claude Code profile level (not per-repo) — see the user's own setup, nothing repo-specific needed.

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.