Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .agents/lessons.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,3 +25,8 @@ Persistent log of corrections and insights from past sessions. Read when relevan
- **Never fabricate quantitative explanations to rationalize surprising data** — when a CI / perf / benchmark number is unexpected (e.g. went up after a "performance" PR), the failure mode is to invent a plausible-sounding cause without verification ("+8 doc files were added since the baseline"). This is intellectual dishonesty that compounds: the fabricated cause gets baked into PR bodies, commit messages, follow-up reasoning, and other agents inherit it as fact. **Pattern:** when a number surprises you, say "I don't know yet" and either (a) instrument / re-run to find the real cause, or (b) accept the unknown and surface it explicitly to the user. Verifiable claim formats: `git diff --name-status A..B | grep '^A'` for file-add counts, `gh run view <id> --log` for CI numbers, repeated CI runs on the same commit for variance characterisation. **Never** invent a numeric explanation that "sounds right". Hit on PR #104 (perf-baseline refresh) — claimed "8 new doc files indexed since cc8daed" explaining a +71ms CI regression; actual delta was 1 file. User caught it; PR was closed.
- **PR titles: no `SCHEMA N` / `SCHEMA_VERSION` suffix** — schema bumps belong in the PR body, changeset, and `db.ts`; putting `(SCHEMA 37)` in the title adds noise and duplicates what reviewers see in the diff. Title = what shipped (`feat(index): callback dispatch synthesis`), not the integer.
- **Perf-baseline flakes are often GHA runner tiers, not code regressions** — `ubuntu-latest` jobs on the same commit can land on fast (~630 ms total) or slow (~1117 ms) runners; cross-job spread dwarfs the +25% gate. **Pattern:** compare pass vs fail CI logs on the same SHA before re-baselining or blaming a PR; capture baseline medians from slow-tier CI logs, use `CODEMAP_PERF_RUNS=5` in CI, and honour `CODEMAP_PERF_REGRESSION_PCT` env during compare (not just `--update`). Hit on main CI May 2026 — #136 merge blocked by `index_create_ms` +31.7% while `total_ms` was only +15%.
- **Workspaces need `"."` listed explicitly** — `workspaces: ["apps/*"]` alone drops the root package from changesets: Release fails with "changeset … which is not in the workspace". Always `workspaces: [".", "apps/*"]` from day one when adding `apps/docs`.
- **Blume `audit` skips `basePath`-relative paths** — with `deployment.base: "/codemap"`, the canonical-bad-target / non-canonical-in-sitemap / indexable-page-not-in-sitemap checks fire on paths that are correct under the subpath. Skip them: `blume audit --fail-on error --skip canonical_bad_target,non_canonical_in_sitemap,indexable_page_not_in_sitemap`.
- **Changelog → maintainer `docs/` links** — old release notes link to `../docs/roadmap.md` / plans. Do **not** stub those under `apps/docs/content/docs/` (pollutes the site). `apps/docs/scripts/validate.ts` filters `BLUME_BROKEN_LINK` on `changelog:*` only; audit still skips `BLUME_AUDIT_LINK_TO_BROKEN` globally.
- **TypeDoc needs classic TypeScript 5–6** — `typedoc@0.28` peers `typescript@5 || 6`; pinning root `typescript@7` breaks `docs:api` (`SyntaxKind` undefined). Keep `typescript@6.0.3` for TypeDoc; typecheck stays on `tsgo` (`@typescript/native-preview`).
- **Don't override root `zod` onto Blume with `"zod": "$zod"`** — forcing the workspace onto zod 4 breaks Blume's frontmatter schema (`config.frontmatter.extend` null). Pin `js-yaml` to `4.3.0` (not `>=4.1.2`) so Astro/Blume don't pull js-yaml v5 ESM breakage. Drop the `$zod` override when adding `apps/docs`; keep root `dependencies.zod` at 4.x for codemap itself.
14 changes: 14 additions & 0 deletions .agents/rules/docs-voice-priming.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
description: Docs voice primer — read docs-voice skill before authoring apps/docs prose.
globs:
- "apps/docs/**"
alwaysApply: false
---

# Docs voice (priming)

Before authoring or editing public docs prose, **read the [`docs-voice` skill](../skills/docs-voice/SKILL.md)**.

Voice, peer framing (code-index / agent-context tools only — never store/adapter middlewares), card/header grammar, and anti-pitch live in the skill — not duplicated here.

Product north-star: [`product-tenets`](../skills/product-tenets/SKILL.md).
17 changes: 17 additions & 0 deletions .agents/skills/docs-governance/LIFECYCLE.md
Original file line number Diff line number Diff line change
Expand Up @@ -225,3 +225,20 @@ Shipped agent templates under `templates/agent-content/**` follow the same consu
| **Maintainer-only** | Never leak into served shards | Module paths under `src/`, CI wiring, dual-file sync, dogfood paths |

When lifting durable policy from a closed plan or audit into agent-content, verify parity across CLI help, MCP tool descriptions, served shards, root README, and changeset bodies — not just one surface.

---

## README surfaces (public site vs npm landing vs maintainer docs)

Codemap has three reading surfaces with distinct jobs; never blur them.

| Surface | Canonical home | Job | Deploy |
| ---------------------------------- | ------------------------------------ | -------------------------------------------------------------------------------------- | -------------------------------------------------- |
| **Public docs site** | `https://stainless-code.com/codemap` | Canonical user docs — install, guides, concepts, recipes, reference, library API | FTP `/codemap` on merge of a **`docs`**-labeled PR |
| **Root `README.md`** (npm landing) | repo root | npm/repo landing digest only — install + one-query hook + pointer to the site | ships in the npm package |
| **Maintainer `docs/`** | `docs/` at repo root (Tier B) | Governance, architecture internals, plans, audits, research — never leaked to the site | tracked in-repo; not deployed |

- **Site is canonical for user docs.** Root `README.md` summarizes and links; it does not restate guide/reference prose ([`docs/README.md` Rule 1](../../../docs/README.md)).
- **`docs` label deploys.** A PR merged with the **`docs`** label triggers `deploy-docs.yml` → FTP to `/codemap`. Releases and `workflow_dispatch` also deploy.
- **Maintainer `docs/` stays separate.** Curated lifts to the site only; never dump `docs/*.md` wholesale into `apps/docs/` ([`docs/README.md` Rule 1](../../../docs/README.md)).
- **Docs-only changeset = `patch`** (pre-1.0; schema-breaking is the only `minor` trigger — see [`.agents/lessons.md`](../../lessons.md)).
115 changes: 115 additions & 0 deletions .agents/skills/docs-voice/SKILL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
---
name: docs-voice
description: Voice, tone, and format for the public Codemap docs (`apps/docs`, built with Blume). Use when authoring or editing apps/docs prose — landing, guides, concepts, recipes, reference, generated API — or deciding headline grammar, benefit framing, peer framing, or anti-pitch wording.
---

# Docs voice — Codemap docs (`apps/docs`, built with Blume)

Keep landing, guides, concepts, recipes, reference, and generated API reading like one voice.

## Voice in one line

Senior-dev to senior-dev: concrete, SQL-literate, dry, honest about scope. No
hype. The differentiators are radical honesty (say what's planned / diverges /
was rejected) and the "when **not** to use it" anti-pitch — keep both.

## Do

- **Lead with the pain, then the mechanism.** "Agents burn tokens scanning files
to find one symbol…" → then "`codemap query --json` returns the row in one SQL
round-trip."
- **Concrete before abstract.** Name `codemap query` / `--recipe` / `createCodemap`
/ `defineConfig` before the coinage "predicate-as-API" or "structural index."
- **CLI-first AND programmatic.** Show the CLI shape first; pair with the library
shape (`createCodemap`, `defineConfig`, adapters) when the page is API-shaped.
The published package entry is the SSOT for generated `/reference/api` (TypeDoc).
- **SQL is the API.** When a page answers a structural question, show the SQL or
the `--recipe` — not a paragraph of prose pretending to be the answer. Recipes
are named SQL patterns; cite the recipe id.
- **Section headers by page type.** Marketing = period-terminated benefit
sentence ("Query your codebase."); guides = action verb ("Find a symbol with
one query"); reference = precise noun; concepts = model noun + consequence.
- **Card titles = the outcome; card bodies = the API / SQL.**
- **One idea per sentence in leads.** Short claim first, then expand.
- **State experimental / pre-1.0 status once per surface, one wording** (see
Canonical patterns).
- **Sidebar icons: all-or-none per sibling list.** Blume does not reserve an
icon column — sparse `sidebar.icon` jaggeds labels. Guides, Concepts,
Recipes, Reference leaves: none unless every peer has a natural glyph.
Section `meta.ts` icons and tab icons stay.
- **Peer framing is structural, not brand-vs-brand.** When comparing, contrast
axes (query API, semantic layer, extraction depth, CI substrate) — see
[`docs/why-codemap.md`](../../../docs/why-codemap.md) § Codemap vs alternatives.
Do not clone peer design in prose; reach for the underlying spec
([`plan-pr-inspiration-discipline`](../../rules/plan-pr-inspiration-discipline.md)).

## Don't

- Don't open a page with a 60+ word sentence.
- Don't restate the frontmatter `description` in the first body sentence — the
docs site renders `description` as the page subtitle, so an echoing opener
duplicates content. Open with a concrete scenario/pain instead.
- Don't title cards with bare feature nouns ("Fan-in") when the outcome is the
hook ("Find what depends on a file in one query").
- Don't manufacture social proof, download counts, "trusted by", or maturity
adjectives ("production-grade", "battle-tested", "world-class") at pre-1.0 —
live queries, source, the changelog, and the benchmark are the proof.
- Don't claim Codemap owns semantic search, refactoring, or editor ergonomics —
peers (LSP, embeddings, verdict linters) own those slots; Codemap owns
structural facts + predicate-as-API. Say when to reach for something else.
- Don't hype ("blazing-fast", "revolutionary", "AI-powered"). Indexed queries
are sub-ms; let the number and the benchmark carry it.
- Don't treat store/adapter middlewares as competitors — different problem
space. Codemap's peers are code-index / agent-context tools; the contrast is
structural-SQL + recipes vs pre-baked graph verbs / embeddings.
- Don't invent Lucide icons for prose nav leaves to "fill out" a section —
strip to none instead of decorating half the list.
- Don't paste maintainer internals (`src/` module names, CI wiring, dual-file
sync, dogfood paths) into public pages — see
[`consumer-surfaces`](../../rules/consumer-surfaces.md).

## Canonical patterns (use verbatim)

- **Experimental disclaimer** (banner / pill / callout / stability page):
"Experimental — the API may change between minor releases. Pin your version."
- **Pre-1.0 semver:** breaking changes are expected and ship in **minor
releases** (`0.x` → `0.y`), **not majors**. Schema-breaking changes that force
a `.codemap/index.db` rebuild are the trigger for `minor`; everything else
(additive CLI, public types, docs) is `patch`.
- **Brand one-liner** (memorable beat, not hype): "Query your codebase."
- **Category label** (what it is — pair with the brand beat, then the
mechanism): "local codebase intelligence" / "codebase intelligence tool".
Same breath as SQLite / SQL / recipes — never as a standalone slogan.
- **Public site URL:** `https://stainless-code.com/codemap` (canonical user
docs). Root `README.md` is the npm landing digest; maintainer `docs/` is
separate.
- **Peer set:** other codebase intelligence / code-index / agent-context tools
— static-analysis linters (knip / ts-prune / jscpd / ESLint), Aider RepoMap,
LSP servers, and the SQLite-backed cohort (srclight, ctxpp, KotaDB, …). Not
store/adapter middlewares.
- **Anti-pitch source of truth:** [`docs/why-codemap.md`](../../../docs/why-codemap.md)
§ When to reach for something else — link, don't restate.

## Product tenets

Decisions and messaging should align with [`product-tenets`](../product-tenets/SKILL.md).

## Verify

`content/**` MDX is excluded from oxfmt (nested `.oxfmtrc.json` ignores
`content/**` — the `:::` directive collapse bug); `.astro` is not oxfmt-managed.
Build green before commit ([`verify-after-each-step`](../../rules/verify-after-each-step.md)):

```bash
bun run docs:validate -- --strict && bun run docs:check -- --isolated && bun run docs:build && bun run docs:audit
```

Scheduled drift sync: [`update-docs`](../update-docs/SKILL.md).

## Reference

- Priming: [`docs-voice-priming`](../../rules/docs-voice-priming.md)
- Tenets: [`product-tenets`](../product-tenets/SKILL.md)
- Lifecycle / README surfaces: [`docs-governance`](../docs-governance/SKILL.md)
- Anti-pitch + peer framing: [`docs/why-codemap.md`](../../../docs/why-codemap.md)
- Consumer-vs-maintainer split: [`consumer-surfaces`](../../rules/consumer-surfaces.md)
6 changes: 6 additions & 0 deletions .agents/skills/harden-pr/LEDGER.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,12 @@ By-design or false-positive findings — do not re-raise.

- **[correctness]** `src/application/impact-engine.ts:147` — explicit inPath on single-definition symbol enables first-hop scopeFiles: by-design — matches show `--in` disambiguation (plan P2.1).
- **[correctness]** `src/application/impact-engine.ts:162` — per-file walk LIMIT before global dedup: by-design v1 — plan architecture per-defining-file walks; global limit still applies at slice.
- **[docs]** `apps/docs/pages/_home/FinalCta.astro` — `pnx` typo: by-design — [`pnx`](https://pnpm.io/cli/pnx) is pnpm's `dlx` alias (user-locked homepage wording).
- **[surfaces]** homepage InstallBox bunx-only vs getting-started multi-PM tabs: by-design — hero chip stays single-command; guides own `package-install` tabs.
- **[surfaces]** `apps/docs/content/reference/env.mdx` — `CODEMAP_TEST_BENCH`: by-design — real `CODEMAP_ROOT` alias used by CLI bootstrap / benches.
- **[surfaces]** `apps/docs/content/reference/roadmap.mdx` — footer link to repo `docs/roadmap.md`: by-design — curated public subset points at maintainer SSOT.
- **[security]** `apps/docs/public/.htaccess` HSTS `includeSubDomains`: by-design — same apex-host policy as sister docs deploys; confirm with host ops if changing.
- **[surfaces]** `src/version.ts` `CODEMAP_VERSION` “inlined at build time”: out of PR diff — leave; scrub if a version-export docs PR touches that file.

<!-- Example:
- **[security]** `src/cli/proxy.ts:42` — https_proxy env: by-design — standard CLI proxy convention.
Expand Down
47 changes: 47 additions & 0 deletions .agents/skills/product-tenets/SKILL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
---
name: product-tenets
description: The product north-star — four Codemap tenets (structural over semantic, predicate-as-API, local-first / agent-native surfaces, honest scope). Use when making a design, API, or architecture decision, evaluating a trade-off, justifying a feature, or writing/reviewing a docs/plans entry.
---

# Product tenets (north-star)

These four tenets are the design north-star for `@stainless-code/codemap`; reach for them whenever a decision needs justifying. Codemap is a local codebase intelligence tool: a deterministic, AST-backed SQLite index of structural facts that an agent queries with SQL instead of scanning files — the tenets fall out of that thesis.

## 1. Structural over semantic

The index carries facts the AST and resolver can prove: symbols, imports, exports, components, calls, dependencies, CSS tokens, markers, scopes, bindings. No embeddings, no LLM-in-the-box, no relevance verdict the tool invented. The agent decides relevance; Codemap answers.

- Rules out: embedding search as a core surface; "smart" context ranking baked into the index; verdicts dressed as facts.
- Codemap shape: `symbols` / `dependencies` / `references` / `coverage` tables; opt-in FTS5 (`--with-fts`) for body search that JOINs with structure — never the foundation.

## 2. Predicate-as-API (SQL + recipes)

SQL is the API. Every structural question is a `SELECT`; every repeated pattern is a named recipe (`codemap query --recipe`). Verdicts (SARIF, annotations, exit codes) are an **output mode** of recipes, never a primitive — `codemap apply` executes diff rows you provide, it doesn't invent fixes.

- Rules out: pre-baked graph verbs that hide the query; magic "find dead code" buttons with no SQL behind them; severity engines that can't be recomposed.
- Codemap shape: `query --json` / `--print-sql` / `--recipe` / `--recipes-json`; `apply` / `apply_rows` / `apply_diff_input` over explicit rows; recipes compose (`untested-and-dead`, `boundary-violations`, `churn-complexity-hotspots`, …).

## 3. Local-first, agent-native surfaces

A small SQLite file on disk (`.codemap/index.db`), queried through whatever surface the agent host speaks: CLI, MCP, HTTP. No daemon required to answer; no remote service in the path. The same recipes run in a terminal, an MCP tool, a `codemap serve` route, or a GitHub Action.

- Rules out: cloud-only indexes; mandatory long-running daemons; surfaces that only work inside one editor.
- Codemap shape: `codemap` CLI verbs; MCP tools (`query`, `show`, `impact`, `trace`, `affected`, `apply`, …); HTTP `codemap serve`; GitHub Action for CI gates; `codemap agents init` wires the surface the consumer's PM prefers.

## 4. Honest scope (anti-pitch)

Say what Codemap does **not** do, on the same page that sells it. Whole-file semantic understanding, editor-time refactoring, verdict-shaped linting, and NL Q&A over the repo are someone else's slot — link to them. Non-goals are a product floor, not a backlog in disguise.

- Rules out: scope creep into embeddings / LSP-shim / verdict engine / one-shot daemon; marketing that hides the seams.
- Codemap shape: [`docs/why-codemap.md`](../../../docs/why-codemap.md) § When to reach for something else; [`roadmap.md § Non-goals (v1)`](../../../docs/roadmap.md) as a durable floor; pre-1.0 semver honesty (breaks ship in minors; schema bumps earn the `minor`).

## Using the tenets

When a proposal conflicts with a tenet, explicitly address why and how the conflict is justified (a `docs/plans/` entry for new surface, inline for a line-level change). Maintainers use these as a PR checklist. Peer-tool design is **not** a tenet — reach for the underlying spec, not a rival's implementation ([`plan-pr-inspiration-discipline`](../../rules/plan-pr-inspiration-discipline.md)).

## Reference

- [`architecture-priming`](../../rules/architecture-priming.md) — STOP signals for structurally significant changes.
- [`improve-codebase-architecture`](../improve-codebase-architecture/SKILL.md) · [`docs/architecture.md`](../../../docs/architecture.md)
- [`docs-voice`](../docs-voice/SKILL.md) — public docs tone + peer framing (Canonical patterns).
- [`plan-pr-inspiration-discipline`](../../rules/plan-pr-inspiration-discipline.md) — cite specs, not peer implementations.
Loading
Loading