AGENTS.md@packages/kb-plugin/src/client · git:20260824.680846f · 2026-08-24 · sha256 e99d157e637de3b6

AGENTS.md@packages/kb-plugin/src/client git:20260824.680846fA

Immutable. This exact content is served forever at /api/v1/blob/e99d157e637de3b6.

# DOX — packages/kb-plugin/src/client

Files in this directory. One row per source file. See change: add-kb-folder-slot.

| File | Purpose |
|------|---------|
| `FolderKbSection.tsx` | `sidebar-folder-section` claim. `deriveKbRowState` ordered five-state: error→indexing→not-indexed→stale→populated (error wins over chunks:0). `clientError = reindexError ?? error` forces `error` state (trigger reject OR poll outage) over the derived state; `indexing` spinner survives transient poll blips. Count tooltip `F files · N chunks`. `→` opens kb settings. Pill is STATE-ONLY: `folder-kb-reindex` / `-index-now` / `-retry` and the indexing spinner GONE. ONE `useFolderMenuItem` (`id:"kb-reindex"`, `group:"maintenance"`, `mdiDatabaseRefreshOutline` so it never collides with the menu's plain `mdiRefresh`) varies by state: Retry (error), indexing… (indexing), Index now (not-indexed), Reindex now (stale, populated or loading); `badge` = `N stale` when stale; `disabled = busy`. Scope is `null` when `placement === "card"` (worktree card has no folder menu) — registers nothing. Optimistic `pending` from `useKbStats` renders the `indexing` branch on activation (error still outranks it); `busy` (pending OR polled indexing) covers the whole optimistic window (no double-submit). Inline `folder-kb-stale` marker STAYS in the pill (state, not a control) — badge on the menu item is the action's context, not duplication. See change: add-kb-folder-slot; fix-kb-index-feedback; add-kb-index-optimistic-pending; move-slot-actions-to-menu. |
| `index.tsx` | Client barrel. Exports `FolderKbSection`, `KbSettingsClaim` for plugin-registry. See change: add-kb-folder-slot. |
| `kb-api.ts` | REST client. `fetchKbStats`/`reindexKb`/`fetchKbConfig`/`saveKbConfig`. base64url folder-path codec `encodeFolderPath`/`decodeFolderPath`, `kbSettingsUrl`. Content-type guard: non-JSON body → typed error not parse crash. See change: add-kb-folder-slot. |
| `KbSettingsClaim.tsx` | `shell-overlay-route` claim `/folder/:encodedCwd/kb`. Decodes cwd param, renders `KbSettingsPanel`. See change: add-kb-folder-slot. |
| `KbSettingsPanel.tsx` | Per-folder KB path editor. Edits sources[] (add/remove/reorder priority)/include/exclude/dbPath only; other config round-tripped. Shows origin + count. `Save + Reindex`. Worktree bootstrap: `Create project config` + `Copy from parent repo` (`parentRepoOf` derives parent from `.worktrees/` path). See change: add-kb-folder-slot. |
| `useKbConfig.ts` | `useKbConfig(cwd)`. GET config, `save(patch)` PUT. Round-trips full config. See change: add-kb-folder-slot. |
| `useKbStats.ts` | `useKbStats(cwd)`. Fetch `/api/kb/stats`, `reindex()` POST (202→`refetch()` engages poll). Polls every 1000ms while `indexing`, stops on settle. Two error channels: `reindexError` (trigger POST rejected, no job) vs `error` (poll outage, surfaced only after `MAX_POLL_MISSES`=3 consecutive misses — a lone blip keeps the spinner, never `clearPoll`s). Optimistic `pending` boolean: set `true` synchronously in `reindex()` (spinner on click), cleared ONLY on POST reject / a `/stats` poll seeing `indexing:true` / a `REINDEX_GUARD_MS` timeout guard (`refetch()`s) — never on the bare `202`, so no spinner flicker/wedge. See change: add-kb-folder-slot; fix-kb-index-feedback; add-kb-index-optimistic-pending. |