# @best-agent/cli

Terminal entrypoint for `best-agent`.

## Commands

- `best-agent server`
- `best-agent serve`
- `best-agent daemon`
- `best-agent acp`
- `best-agent run`
- `best-agent chat`

## Features

- loads `.env` from `--cwd` or the current working directory
- starts `app-server` or `acp-server`
- starts a REST + SSE server over the shared runtime
- starts a long-lived local daemon over a native socket or named pipe
- runs direct one-shot prompts through the daemon-backed app-server path with foreground approval prompts
- runs TTY chat through the goatagent `DimSdk` TUI backed by the `best-agent` runtime
- runs the non-TTY interactive chat loop through `sdk-ts -> daemon client -> local daemon -> runtime`
- exposes project-memory, plan mode, diagnostics, compaction, research, fork/resume, and thread lifecycle commands

## Key Flags

- `--cwd <path>`
- `--storage-root <path>`
- `--extensions-root <path>`
- `--agent <name>`
- `--plan`
- `--resume <threadId>`
- `--latest`
- `--provider <openai|anthropic|google>`
- `--model <id>`
- `--base-url <url>`
- `--compatibility <auto|native|compatible>`
- `--approval-timeout-ms <ms>`
- `--guardian-enabled <true|false>`
- `--guardian-model <id>`
- `--guardian-threshold <0-100>`
- `--guardian-timeout-ms <ms>`

## Examples

Start the server:

```bash
best-agent server --cwd /path/to/repo
```

Start the local daemon:

```bash
best-agent daemon --cwd /path/to/repo
```

Start the HTTP+SSE server:

```bash
best-agent serve --host 127.0.0.1 --port 3000 --cwd /path/to/repo
```

HTTP auth:

- loopback hosts (`127.0.0.1`, `::1`, `localhost`) keep the existing no-auth default
- non-loopback hosts require `BEST_AGENT_HTTP_TOKEN`
- when `BEST_AGENT_HTTP_TOKEN` is set, JSON routes require `Authorization: Bearer <token>`
- SSE also accepts `?access_token=<token>`

Run a single prompt:

```bash
best-agent run --agent verify 'tool:read-file {"path":"package.json"}'
```

Start chat with a provider:

```bash
OPENAI_API_KEY=your_key \
OPENAI_MODEL=gpt-5-mini \
best-agent chat --cwd /path/to/repo
```

Start the migrated local CLI from the repo root:

```bash
pnpm chat -- --cwd /path/to/repo
```

Start a planning session:

```bash
best-agent chat --plan
```

Run the TTY smoke check:

```bash
pnpm smoke:cli-tui
```

## Web Search Configuration

`web-search` is exposed by capability, not just by the presence of one vendor key.

- if the active provider supports native web search, no external search key is required
- if the active provider does not support native web search, the CLI can build an external search adapter from the persisted DimSdk tool settings
- if neither capability exists, the runtime hides `web-search` from model-visible tools for that turn

The CLI persists external search settings in:

- `DIMCODE_HOME/tools.json` when `DIMCODE_HOME` is set
- otherwise `~/.dimcode/tools.json`

Relevant fields:

```json
{
  "version": 1,
  "updatedAt": 0,
  "settings": {
    "websearch": {
      "apiKey": "serper-key",
      "apiEndpoint": "https://google.serper.dev/search?format=json",
      "numResults": 10
    }
  }
}
```

You can provide the key in either of these ways:

- before starting chat, by writing the `tools.json` values above
- during an existing chat, by updating the same search settings through the DimSdk settings flow

Dynamic updates apply on the next turn:

- if the conversation is already open and the user adds the missing search key, the next user message re-evaluates capability
- a new thread is not required just to pick up the new key
- endpoint and result-count changes follow the same next-turn behavior in the current CLI implementation

For the deeper runtime contract, see `/Users/Simon/Github/best-agent/docs/architecture/web-search-capability-and-configuration.md`.

## Chat Commands

- `/threads`, `/resume`, `/new`
- `/archive`, `/unarchive`, `/delete`
- `/memory show|set|add|edit|clear`
- `/agent`, `/agents`
- `/plan on|off|status|show|todos|approve|reject|export`
- `/tools`, `/skills`, `/use-skill`, `/drop-skill`
- `/diagnostics`, `/compact`
- `/research`, `/evidence`, `/handoff`
- `/fork`, `/forks`

`/memory show` displays both user-authored manual memory and auto-extracted workspace memory. `/memory edit`, `/memory set`, and `/memory add` edit manual memory only. `/memory clear` clears both manual and auto memory.

## Does Not Own

- protocol definitions
- runtime policy
- tool implementations

The CLI stays intentionally thin. Runtime behavior belongs in `packages/engine`.

## Migration Notes

- `best-agent run` now goes through `sdk-ts -> daemon client -> local daemon -> runtime` and no longer creates an in-process runtime for one-shot execution.
- `best-agent serve` now exposes the same runtime through a thin HTTP+SSE surface for local integrations and e2e coverage.
- `best-agent chat` now loads a bundled `DimSdk` runtime from `dist/dimsdk-tui.bundle.js`.
- The bundle resolves `@simon_he/vue-tui` from the installed package in `node_modules`, so `best-agent chat` keeps the real goatagent shell and swaps only the runtime/backend bridge.
- Provider/model changes now sync back into the `best-agent` runtime and persist through `cli-state.json`.
- Session rename and `metadata.ui` persistence now round-trip through runtime/server/sdk/CLI bridge and survive restart.
- Existing non-TTY CLI e2e remains the baseline acceptance path, `apps/cli/test/goatchain-bridge.test.ts` covers the runtime bridge, the DimSdk compatibility tests live in `apps/cli/test`, and `pnpm smoke:cli-tui` is the manual TTY acceptance path.

## Known Gaps

- The bundled TUI still depends on external package compatibility, but [package.json](/Users/Simon/Github/best-agent/package.json) no longer hardcodes a machine-specific `link:` path for `@simon_he/vue-tui`.
- We now cover provider persistence, session metadata hydration, and session list view-model compatibility in `apps/cli/test`, but we have not yet ported the heaviest full-terminal DimSdk interaction tests such as transcript rendering order, tool call expansion/collapse, and approval overlays.

## Follow-up Plan

### 1. Keep External TUI Dependency Pinned

- Keep `@simon_he/vue-tui` pinned to the exact published version used by the bundle.
- If the package API changes, update the bundle and test suite together instead of relinking a sibling repo path.

Acceptance:
- `pnpm build` and `pnpm chat -- --cwd ...` work on a clean machine without a sibling `goatagent` checkout.

### 2. Port Heavier DimSdk Terminal Tests

- Continue with bridge-compatible tests that exercise transcript ordering, tool call rendering, and approval overlays.
- Prefer real shell tests when they are stable; otherwise keep the current compatibility-layer tests that directly target DimSdk persistence and view-model logic.

Acceptance:
- The acceptance baseline remains: `pnpm test` and `pnpm smoke:cli-tui` both green.
