# Indexing: init, update, reindex

repowise init builds the intelligence layers from scratch, update keeps them current on each commit, and reindex rebuilds the vector store with no LLM.

## `repowise init`

Generate the wiki for a codebase. Runs full AST parsing, graph
analysis, git history indexing, dead-code detection, and page
generation.

`init` never requires an API key. With a provider resolvable it writes
the wiki with a model; without one it renders the whole wiki from the
parsed structure and exits 0. See
[Deterministic wiki](https://docs.repowise.dev/intelligence/deterministic-wiki). A keyless run
ends with one line naming what more is available: `repowise generate` writes
the subsystem pages with a model (a key, or `--provider ollama` for a local
model), and `repowise reindex` adds semantic search. `repowise status` prints
the same line.

A logged-in Claude Code, Codex or OpenCode is offered with its plan quota,
call count and time, Claude Code first. It is used only when you pick it or
pass `--provider`, never by default.

```bash
repowise init [PATH] [OPTIONS]
```

| Name | Type | Default | Description |
|---|---|---|---|
| `--provider` | string |  | LLM provider: anthropic, openai, openrouter, gemini, deepseek, kimi, ollama, litellm, codex_cli, copilot_cli, claude_cli, opencode, edenai, mock |
| `--model` | string |  | Model identifier override |
| `--embedder` | string |  | Embedder for RAG: gemini, openai, openrouter, ollama, edenai, mock. When unset, the first match in the embedder order (see Configuration) |
| `--mode` | string | `standard` | Pipeline depth: standard, or fast (Index only: graph and essential git, no documentation; upgrade later with update --full, no key needed) |
| `--skip-tests` | boolean | `false` | Skip test files during indexing |
| `--skip-infra` | boolean | `false` | Skip infrastructure files |
| `--dry-run` | boolean | `false` | Show the generation plan and cost estimate. Writes no wiki |
| `--yes / -y` | boolean | `false` | Skip the plan screen and every question, each answer at its default. A model writes the documentation only when a provider is configured; a logged-in Claude Code, Codex or OpenCode is used only with --provider. Points the global MCP entry here and prints the old and new target |
| `--resume` | boolean | `false` | Resume from the last checkpoint |
| `--force` | boolean | `false` | Regenerate all pages, ignoring existing |
| `--concurrency` | number | `10` | Max concurrent LLM calls |
| `--reasoning` | string | `auto` | Reasoning mode for supported providers: auto, off/none, minimal, low, medium, high, xhigh, max |
| `--test-run` | boolean | `false` | Write docs with the model for only the top 10 files by PageRank. Not with --no-prose or --mode fast |
| `--prose / --no-prose` | boolean | `prose if a key` | Documentation written by a model (--prose, needs a key) or built from code (--no-prose). Only the subsystem (concept) pages differ. --no-prose makes no model calls whatever keys are set, so decisions from PRs, commit history and code comments wait for repowise generate |
| `--index-only / --docs` | string |  | Deprecated hidden aliases. --index-only == --no-prose; --docs llm == --prose, --docs deterministic == --no-prose |
| `--exclude / -x` | string |  | Gitignore-style pattern to exclude (repeatable) |
| `--commit-limit` | number | `5000` | Newest commits to analyze per file and for co-change detection. Cap is 10000. Saved to config |
| `--follow-renames` | boolean | `false` | Use git log --follow to track renames (slower) |
| `--no-claude-md` | boolean | `false` | Skip generating .claude/CLAUDE.md |
| `--agents / --no-agents` | boolean |  | Generate or skip the managed AGENTS.md (default: config, else on) |
| `--codex / --no-codex` | boolean |  | Generate or skip the project-local Codex setup: .codex/config.toml, .codex/hooks.json and AGENTS.md |
| `--distill-hook / --no-distill-hook` | boolean |  | Let repowise's hooks compact what your agent sees (distilled command output, file skeletons, search digests, re-read pointers). One consent for all four. Default: ask when interactive, skip otherwise |
| `--hook / --no-hook` | boolean | `true` | Install the post-commit hook that runs repowise update after each commit. Interactive runs ask; --yes and non-interactive runs install it and print how to undo it (repowise hook uninstall) |
| `--editor-setup / --no-editor-setup` | boolean | `true` | Wire repowise into your editors: the Claude Code and Claude Desktop MCP entry and Claude Code hooks, plus .mcp.json, .claude/CLAUDE.md, .vscode/mcp.json and .vscode/extensions.json. --no-editor-setup touches only .repowise/. REPOWISE_SKIP_EDITOR_SETUP=1 does the same and wins |
| `--save-key / --no-save-key` | boolean | `true` | Save the provider API key this run authenticated with into .repowise/.env (gitignored, owner-only), so the MCP server can answer from a new shell. REPOWISE_NO_SAVE_KEY=1 does the same as --no-save-key |
| `--onboarding / --no-onboarding` | boolean | `true` | Generate the curated Onboarding collection (up to 8 overview pages) |
| `--max-file-pages` | number |  | Most file pages to emit, highest importance first. Omit to let the size policy decide; 0 means one page per eligible file. Saved to config.yaml |
| `--coverage-report` | string |  | Test-coverage report to ingest (repeatable). Common locations such as coverage/lcov.info are auto-discovered when omitted |
| `--wiki-style` | string | `comprehensive` | Documentation voice/density: comprehensive, caveman, reference, tutorial |
| `--language` | string | `en` | Output language for generated pages (e.g. en, zh, ru, hi). Code, paths and symbol names stay untranslated. Saved to config |
| `--include-submodules` | boolean | `false` | Include git submodule directories |
| `--all` | boolean | `false` | In a folder with several repos, index every detected repo without prompting. --yes and a piped stdin do the same and print which repos they took |
| `--repos` | string |  | In a folder with several repos, index only these, with no picker: --repos api,web. Each name is an alias, a directory name, or a path relative to the folder. In a new workspace the first one listed is primary. An unknown name stops the run and lists the available ones |
| `--no-workspace` | boolean | `false` | Force single-repo mode even when invoked from a workspace root |
| `--seed-from` | string |  | Seed the index from an existing base-branch checkout to skip unmodified files. Inside a linked git worktree this happens automatically |
| `--no-seed` | boolean | `false` | Disable worktree auto-seeding and run a full init |
| `--no-cost-tracking` | boolean | `false` | Skip DB-backed LLM cost tracking for this run |
| `--verbose / -v` | boolean | `false` | Show per-phase internals and debug logs |
| `--progress` | string | `rich` | rich: a live checklist in a terminal, one short line per step anywhere else. json: one JSON event per line on stdout, ending with a summary line |

```bash
repowise init                                     # current dir
repowise init /path/to/repo --provider anthropic
repowise init -x vendor/ -x 'src/generated/**'    # multiple excludes
repowise init --yes                               # non-interactive; no key needed
repowise init --yes --no-prose                    # guarantee no spend
repowise init --prose --provider anthropic        # write the subsystem pages as prose
repowise init --mode fast                         # very large repos: Index only
repowise init --test-run                          # 10 files, smoke test
repowise init . --yes --repos api,web             # workspace, two of its repos
repowise init --yes --no-prose --progress json    # agents and scripts
```

### The plan screen

`repowise init` on a terminal, with none of `--provider`, `--no-prose`,
`--mode fast`, `--resume` or `--yes`, opens one screen: the repo scan, an ETA,
the plan, and an opt-in model line with what a model adds and costs. Type a
key and press Enter.

| Key | Action |
|-----|--------|
| Enter | Start the free run: documentation built from code, no key, no model calls |
| `m` | Pick a model: a detected API key or a logged-in agent CLI |
| `e` | Edit the plan: advanced options, agents, the post-commit hook, and adding machine-specific files to `.git/info/exclude` (off by default) |
| `s` | When a global MCP entry points at another repo, keep it there; this repo still connects through `.mcp.json` |
| `r` | In a folder of repos, choose the repos and the primary |
| `q` | Quit. A `.repowise/` this run created is removed again |

While it runs, `init` shows a checklist of every step with counts, time and
what comes next. If the screen reads EOF (an agent piping stdin), `init`
prints a notice and continues with defaults.

**Cost gate.** Before any tokens are spent, `init` shows the estimate and
asks. With no terminal it declines, keeps the index, builds the documentation
from code, and exits `2` naming `--yes`. The default answer is Yes up to $25
and No above that.

### Exit codes

| Code | Meaning |
|------|---------|
| `0` | Ready |
| `2` | Finished with gaps. Everything is saved; the last line names what is missing and the command that adds it. A usage error also exits `2`, before anything runs |
| `130` | Interrupted. Run `repowise init --resume` |
| other | Failed. Run `repowise doctor` |

A run whose page vectors fail to write (a real embedder, a broken LanceDB
install) keeps its pages and full-text index, exits `2`, and names the fix:
reinstall, then `repowise reindex`. A workspace `init` exits `2` after saving
every repo and names the repos with gaps. `repowise update` exits `1` on a
failed embed.

### Driving init from an agent or script

`repowise init --yes --no-prose --progress json` writes only JSON lines to
stdout; human text goes to stderr. Every line has `v` (schema version, `1`)
and `event`:

| Event | Fields |
|-------|--------|
| `stage` | A top-level step starting |
| `phase` | `state` (`start`, `done` or `failed`), `completed`, `total`, `unit`, `elapsed_s` |
| `warning` | Something the run worked around |
| `summary` | The last line: `status`, `mode`, `restart_required`, `spend`, `warnings`, `files_written`, `next` |

The summary's `status` is `ready`, `degraded`, `interrupted` or `failed`,
matching exit `0`, `2`, `130` or any other code. `mode` carries `key`, `label`
and `run_mode`; `spend` carries `tokens` and `usd`; `restart_required` means
the editor needs a restart or `/mcp` to load the tools; `next` lists commands,
`repowise serve` first.

> **Note**
>
> **The canonical non-interactive command is `repowise init --yes --no-prose`.**
> It never prompts and makes no model calls, whatever keys are set. This is what
> agents and CI should run.

### Modes

`init`, `status` and `update` name an index by its mode.

| Mode | Reached by | Upgrade with |
|------|-----------|--------------|
| Index only | `init --mode fast` | `repowise update --full` (no key needed) |
| Built from code | `init --no-prose`, or no key | `repowise generate` (needs a model) |
| `Written by <model>` | a model run, or an upgrade | |

Semantic search sits on top of either documentation mode and is added with
`repowise reindex --embedder <name>`. Every upgrade reuses the existing index
and shows a cost estimate before any model call.

### Provider, model and base URL

Every command that calls a model, `repowise serve` chat and jobs, and the MCP
server resolve the provider, model and base URL in one order. The first match
wins:

1. `--provider` / `--model`, or a per-request choice in the web UI
2. `provider`, `model` and `<provider>: {base_url: ...}` in `.repowise/config.yaml`
3. the global default saved from the web UI settings
4. `REPOWISE_PROVIDER` / `REPOWISE_MODEL` and the provider's `*_BASE_URL` variable
5. whichever provider API key is set

Choosing a model or base URL for a repo in the web UI writes that repo's
`config.yaml`, so the CLI picks it up. See
[Environment variables](https://docs.repowise.dev/installation/env-vars#provider-model-and-base-url-order).

> **Note**
>
> The graph, git, dead-code, and code-health layers build in minutes with
> **zero LLM calls**, and so does the wiki when you run keyless. The
> one-time cost is the model-written documentation layer, which scales with
> repo size and can run in the background. After that, each commit-triggered
> `update` takes under 30 seconds. Interrupted a run? Re-run with `--resume`
> to pick up from the last checkpoint.

---

## `repowise update`

Incremental update for files changed since the last sync. Detects
changed files via `git diff`, re-parses them, rebuilds the affected
slice of the dependency graph, and regenerates the affected pages.

```bash
repowise update [PATH] [OPTIONS]
```

| Name | Type | Default | Description |
|---|---|---|---|
| `--provider` | string |  | LLM provider name |
| `--model` | string |  | Model identifier override |
| `--since` | string |  | Base git ref to diff from (overrides stored state) |
| `--concurrency` | number | `5` | Max concurrent LLM calls |
| `--reasoning` | string |  | Reasoning mode for supported providers: auto, off/none, minimal, low, medium, high, xhigh, max |
| `--cascade-budget` | number |  | Max pages to regenerate (auto-scaled if unset) |
| `--dry-run` | boolean | `false` | Show affected pages without regenerating |
| `--workspace / -w` | boolean | `false` | Update every stale repo in the workspace |
| `--repo` | string |  | Update only this repo alias within the workspace |
| `--index-only` | boolean | `false` | Refresh the index only, skip doc regeneration for this run. In workspace mode, forces every stale repo to index-only |
| `--working-tree` | boolean | `false` | Also index uncommitted work (staged, unstaged and untracked files) on top of the commits since the last sync. In a workspace, a repo with uncommitted changes counts as stale |
| `--docs / --no-docs` | boolean |  | Regenerate wiki pages for changed files, or skip doc regeneration entirely |
| `--full` | boolean | `false` | Take an Index only (--mode fast) repo to a full index: backfill the full git history and build the documentation. No key needed: with no model configured the documentation is built from code; with one, the model writes it after a cost preview. One repo at a time (in a workspace, pass --repo) |
| `--no-workspace` | boolean | `false` | Force single-repo mode (handy when running from a workspace root) |
| `--agents / --no-agents` | boolean |  | Regenerate or skip the managed AGENTS.md (default: config, else on) |
| `--no-cost-tracking` | boolean | `false` | Skip DB-backed LLM cost tracking for this run |
| `--verbose / -v` | boolean | `false` | Show the full changed-file list and per-phase internals |
| `--progress` | string | `rich` | Progress output: rich, or json for one newline-delimited event per line on stdout |

```bash
repowise update                          # incremental from current HEAD
repowise update --since main             # diff against main
repowise update --workspace              # all stale repos
repowise update --repo backend           # one workspace repo
repowise update --dry-run                # see what would regenerate
repowise update --working-tree           # bring uncommitted edits into the index
repowise update --full                   # Index only to a full index, no key
repowise update --full --provider anthropic   # straight to Written by <model>
```

A typical single-commit update touches 3 to 10 pages in under 30 seconds.
A working-tree-only update skips the history and analysis phases: a 2-file
edit on a small repository refreshes in about 4.5 s. MCP responses mark which
served files carry uncommitted edits.

**History depth.** Git analysis reads the newest 5,000 commits by default, so
churn, hotspots, co-change, Change Records and suspects cover a real span of
history on active repositories. An index whose `config.yaml` records a lower
`commit_limit` keeps it, and `update` names that value once; set
`commit_limit: 5000` there to read the wider window. The first update after
raising it re-reads history once, with no model calls.

`--full` with a model configured is also the wholesale way to write the
subsystem pages across documentation built from code. For a slice at a time, use
[`repowise generate`](https://docs.repowise.dev/cli/indexing#repowise-generate) below.

> **Note**
>
> **After a package upgrade**, `repowise update` picks up the new version against
> your existing index (no reindex in the normal case) and shows a short
> "what's new" panel for the versions you crossed. It also prints a one-line,
> non-blocking notice when a newer release is available. See
> [Upgrading](https://docs.repowise.dev/upgrading) for the full flow.

---

## `repowise generate`

Write the subsystem (concept) pages with a model, on demand. This is the
upgrade path for a repo indexed without a key: it fills the subsystem stubs
with model prose, one page, one directory, or the whole concept layer at a
time, each behind a cost estimate, and rewrites already-written pages. It
writes only the model-written pages (the concept tree and the overview);
naming a structural page such as a file page is an error, since those refresh
on `repowise update`.

It reuses the persisted index. The graph and git metadata are rehydrated
from SQL, so only the per-file parse and the generation for the pages you
selected run. A provider is required here, and a missing one is an
actionable error naming the key-setup path.

```bash
repowise generate [PATH] [OPTIONS]
```

| Name | Type | Default | Description |
|---|---|---|---|
| `--unwritten` | boolean | `false` | Every subsystem page still on a stub. The default for a non-interactive run: 'finish writing the wiki' |
| `--all` | boolean | `false` | Every subsystem page, stub or already written. Rewrites the prose |
| `--stale` | boolean | `false` | Every subsystem page marked stale (its code changed since it was written) |
| `--path` | string |  | Subsystem pages under a path prefix or glob, e.g. src/api (repeatable) |
| `--page` | string |  | One explicit subsystem page id, e.g. module_page:src/api (repeatable). A structural page id is an error |
| `--cascade` | string | `dependents` | What happens to pages that summarize a regenerated one: none, dependents, or full |

```bash
repowise generate                     # every unwritten subsystem page, one cost estimate
repowise generate --path src/api      # just the subsystem pages under one directory
repowise generate --all               # rewrite the prose on every subsystem page
```

Selection names which subsystem pages to write, combined as a union:
`--unwritten` / `--all` / `--stale` / `--path` / `--page`.

Run `repowise generate` with no selection flag on a terminal and it prints
the wiki's state and writes every unwritten subsystem page behind a single
cost estimate, asking about cascade only when it changes which pages get
written. Piped runs, `--yes`, and flagged runs stay non-interactive with the
same `--unwritten` default.

**Cascade.** Rewriting a subsystem page makes the pages that summarize it
drift: its layer page, plus the repo overview, architecture and onboarding
pages. `--cascade none` marks them stale, `dependents` (the default) also
regenerates the overview and layer pages that summarize it, and `full` leaves
nothing stale. The cost estimate includes the cascade fallout, so it does not
under-quote.

**Decisions a keyless index skipped.** An index built without a model cannot
read decisions from PRs, git history or code comments. The first `generate`
(or `update --full`) with a model runs those lanes too and prices them on
their own line of the estimate. `repowise status` shows a Decisions row while
they are pending.

---

## `repowise reindex`

Rebuild the vector search index from existing wiki pages. No LLM
calls, only embedding API calls. Fast and cheap. Use when you
switch embedders, suspect FTS/vector drift, or want semantic search on an
index built without an embedder. Every run names the embedder it uses.

```bash
repowise reindex [PATH] [OPTIONS]
```

| Name | Type | Default | Description |
|---|---|---|---|
| `--embedder` | string | `auto` | Embedder: gemini, openai, openrouter, ollama, edenai, mock, auto (keep the repo's embedder, or detect one from env keys when it has none or only mock) |
| `--batch-size` | number | `32` | Pages per embedding batch |

```bash
repowise reindex
repowise reindex --embedder openai --batch-size 50
```

---

## `repowise restyle`

Switch a repo's wiki documentation style and regenerate every LLM page in
the new voice. Reuses the persisted graph and git metadata (no re-blame);
the only unavoidable rework is re-parsing files for ASTs, the same cost as
`repowise update --full`. This is an LLM-generation command (a cost),
unlike `init`/`update`/`reindex` above.

```bash
repowise restyle [STYLE] [PATH] [OPTIONS]
```

| Name | Type | Default | Description |
|---|---|---|---|
| `--provider` | string |  | LLM provider name |
| `--model` | string |  | Model identifier override |
| `--concurrency` | number | `12` | Max concurrent LLM calls |
| `--reasoning` | string |  | Reasoning mode override |
| `--verbose / -v` | boolean | `false` | Show debug logs from the pipeline |
| `--yes / -y` | boolean | `false` | Skip the confirmation prompt |

```bash
repowise restyle                        # show current style + available choices
repowise restyle caveman                # switch and regenerate every page
repowise restyle reference --yes --provider anthropic
```

STYLE is one of `comprehensive`, `caveman`, `reference`, `tutorial`. With no
STYLE, prints the current style and exits.

> **Note**
>
> Because the style folds into each page's `source_hash`, the regeneration is
> unconditional: every LLM-written page is rewritten, not just stale ones. A
> repo indexed keyless (no written prose) can still restyle: it writes the
> subsystem pages for the first time, in the chosen style.

---

## `repowise wiki-styles`

List the available wiki documentation styles, and which one the current
repo uses.

```bash
repowise wiki-styles [PATH]
```

```bash
repowise wiki-styles
```
