> For the complete documentation index, see [llms.txt](https://faction-os.gitbook.io/faction-os-docs/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://faction-os.gitbook.io/faction-os-docs/apps/cli/readme_cli.md).

# @factionos/cli

Command-line tool for local FactionOS setup and diagnostics.

The current installer targets Claude Code hook settings by default and can also install user-level Codex CLI hooks when selected. FactionOS remains local-first: it creates local state under `~/.factionos/`, writes selected local agent hook configuration, and does not require hosted auth, hosted storage, or API keys. Provider selection is available with `--cli claude|codex|all`.

## Install

```bash
npm install -g @factionos/cli
# or, from the monorepo:
npm --workspace apps/cli link
```

## Commands

```
factionos init                              # First-run Claude Code setup
factionos install                           # Alias for init
  --cli claude|codex|all                    # Select provider routing; default is claude
  --faction orc|human|elf|undead|lobster    # Pre-assign a faction
  --server-url http://localhost:2468        # Override default server URL

factionos start                             # Start server + web from the current repo workspace
factionos start --daemon                    # Start in the background and record a managed PID
factionos launch                            # Alias for start
factionos open                              # Open the local web client when server/state is ready
factionos stop                              # Stop the CLI-managed background runtime
factionos status --cli claude|codex|all     # Live snapshot plus provider and lifecycle diagnostics
factionos doctor --cli claude|codex|all     # Diagnose provider hooks, orchestration, server, PIDs, ports, and workspace scripts
factionos doctor --recover-orchestration    # Remove stale listener PIDs and malformed spool entries only
factionos notice post status "Working on X" # Post an agent Notice Board message
factionos notice list                       # List active unresolved notices
factionos notice list --type review         # List active review notices
factionos notice context --session sess_1   # Read bounded notice context for a session
factionos notice resolve notice_1           # Resolve an active notice
factionos erase                             # Preview release-scoped local erasure
factionos erase --confirm "ERASE LOCAL FACTIONOS STATE"
factionos uninstall --cli claude|codex|all  # Remove selected FactionOS-managed provider hooks
```

The CLI auto-loads env files in this order when run from this monorepo: root `.env.local`, root `.env`, `apps/cli/.env.local`, then `apps/cli/.env`. Already-exported shell variables keep priority over file values, earlier files win over later files, and blank placeholders are ignored. Prefer root `.env.local` for normal local deployment.

## Notice Board Commands

`factionos notice` talks to the canonical local Notice Board routes exposed by the FactionOS server. It uses `FACTIONOS_SERVER_URL` when set, then local lifecycle/settings state, and falls back to `http://localhost:2468`.

```bash
factionos notice post status "Working on CLI notice commands"
factionos notice list
factionos notice list --type review
factionos notice context --session sess_abc123
factionos notice resolve notice_abc123
```

Supported notice types are `status`, `question`, `review`, `announcement`, `conflict`, `completion`, and `human`. `notice post` sends canonical `type` and `content` fields with `authorType: "agent"`. The message is bounded by the server Notice Board content limit and is intended for brief coordination, not transcripts or command dumps. The CLI derives `authorSessionId` from `FACTIONOS_SESSION_ID`, provider session environment values, local settings, or `unknown`. It derives the display author from safe local/env display settings and otherwise prints `Agent-<session-prefix>`.

When `FACTIONOS_AUTH_TOKEN` is configured, notice requests include it only as `Authorization: Bearer <token>`. The token is not printed in command output or compact errors.

`notice list` fetches `GET /notice-board?limit=20` and includes `forSession` when a usable session id is available. `notice list --type <type>` validates the type before sending the request. List output is a compact terminal summary: timestamp, type, author, content, priority, and up to the first three related files per notice. It does not print full response JSON or hidden target lists. Empty results print `No active notices on the board.`

`notice context --session <id>` fetches bounded `/notice-board/context` output for the requested session and prints only the returned context text. `notice resolve <noticeId>` posts to `/notice-board/<noticeId>/resolve` and includes the local author session id when one is available. Missing arguments, invalid types, unreachable server, malformed responses, unauthorized responses, and non-2xx server responses map to compact CLI errors without dumping raw response bodies.

Notice output is for explicit coordination messages only. The CLI redacts secret-like values, bearer tokens, URLs, and absolute paths in formatted output and errors, and it does not print raw server error bodies. Do not use Notice Board messages for raw prompts, transcripts, terminal output, command bodies, file contents, secrets, absolute paths, logs, exports, replay buffers, scans, diagnostics, backups, media drafts, or quarantined historical material.

## Provider Selection

`factionos init` and `factionos install` remain Claude-only by default for this release. `factionos init --cli claude` is the explicit form of the same setup. `factionos init --cli codex` installs user-level Codex hooks into `~/.codex/hooks.json`, respecting `CODEX_HOME` when it is set. `factionos init --cli all` runs Claude setup first and then installs the Codex hook map.

Invalid `--cli` values fail before local settings or hook files are written. Accepted values are `claude`, `codex`, and `all`; compatibility aliases such as `claude-code` and `codex-cli` normalize to the same provider routes.

Codex support writes only FactionOS local state and user-level Codex hook configuration. It does not mutate Codex auth, provider, telemetry, model, profile, API key, account settings, trusted-project state, or hook trust decisions. It also does not add custom Codex slash commands, generate project-local `.codex` files, package a Codex plugin, or bypass `/hooks` review. Phase 12 Session 01 explicitly defers plugin packaging because direct user-level hooks are the validated supported path for this release.

Source-backed Codex setup notes:

* `CODEX_HOME` is optional. When set, the installer writes that user-level Codex config directory; otherwise it writes `~/.codex/hooks.json`.
* `FACTIONOS_CLI=codex-cli` is injected into managed hook command strings by the installer so hook handlers report Codex events consistently. Users do not normally need to export it.
* Existing Codex hooks are backed up before the first FactionOS write when a raw `hooks.json` is present, then user-owned hooks and unknown top-level fields are preserved during merge.
* Plugin packaging and project-local trusted `.codex` setup are explicitly deferred; the supported path here is user-level hooks plus Codex `/hooks` review.

## What `factionos init --cli claude` Does

1. Creates `~/.factionos/`, `~/.factionos/sessions/`, and `~/.factionos/spool/`.
2. Writes `~/.factionos/settings.json` with faction, server URL, and voice preferences using an atomic temp-file-plus-rename write.
3. Creates `~/.claude/settings.backup.json` from `~/.claude/settings.json` only when a backup does not already exist.
4. Deep-merges the FactionOS hook map into `~/.claude/settings.json` while preserving pre-existing hooks, then writes the result atomically.
5. Sets `CLAUDE_PLUGIN_ROOT` in hook command strings so the handlers resolve to the installed hooks package.

After this, run `factionos start --daemon`, `factionos open`, and then open a new terminal and run Claude Code. A hero can spawn on the FactionOS battlefield when the local server is reachable.

Malformed existing settings files do not crash `factionos init`. The CLI keeps the raw Claude settings backup when possible, falls back to a fresh settings object, and reports the fallback in the terminal.

## What `factionos init --cli codex` Does

1. Creates `~/.factionos/`, `~/.factionos/sessions/`, and `~/.factionos/spool/`.
2. Writes or merges `~/.factionos/settings.json`; it sets `cli: "codex-cli"` only when Codex is the selected default provider.
3. Creates the Codex user config directory from `CODEX_HOME` or `~/.codex`.
4. Backs up the first raw `hooks.json` to `hooks.backup.factionos.json` when an existing Codex hooks file is present and no FactionOS backup exists.
5. Reads `apps/hooks/hooks.codex.json`, interpolates the installed hooks package root, injects applicable FactionOS hook environment values, removes older FactionOS-managed command hooks, and writes the merged `hooks.json` atomically.
6. Preserves user-owned Codex hooks, matchers, events, and unknown top-level fields. Malformed existing hooks are backed up raw and replaced with a fresh managed hooks object during install.

After this, run `factionos start --daemon`, open a new terminal and run `codex`, then review loaded hooks with `/hooks`. Codex may require changed non-managed hooks to be reviewed before they run.

## Provider Workflow Checks

```bash
factionos status --cli claude
factionos status --cli codex
factionos status --cli all
factionos doctor --cli all
factionos uninstall --cli codex
```

Use `status` for a compact live snapshot and `doctor` for actionable provider posture. Codex posture includes hooks file presence, JSON validity, managed-hook counts, unmanaged-hook counts, backup state, hooks feature state, and `/hooks` trust-review guidance. Uninstall removes only selected FactionOS-managed provider hooks: Claude uses `settings.backup.json` when available, and Codex uses `hooks.backup.factionos.json` when available.

## Lifecycle Commands

`factionos start` and `factionos launch` use the current repository workspace scripts. The runtime root must contain the root `dev` script plus `apps/server` and `apps/web` `dev` scripts. From this monorepo, the managed command is equivalent to `npm run dev`.

`factionos start --daemon` records managed lifecycle state under `~/.factionos/`:

* `server.pid` - the CLI-managed root dev process PID.
* `lifecycle.json` - configured server URL, web URL, port, runtime root, workspace root, command metadata, and lifecycle timestamps.
* `project-root.json` - the workspace root being monitored for diagnostics.

`factionos stop` only acts on the managed PID recorded by this CLI. Stale PID files are cleaned automatically. On Linux, stop also checks the process metadata token written at daemon launch and refuses to stop a PID that does not match the recorded lifecycle state.

`factionos open` opens the local web URL only when the server health probe or managed lifecycle state indicates FactionOS is reachable. If the browser opener is unavailable or times out, the CLI prints the manual URL instead.

Default ports are server `2468` and web `5193`. `--port` or `PORT` can change the server process port for the managed runtime, but the current web client still connects to server port `2468` in its shipped code. Use the default port for the full local cockpit until the web port configuration work is completed.

Published-package process supervision is not claimed yet. The lifecycle commands are current-workspace commands for this npm workspace; release packaging can add a different launch boundary later.

## Runtime Diagnostics

`factionos doctor` and `factionos status` inspect local state without printing raw hook payloads, prompts, command bodies, file contents, tokens, or spool entry data. Both commands accept `--cli claude|codex|all`; omitted provider selection reports all provider posture.

Diagnostics currently report:

* FactionOS settings presence and JSON validity.
* Claude settings presence, JSON validity, and whether FactionOS hooks are registered.
* Provider posture for Claude and Codex using compact labels, JSON validity, managed-hook counts, unmanaged-hook counts, backup state, disabled-hook posture, and `/hooks` trust-review guidance.
* Server health using the configured `FACTIONOS_AUTH_TOKEN` when present.
* Local orchestration diagnostics from `/diagnostics/orchestration` when the loopback server is reachable: queue counts, terminal queue execution posture, template availability, mission graph counts, guarded-action counts, and compact server availability labels.
* Local provider diagnostics from `/diagnostics/provider-readiness` when the loopback server is reachable: provider readiness counts, hook status, model-list status, setup command/env-name labels, runtime health counts, and safe recovery descriptors.
* Local isolation diagnostics from `/diagnostics/isolation` or the compact orchestration isolation summary when the loopback server is reachable: non-executing posture, unavailable executor counts, guarded-action posture, and narrow recovery limits.
* Managed lifecycle PID, configured server port, web URL, and workspace root.
* Listener PID files, alive or stale status, and sanitized terminal ids.
* Hook log posture: available, missing, unreadable, malformed, recent line count, and malformed line count.
* Spool posture: queued file count, malformed file count, and total bytes.

Unavailable server responses are reported as local diagnostic state. They are not treated as CLI crashes unless the command specifically requires server data.

`factionos status` keeps orchestration output compact: it prints queue, terminal queue, template, mission graph, guarded-action, hook, listener, and spool posture with explicit offline, unavailable, malformed, and auth-required labels. Terminal queue diagnostics are counts and status labels only: total, executing, completed, failed, unavailable, and linked terminal-session counts. It does not print raw queue titles, proposal rationale, prompts, command bodies, terminal output, stdout, stderr, file contents, tokens, broad absolute paths, transcript paths, raw spool payloads, or raw state file contents.

`factionos status` and `factionos doctor` also keep isolation posture compact. They may print unavailable, offline, auth-required, timeout, malformed, non-executing, and recovery-narrow labels. They must not print raw isolation diagnostic payloads, prompts, command bodies, terminal output, file contents, tokens, broad paths, raw spool payloads, logs, backups, state files, or trusted erasure claims.

`factionos status` and `factionos doctor` keep provider diagnostics compact as well. They fetch only loopback local server URLs, send `FACTIONOS_AUTH_TOKEN` as a bearer header when configured, and print provider/setup/runtime labels instead of raw response JSON. Output may include exact operator-run recovery commands published by the local server. It must not print raw env values, provider payloads, model provider responses, logs, command output, prompts, tokens, broad absolute paths, raw spool payloads, or local state file contents.

`factionos doctor --recover-orchestration` is an explicit local diagnostic repair mode. It only removes stale `listener-*.pid` files and malformed `spool/*.json` entries under the configured FactionOS home. It is idempotent and protected by a local recovery lock. It does not delete settings, lifecycle state, project roots, sessions, archives, memory, browser state, workspace files, valid spool entries, or all `~/.factionos` data.

## Local Erasure Command

`factionos erase` previews release-scoped local erasure through the loopback local server. Preview is non-destructive and prints redacted boundary ids, statuses, counts, manual-review states, unsupported states, and no-overclaim wording only.

Confirmed execution requires the exact typed phrase:

```bash
factionos erase --confirm "ERASE LOCAL FACTIONOS STATE"
```

The command refuses non-loopback server URLs, sends a bounded idempotency key, and formats local-server responses without raw paths, prompts, commands, exports, backups, logs, diagnostics, spool payloads, tokens, or request bodies. It covers eligible local filesystem boundaries only. Browser state is erased from the web Settings drawer. Worker Durable Object state, hosted identity or storage, analytics, public replay, push, remote access, broad workspace files, and full trusted unified erasure remain unavailable.

## Removal

```bash
factionos uninstall --cli claude
```

If `~/.claude/settings.backup.json` exists, uninstall restores `~/.claude/settings.json` from that backup. If no backup exists, uninstall surgically removes hook entries whose command strings reference the FactionOS install path and leaves other user-owned hooks in place.

`factionos uninstall --cli codex` restores `hooks.backup.factionos.json` when that first-run FactionOS backup exists. If no backup exists, uninstall surgically removes only FactionOS-managed Codex command hooks and leaves user-owned Codex hooks in place. If `hooks.json` is malformed and no backup is available, uninstall reports the condition and leaves the file untouched.

Uninstall does not delete user session archives or other local state under `~/.factionos/`.

## Current Integration Boundary

* Claude Code hook installation is the supported CLI setup path and remains the default for `factionos init` and `factionos install`.
* Codex CLI user-level hook installation is supported through `--cli codex` or `--cli all`. The CLI does not generate project-local `.codex` files, create trusted hook state, package a Codex plugin, or add custom Codex slash commands. Phase 12 Session 01 records plugin packaging as an explicit deferral, not a release blocker.
* Non-Claude tools can integrate by posting compatible events to the local server's `/event` endpoint, but this CLI does not yet install Cursor, OpenCode, or other tool-specific hooks.
* The local server and web client can be started together from this repo with `factionos start` or `factionos start --daemon`.
* Published npm package supervision, production process management, and non-workspace launch are deferred to release hardening.
* Listener startup is owned by the hook runtime. The CLI reports listener posture; server/web lifecycle management is separate from listener PIDs.
* Phase 01 runtime docs are the source of truth for shipped local behavior; historical package snapshots under ignored `EXAMPLES/` are traceability evidence only until release decommission gates close.

## Phase 03 Orchestration Diagnostics Boundary

Phase 03 ships queue, template, lineage, guarded-action, hook/listener, spool, and recovery diagnostics for the local orchestration subset. CLI output summarizes health, stale state, malformed state, unavailable server/listener state, terminal queue posture, Git queue posture, policy-blocked Git counts, operation counts, and recovery results without printing raw prompts, command bodies, terminal output, Git stdout, Git stderr, diffs, patch bodies, commit messages, file contents, tokens, broad absolute paths, transcripts, raw queue entries, proposal rationale, or raw state file contents.

Recovery is intentionally narrow: it removes stale listener PID files and malformed spool JSON entries only after an explicit flag. It does not approve guarded actions, execute queue entries, delete valid spool entries, erase settings, remove archives, clear memory, reset browser state, or touch workspace files. Unified erasure remains release-hardening work, not a Phase 03 recovery shortcut.

## Phase 06 Diagnostics Boundary

Phase 06 Session 01 keeps CLI diagnostics and recovery local, compact, and non-executing. Future isolation or sandbox diagnostics may report availability, counts, stale PID state, malformed spool counts, durations, and sanitized identifiers, but must not print raw prompts, command bodies, terminal output, file contents, tokens, broad absolute paths, transcripts, raw queue entries, proposal rationale, raw state files, or raw spool payloads.

CLI recovery must remain explicit and narrow until Phase 08 erasure work ships. It must not be described as trusted deletion, and it must not remove valid spool entries, settings, lifecycle files, sessions, archives, memory, browser state, Worker state, backups, or workspace files.

Session 05 keeps all file, git, terminal, container, remote, Worker, and hosted executors unavailable. CLI diagnostics report posture only; they do not approve guarded actions, execute queue entries, start containers, run commands, call remote runners, or clean valid local state.

## Phase 06 Closeout

Phase 06 closes the CLI-owned diagnostics subset. `factionos status` and `factionos doctor` may report compact local server, hook, listener, spool, orchestration, and isolation posture, including unavailable executor counts and narrow recovery limits. They must not print raw prompts, command bodies, terminal output, file contents, tokens, broad paths, raw spool payloads, logs, backups, state file contents, Worker payloads, or trusted erasure claims.

`factionos doctor --recover-orchestration` remains limited to stale listener PID files and malformed spool JSON entries. It is not an executor, queue runner, Worker bridge, hosted diagnostic agent, or erasure tool.

## Phase 07 Hosted Diagnostics Boundary

Phase 07 Session 01 keeps CLI hosted-adjacent work diagnostic-only unless a later session scopes source changes. CLI output may report compact hosted readiness posture such as missing, present, disabled, unavailable, invalid, auth-required, timeout, or rate-limited. It must not print raw hosted config, provider keys, webhook URLs, bearer values, Cloudflare account ids, zone ids, tunnel tokens, prompts, command bodies, terminal output, file contents, exports, replay buffers, room payloads, logs, backups, state files, or raw spool data.

The CLI does not ship hosted identity, hosted storage, analytics, push, remote access, tunnel workflows, hosted diagnostic agents, production-hosted validation, trusted erasure, or release decommission behavior.

Phase 08 Session 01 keeps CLI-adjacent release claims gated in `.spec_system/archive/phases/phase_08/release_requirements_risk_baseline.md`. CLI status, doctor, uninstall, and orchestration recovery remain local diagnostics or settings operations only until later erasure sessions add dry-run, confirmation, audit, verification, redacted output, and tests.

## Phase 07 Hosted Operation Diagnostics Boundary

Phase 07 Session 06 adds loopback-only hosted operation diagnostics to `factionos status` and `factionos doctor`. The CLI fetches `/diagnostics/hosted-operations` only from local server URLs and fails closed for non-loopback targets. Output is compact: push disabled, remote access unavailable, tunnel unavailable, operator diagnostics posture, blocked payload label counts, and unsupported claim counts.

The CLI treats disabled push, unavailable remote access, unavailable tunnels, and inactive hosted diagnostic agents as successful local-first posture. It does not start tunnels, probe remote hosts, create push subscriptions, read VAPID keys, run remote executors, upload diagnostics, or perform erasure. Output must not print raw hosted config, subscriptions, VAPID private keys, Cloudflare account ids, zone ids, tunnel tokens, provider keys, webhook URLs, bearer values, prompts, command bodies, terminal output, file contents, paths, exports, replay buffers, room payloads, logs, backups, state files, or raw spool data.

Phase 07 Session 07 closeout validated this loopback diagnostics boundary. CLI runtime and diagnostics tests confirm loopback-only fetch, compaction, redaction of synthetic values, and fail-closed handling for non-loopback, malformed, auth, and timeout cases. `factionos status` and `doctor` report disabled/unavailable hosted posture as healthy local-first state; no hosted, remote, or erasure action is performed.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://faction-os.gitbook.io/faction-os-docs/apps/cli/readme_cli.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
