Agent Setup

Install a repo-local Fragments CLI, generate a discoverable design-system contract, mirror it in CI, and prove the supported agent integrations before calling the setup ready.

AI coding tools work better when a repo explains its component vocabulary and gives them a deterministic way to check it. fragments init turns that contract into committed context, local checks, supported hook or rule-file integrations, and a CI check you can require before merge. Local-only checks work offline; the hosted MCP entry needs a valid Fragments API key before an agent can use it.

For the React component library setup (installing @usefragments/ui, theming, providers), see Install & Theming. This page covers the agent and governance layer that wraps any React codebase.

Quick start

Run from the root of the project you want Fragments to govern:

terminal
npx --yes @usefragments/cli init

The bootstrap command runs the published CLI once. Init detects the project and its existing UI library, writes the contract — including govern.canonicalSources when a supported library is detected — then pins the exact running version of @usefragments/cli as a dev dependency, installs it with the repo's package manager, and verifies that local binary. It writes agent context, MCP configuration, a governance baseline, and a release-safe CI workflow before installing the explicit Claude Code, Codex, Cursor, and GitHub Copilot integrations. Setup ends by running fragments doctor. Only a successful required-check pass earns the final Ready state.

terminal
# npm: offline prevents a registry fallback if the local binary is missing
npm exec --offline -- fragments status

# equivalent local invocations
pnpm exec fragments status
yarn run fragments status
bun run fragments status

status checks the committed configuration. It does not claim the hosted MCP endpoint is reachable or that an agent executed its hook. Use Doctor for the local activation chain and the generated workflow for the repository-wide check. Make that check required in your repository rules when it must block merges.

Configured is a valid staged state.
--no-install writes the exact dependency declaration but skips the package-manager install, so hooks wait for a later init. --no-hook installs the local CLI but deliberately skips agent integrations and Doctor. Both finish as Configured, never Ready.

The Guardrails Contract

A repo has a complete configuration contract when four things are true. fragments status verifies these persisted facts; Doctor separately verifies local activation.

  • Agent context current. AGENTS.md references .fragments/agent-context.md, which exists and was generated against your current preset.
  • MCP configured. .mcp.json has a hosted fragments entry. This proves configuration shape, not authentication, network reachability, or tool availability. With a valid API key, compatible clients can call design_system/conform and design_system/prove_compliant mid-edit.
  • CI mirrors local. A discoverable GitHub workflow runs the committed local CLI. Local-only runs use the committed config; connected runs use Cloud policy when the scoped CI secret is present. Status requires a pull-request trigger, a gating --ci check step, and no fail-open setting on that step. Nested projects are scoped from the repository-root workflow.
  • In sync with team (when Cloud-connected) — sync metadata is inside the allowed age; when status has a Cloud token, it also compares the catalog revision.

What init writes

Re-running init refreshes Fragments-owned sections without replacing unrelated config or instructions.

  • package.json — an exact @usefragments/cli dev dependency matching the bootstrap CLI. Default init runs the native package manager and verifies the local binary; its lockfile records that version. --no-install stages only the manifest change.
  • fragments.config.ts — project shape, framework, pinned preset version (e.g. universal@2), and govern.canonicalSources when an existing UI library is detected — so canonical-component enforcement works from the first scan, scoped to the component names that library actually exports.
  • AGENTS.md — the cross-tool convention file. On first run Fragments creates it; on subsequent runs it adds only one pointer to the generated context. The rest of the file stays yours.
  • .fragments/agent-context.md — canonical primitives, available tokens, enabled rules, and the definition-of-done agents should follow. Generated on every init run.
  • .mcp.json — merged conservatively. We only own the fragments entry; any other MCP servers you have configured are preserved. The fragments entry always points at the hosted Fragments MCP endpoint with an Authorization: Bearer ${FRAGMENTS_API_KEY} header resolved from the environment at runtime.
  • .github/workflows/fragments*.yml — a PR + push workflow at the git repository root. It installs from the frozen lockfile and runs the exact committed CLI with fragments check --ci against the committed config, emits SARIF for GitHub code-scanning, and writes a JSON report to .fragments/governance.json.
  • .fragments/baseline.json — governance snapshot at init time. Future scans can compute deltas against this baseline.
  • .fragments/classification.json — per-component canonical mapping. Heuristic classification always runs; setting ANTHROPIC_API_KEY or OPENAI_API_KEY adds an AI semantic layer for low-confidence components. Re-run fragments classify after adding a key.
  • Agent hook config — programmatic hook entries for Claude Code and Codex, plus static rule files for Cursor and GitHub Copilot (unless --no-hook). Default init installs and verifies @usefragments/cli as an exact dev dependency so the hook command is repo-portable. Teammates still need to install dependencies, and Codex users must trust the project hook and enable its hooks feature. See Agent contract hook.

Setup finishes by running fragments doctor after the exact local CLI and integrations are installed. Its required checks validate the hook entries, pinned command, contract resolution, and a synthetic payload through the installed hook. Init prints Ready only when those required checks pass. With --no-install or --no-hook, it skips this proof and prints Configured. Run Doctor anytime; pass --json for machines or --reset-debounce to clear per-session hook state first.

Agent contract hook

MCP lets an agent pull validation when it chooses to. The contract hook pushes your guardrails into the agent as it works — so your canonical primitives and tokens reach it before the PR, not flagged after merge. It reads the same Cloud-served rules and scan scope as connected CI. The hook checks a conservative subset and fails open when policy context is unavailable; CI remains the complete repository check. Require that check in your repository rules when it must block merges. init targets Claude Code, Codex, Cursor, and GitHub Copilot explicitly (opt out with --no-hook). Other agents still benefit from committed context and CI but do not receive an integration file. The standalone command can retarget one of the four integrations:

terminal
npm exec --offline -- fragments hook install --agent all

How the contract reaches each agent depends on what that agent supports:

  • Claude Code — programmatic hooks inject the vocabulary card at session start, plus a check at the moment of each governed edit (before the agent writes a raw <button> or a hardcoded hex). Advisory by default — add --mode blocking to also deny a write locally on a confirmed, deterministic violation (a raw color where a token exists; a canonical-component bypass) — never a judgment call, and only what CI would also fail. A deny embeds the conformed replacement — corrected content produced by the same deterministic rewrite engine as design_system/conform — so Claude can retry with the fix instead of guessing. Producing that fix is deterministic; the agent applying it is probabilistic, so after two denies for the same file and finding set the hook downgrades to advisory and lets CI arbitrate. CI stays the source of truth.
  • Codex — session-start and prompt hooks inject the contract. Codex does not accept advisory context on its pre-tool event, so advisory mode does not claim a write-time check. Blocking mode adds a pre-tool deny for confirmed violations. Project hooks also require trust via /hooks and [features].hooks = true in the user config.
  • Cursor & GitHub Copilot — these have no programmatic edit hook, so they get a static, always-on rule file instead (.cursor/rules/fragments-design-system.mdc with alwaysApply: true, .github/copilot-instructions.md), embedding your real canonical component names and token prefix. This is static injection, not interception: the contract rides in every conversation, but these tools cannot block a write. The files refresh on the next install; the CI check remains the agent-independent backstop.

Target one agent with --agent claude|codex|cursor|copilot, turn on the local deny gate, or fold installation into library setup with fragments setup:

terminal
# advisory hook for one agent
npm exec --offline -- fragments hook install --agent codex

# local deny gate (Claude/Codex) — blocks confirmed hard violations pre-write
npm exec --offline -- fragments hook install --agent claude --mode blocking

# install during library setup, then remove later
npm exec --offline -- fragments setup
npm exec --offline -- fragments hook uninstall --agent all
Fail-open, idempotent, and portable.
A hook bug never blocks your agent — the engine always exits cleanly and a deny is expressed in the response, never as an error. When @usefragments/cli is installed as a declared dependency, the hook command is repo-portable with no machine-absolute paths — commit .claude/settings.json and teammates can run the same pinned command after dependency install. Agent trust and feature settings still apply. Without the dependency, install pins the resolved CLI path instead. Re-running does not duplicate Fragments-owned entries, and unrelated hooks are preserved. Prove the chain anytime with fragments doctor.

The vocabulary card

The highest-leverage moment to influence an agent is before it writes code. The vocabulary card is a compact (≤2.5KB) digest of your contract, built from your confirmed canonical mappings: canonical component names with their import path, your token prefix, a short exemplar, and a contract-hash stamp so staleness is detectable. If the contract has no confirmed component names yet, the card degrades honestly to a token-prefix and canonical-preference nudge — it never fabricates names.

When it reaches each agent:

  • Claude Code & Codex — injected at session start, including after a session resume, a context compaction, or a clear (long sessions would otherwise lose it), and re-stamped on prompts with debounce. Claude also gets the advisory write-time check; Codex adds a write-time hook only in blocking mode.
  • Cursor & GitHub Copilot — the same vocabulary is embedded in their static rule files at install time. Always present in conversation context, but static: it refreshes on the next install, not per session.

Honest coverage note: injection raises the probability that the first draft is already on-system — it is measured and improving, not a guarantee. Writes that bypass hooked tools (shell-mediated file edits, un-hooked editors) are not intercepted at write time; the CI check covers the repository regardless of which agent or human produced the change. Configure it as a required check to enforce a merge boundary.

Coming from Cloud

If your repo is linked at app.usefragments.com, the token type determines what init is allowed to do:

  • Setup token (fca_…). A one-time onboarding handoff. Init completes the local path, runs Doctor, and submits a verified setup projection only after it reaches Ready. The token is not stored, does not create Cloud sync metadata, and does not authenticate hosted MCP or later Cloud-backed checks.
  • Project token (fc_…). Durable project authentication. Init resolves the Cloud catalog scope, installs generated agent context, caches the findings baseline, records sync metadata, and writes an ignored, mode-0600 .fragments/mcp.env for CLI checks and hooks (plus the OS keychain when available). MCP clients do not load that file or keychain entry.
terminal
# one-time setup handoff
npx --yes @usefragments/cli init --token="$FRAGMENTS_SETUP_TOKEN"

# durable project connection
npx --yes @usefragments/cli init --token="$FRAGMENTS_API_KEY"

The project-token path gives a fresh project a scope-aligned config; an existing fragments.config.ts is kept by default. Cloud policy is not copied into that file as a hidden rewrite. Re-run init explicitly when you want to refresh generated Cloud context and baseline data.

To use the hosted MCP entry, export FRAGMENTS_API_KEY into the editor or MCP process environment, or use that client's secret configuration. The generated .mcp.json references that process variable; init does not make a fresh editor process authenticated automatically.

No background source-file mutation.
Cloud does not push file changes into the repo. Only an explicit CLI command writes generated context, baseline, or sync metadata. The committed fragments.config.ts remains the reviewable repo config and local-only fallback. When a scoped project credential is supplied, the Cloud-served policy is authoritative for checks and hooks; a failed policy fetch does not silently fall back to local rules. Connected CI therefore needs the generated project-specific secret.

Verifying with fragments status

status reads four persisted contract items and reports a pass/fail per item. It verifies configuration, not live MCP connectivity or agent execution.

terminal
$ npm exec --offline -- fragments status

Fragments status

  ✓ Agent context current
    .fragments/agent-context.md is referenced and current.
  ✓ MCP configured
    Fragments hosted MCP endpoint is configured; runtime availability is not asserted.
  ✓ CI mirrors local
    .github/workflows/fragments.yml runs fragments check with universal.
  - In sync with team
    No Cloud sync file found; local-only project.

Guardrails configured.

Exit codes

status exits non-zero when any required item fails. Each item has a stable exit code so scripts can react specifically.

  • 0 — all required configuration checks pass.
  • 11 — Agent context current failed (missing or stale).
  • 12 — MCP configured failed (entry missing, malformed, or locally unresolvable).
  • 13 — CI mirrors local failed (no discoverable, gating pull-request workflow runs the check for this project).
  • 14 — In sync with team failed (Cloud sync stale or rules version mismatch).

Pre-commit hook

npm example for Husky, lefthook, or a plain git hook:

.husky/pre-commit
#!/usr/bin/env sh
npm exec --offline -- fragments status || {
  echo "Run 'npx @usefragments/cli init' to refresh guardrails."
  exit 1
}

For JSON output suitable for CI dashboards, pass --json.

CI workflow

init writes a GitHub Actions workflow under the git repository root. A root project uses .github/workflows/fragments.yml ; a nested project gets a path-derived name such as fragments-apps-cloud.yml so multiple packages do not overwrite one another. The workflow installs dependencies with the package manager's frozen-lockfile mode and runs the committed local CLI — no floating @latest or registry fallback — then executes fragments check --ci on PRs and pushes without passing a second preset. Local-only CI reads the committed config; a scoped API-key secret makes Cloud policy authoritative. The job emits SARIF for GitHub code-scanning and writes a JSON report to .fragments/governance.json. The check step remains the gate; SARIF upload runs on failure and is best-effort so a GitHub code-scanning outage cannot replace the real result.

To ingest findings into Fragments Cloud (Check Runs + inline PR review comments), add a project-scoped key in your GitHub repo settings:

  • FRAGMENTS_API_KEY — used by a repository-root project.
  • FRAGMENTS_API_KEY_APPS_CLOUD — example generated name for a nested project at apps/cloud. Each nested Cloud project gets its own path-derived secret name and must receive its own scoped key.

The hosted Cloud URL is the runtime default. The workflow omits FRAGMENTS_CLOUD_URL unless init received an explicit, nonblank --cloud-url override.

Monorepos

GitHub Actions only reads workflows from the repository root, so a project at a subpath like apps/cloud cannot rely on a workflow at apps/cloud/.github/workflows. Init handles this directly: it walks to the git root and writes a unique workflow in .github/workflows/. Dependency install runs at the directory that owns the detected lockfile (normally the workspace root); only the Fragments check gets a working-directory matching the subproject. Report and SARIF upload paths are rooted correctly as well. Status scans only repository-root workflows and requires either a matching working directory or a matching --dir. An unscoped repository-root check is not treated as proof that the nested project's config was discovered.

For a project under apps/cloud with multiple packages, run init from each project root. Each gets its own scoped token (when Cloud-connected) and its own context files.

terminal
# from a monorepo subpackage
cd apps/cloud
npx --yes @usefragments/cli init
npm exec --offline -- fragments status

AI component classifier

On first run, init heuristically scans components and maps them to canonical primitives (Button, Input, Dialog, etc.). If you provide an Anthropic or OpenAI API key, low-confidence mappings can receive an additional semantic classification pass using that key.

export ANTHROPIC_API_KEY=sk-ant-...
npx --yes @usefragments/cli init

If no key is set, the AI semantic pass is skipped cleanly; heuristic classification still runs. Add a key and run npx @usefragments/cli classify later when ready.

Updating

init is idempotent. Run it again to:

  • Refresh .fragments/agent-context.md with the latest preset rules.
  • Re-pull team rules from Cloud (when a token is configured).
  • Re-baseline governance findings.
  • Pick up a new preset version (e.g. moving from universal@2 to universal@3).

Your AGENTS.md body is never touched after the initial pointer is added. Add --force to reinitialize an already-set-up project from scratch.

Troubleshooting

Exit code 11 — agent context. Most often: AGENTS.md doesn't reference .fragments/agent-context.md. Re-run init to add the pointer line, or add See: .fragments/agent-context.md by hand.

Exit code 12 — MCP entry. Your .mcp.json exists but the fragments server entry is missing or malformed. Re-run init to repair just the fragments entry — other servers stay untouched.

Exit code 13 — CI mirror. No gating pull-request workflow runs fragments check with --ci for this project, or the check step is allowed to fail. In a monorepo, put the workflow at the git root and either set a matching working-directory, pass --dir <your-project-path> or scan the whole repo.

Exit code 14 — Cloud sync. Local sync metadata is older than the tolerance window (default 168h), or — when a Cloud token is available to status — the catalog revision differs. Re-run init with your token to refresh generated Cloud context, baseline data, and sync metadata.

For machine-readable output, pass --json to status — the same checks come back as a structured object with the failing item identified by id.