{"id":51406312,"url":"https://github.com/qxbyte/codemap","last_synced_at":"2026-07-04T11:03:13.806Z","repository":{"id":361358775,"uuid":"1251353255","full_name":"qxbyte/codemap","owner":"qxbyte","description":"🧭 为 AI Agent 准备的代码索引 — 基于 AST 精确查询调用链、路由与跨文件依赖","archived":false,"fork":false,"pushed_at":"2026-06-25T16:08:22.000Z","size":450,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-06-25T17:23:54.876Z","etag":null,"topics":["ai-agents","ast","claude-code","code-index","code-navigation","developer-tools","mcp","pypi-package","python","scip","tree-sitter"],"latest_commit_sha":null,"homepage":"https://pypi.org/project/codemap-core/","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/qxbyte.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-05-27T13:49:38.000Z","updated_at":"2026-06-25T15:57:28.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/qxbyte/codemap","commit_stats":null,"previous_names":["qxbyte/codemap"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/qxbyte/codemap","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/qxbyte%2Fcodemap","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/qxbyte%2Fcodemap/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/qxbyte%2Fcodemap/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/qxbyte%2Fcodemap/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/qxbyte","download_url":"https://codeload.github.com/qxbyte/codemap/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/qxbyte%2Fcodemap/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":35118991,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-07-04T02:00:05.987Z","response_time":113,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["ai-agents","ast","claude-code","code-index","code-navigation","developer-tools","mcp","pypi-package","python","scip","tree-sitter"],"created_at":"2026-07-04T11:03:13.223Z","updated_at":"2026-07-04T11:03:13.796Z","avatar_url":"https://github.com/qxbyte.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# CodeMap\n\n**English** · [简体中文](./README.zh-CN.md)\n\n\u003e Language-neutral code index for AI agents — precise navigation without\n\u003e full-project search.\n\nCodeMap builds a deterministic, AST-based index of your codebase so AI\nagents (Claude Code, Cursor, Codex, etc.) can find call chains, route\nmappings, and cross-file relationships without grepping the entire\nproject. Indexing is static, fast, and reproducible — no LLM in the\nindex path.\n\n**Status**: 0.3.1 stable. Installable from PyPI as `codemap-core`\nplus 17 `codemap-\u003clang\u003e` plugins + 2 framework / output plugins\n(`codemap-mybatis`, `codemap-aimemory`, added in 0.3.0; 0.3.1\nadds the `codemap llm config` CLI).\n\n\u003e 👉 **In a hurry?** The [`INSTALL.md`](./INSTALL.md) guide is the\n\u003e definitive walkthrough — it covers `pipx` / `uv tool` / `pip`,\n\u003e language-plugin injection, offline distribution, troubleshooting, and\n\u003e a verbatim clean-machine validation log.\n\n---\n\n## Table of contents\n\n- [Core principles](#core-principles)\n- [Installation](#installation)\n  - [1. Main CLI](#1-main-cli)\n  - [2. Optional extras](#2-optional-extras)\n  - [3. Language plugins](#3-language-plugins)\n  - [4. Local clone (development)](#4-local-clone-development)\n  - [4b. Install from git](#4b-install-from-git-track-main-pin-to-a-commit)\n  - [5. System requirements](#5-system-requirements)\n- [Verify](#verify)\n- [Commands](#commands)\n- [Configuration](#configuration)\n- [Built-in indexers and bridges](#built-in-indexers-and-bridges)\n- [Architecture](#architecture)\n- [Writing a plugin](#writing-a-plugin)\n- [Performance](#performance)\n- [Documentation](#documentation)\n- [Contributing](#contributing)\n- [License](#license)\n\n---\n\n## Core principles\n\n1. **Static analysis first, LLM as consumer** — the index is\n   deterministic and reproducible.\n2. **Layered defense, confidence-graded** — admit uncertainty rather\n   than hallucinate.\n3. **Cross-asset bridging is the core value** — non-source assets (XML,\n   YAML, IDL) bridge to code via the same protocol as languages.\n4. **Evolvable path** — CLI → MCP Server → Agent CLI, each step\n   independently valuable.\n5. **Ecosystem-compatible** — SCIP for symbols, MCP for tools.\n6. **Language-neutral** — no language or framework is privileged; all\n   indexers and bridges register through the same plugin protocol\n   (see [ADR-L001](docs/adr/0011-language-neutrality.md)).\n\n## Installation\n\n### 1. Main CLI\n\n```bash\n# Recommended: pipx provides environment isolation + a system-wide\n# `codemap` command\npipx install codemap-core\n\n# Plain pip (preferably into a venv)\npip install codemap-core\n\n# Or with uv\nuv tool install codemap-core\n```\n\n### 2. Optional extras\n\n```bash\n# `--watch` mode needs watchdog\npip install \"codemap-core[watch]\"\npipx install \"codemap-core[watch]\"\n\n# Development tools (tests, lint, mypy, import-linter, benchmarks)\npip install \"codemap-core[dev]\"\n```\n\n### 3. Language plugins\n\nEach non-Python language indexer ships as an **independent PyPI\ndistribution**. To add a language to a `pipx`-installed `codemap`, use\n`pipx inject` so the plugin lands in the same isolated venv as the\nmain CLI:\n\n```bash\n# All 17 languages in one shot\npipx inject codemap codemap-typescript codemap-javascript codemap-vue \\\n                    codemap-java codemap-jsp codemap-go \\\n                    codemap-rust codemap-swift codemap-kotlin \\\n                    codemap-ruby codemap-php codemap-sql \\\n                    codemap-bash codemap-c codemap-cpp \\\n                    codemap-csharp codemap-scala\n```\n\nPlain pip (when `codemap-core` is installed via `pip`, not `pipx`):\n\n```bash\npip install codemap-typescript codemap-javascript codemap-vue \\\n            codemap-java codemap-jsp codemap-go codemap-rust \\\n            codemap-swift codemap-kotlin codemap-ruby codemap-php \\\n            codemap-sql codemap-bash codemap-c codemap-cpp \\\n            codemap-csharp codemap-scala\n```\n\nOr one at a time when you only need a single language:\n\n```bash\npipx inject codemap codemap-typescript   # or pip install codemap-typescript\n```\n\nEach plugin declares `codemap-core` as a dependency, so pip will pull\nthe engine if you don't already have it. After installation, `codemap\ndoctor` lists every installed plugin alongside the built-in indexers on\nidentical terms — see [Writing a plugin](#writing-a-plugin) for the\ndesign.\n\n### 4. Local clone (development)\n\n```bash\ngit clone https://github.com/qxbyte/codemap.git\ncd codemap\n\n# Editable install with all dev tooling\npip install -e \".[dev,watch]\"\n\n# Optionally install language plugins in editable mode\npip install -e plugins/codemap-typescript\npip install -e plugins/codemap-java\npip install -e plugins/codemap-go\npip install -e plugins/codemap-rust\npip install -e plugins/codemap-swift\npip install -e plugins/codemap-kotlin\npip install -e plugins/codemap-ruby\npip install -e plugins/codemap-php\npip install -e plugins/codemap-sql\npip install -e plugins/codemap-bash\npip install -e plugins/codemap-c\npip install -e plugins/codemap-cpp\npip install -e plugins/codemap-csharp\npip install -e plugins/codemap-scala\n```\n\n### 4b. Install from git (track `main`, pin to a commit)\n\nFor users who want unreleased changes from `main` or to pin to a\nspecific commit, the git URL form still works:\n\n```bash\n# Track main\npip install git+https://github.com/qxbyte/codemap.git\npipx install git+https://github.com/qxbyte/codemap.git\n\n# Pin to a commit\npip install git+https://github.com/qxbyte/codemap.git@2c3ed45\n\n# A specific language plugin from a subdirectory\npip install \"git+https://github.com/qxbyte/codemap.git#subdirectory=plugins/codemap-typescript\"\n```\n\n### 5. System requirements\n\n| Item | Requirement |\n|---|---|\n| Python | ≥ 3.11 (the project develops on 3.13) |\n| OS | macOS / Linux (Windows may need polling fallback for `--watch`) |\n| Network | Required at install time to fetch `tree-sitter-typescript` etc. |\n\n---\n\n## Verify\n\n```bash\ncodemap --version      # → 0.1.0\ncodemap --help         # list global flags + subcommands\ncodemap doctor         # show registered indexers, bridges, and `.codemap/` state\n```\n\nA successful install with the TypeScript plugin should look like:\n\n```\n$ codemap doctor\nCodeMap 0.1.0\nproject_root: /your/path\n\n                   Registered indexers\n┃ name          ┃ version ┃ languages  ┃ file_patterns ┃\n┃ _example_lang │ 0.1.0   │ example    │ *.example     │\n┃ python        │ 0.1.0   │ python     │ *.py, *.pyi   │\n┃ typescript    │ 0.1.0   │ typescript │ *.ts, *.tsx   │\n┃ java          │ 0.1.0   │ java       │ *.java        │\n┃ go            │ 0.1.0   │ go         │ *.go          │\n┃ rust          │ 0.1.0   │ rust       │ *.rs          │\n┃ swift         │ 0.1.0   │ swift      │ *.swift       │\n┃ kotlin        │ 0.1.0   │ kotlin     │ *.kt, *.kts   │\n┃ ruby          │ 0.1.0   │ ruby       │ *.rb          │\n┃ php           │ 0.1.0   │ php        │ *.php         │\n┃ sql           │ 0.1.0   │ sql        │ *.sql, *.ddl  │\n┃ bash          │ 0.1.0   │ bash       │ *.sh, *.bash, *.bats │\n┃ c             │ 0.1.0   │ c          │ *.c, *.h      │\n┃ cpp           │ 0.1.0   │ cpp        │ *.cpp, *.cc, *.cxx, *.hpp, *.hh, *.hxx │\n┃ csharp        │ 0.1.0   │ csharp     │ *.cs, *.csx   │\n┃ scala         │ 0.1.0   │ scala      │ *.scala, *.sc │\n\n           Registered bridges\n┃ name                 ┃ version ┃ requires ┃\n┃ http_route           │ 0.1.0   │ -        │\n┃ python_cross_module  │ 0.1.0   │ -        │\n```\n\n---\n\n## Commands\n\nFull reference: [`docs/cli.md`](docs/cli.md).\n\n```bash\n# Index a project (writes .codemap/)\ncodemap index /path/to/project\ncodemap index . --rebuild               # discard old index\ncodemap index . --incremental           # re-parse only files whose sha256 changed\ncodemap index . --watch                 # stay running and re-index on changes\ncodemap index . --dry-run               # report what would be indexed, no write\n\n# Diagnose\ncodemap doctor                          # plugins + index health\ncodemap diagnostics --severity error    # show recorded warnings / errors\ncodemap config show                     # merged effective configuration\n\n# Query\ncodemap search login -n 5\ncodemap get '\u003csymbol-id\u003e'\ncodemap callers '\u003csymbol-id\u003e' --depth 2\ncodemap callees '\u003csymbol-id\u003e'\ncodemap trace --from '\u003cid\u003e' --depth 5\ncodemap trace --from '\u003cid\u003e' --to '\u003cid\u003e' # shortest path\ncodemap routes                          # HTTP routes from the http_route bridge\n\n# Knowledge recall — 0.3.5+ (codemap-aimemory plugin)\n# Scans .ai-memory/knowledge/*.yml (written by specode-distill / task-swarm)\n# and ranks by token overlap; returns top-K relevant knowledge.\n# Designed to be called by specode at the start of the requirements phase.\ncodemap recall '\u003cquery\u003e'                                 # default top-k 5, yaml output\ncodemap recall '\u003cquery\u003e' -p /abs/project -k 10 -o json   # explicit project + json\ncodemap recall '\u003cquery\u003e' -t rules,pitfalls               # filter categories\ncodemap recall --from-spec requirements.md               # 0.3.6+: use spec file as query\ncodemap recall '\u003cquery\u003e' --with-content                  # 0.4.0+: include rule/pit/case core fields\n# Every result carries `freshness_score`/`ranked_score`/`stale` since 0.4.0;\n# fresher hits outrank stale ones at the same token score (180-day half-life + code-churn decay).\n# With `codemap-semantic-index` plugin installed (P1-3, since v0.4.2), recall\n# automatically does hybrid token+embedding ranking with RRF fusion.\n\n# Semantic recall (requires opt-in `codemap-semantic-index` plugin, P1-3)\ncodemap embed install               # interactive picker; downloads default Qwen3-Embedding-0.6B (1.2GB)\ncodemap embed                       # incremental embed of knowledge-base/*.md\ncodemap embed --rebuild             # force full rebuild\ncodemap embed backend set --provider qwen --api-key sk-xxx  # switch to cloud Qwen embedding\n\n# Machine-readable output: all commands take --json\ncodemap --json callers '\u003csymbol-id\u003e'\n\n# Optional LLM enrichment (codemap-aimemory plugin, 0.3.0+)\ncodemap llm config set api-key sk-xxx       # persist to ~/.config/codemap/llm.yaml\ncodemap llm config set base-url https://api.deepseek.com/v1\ncodemap llm config set model deepseek-chat\ncodemap llm config show                     # masked-key view + value source\ncodemap enrich .                            # fills .ai-memory/enrichment/*.yml\ncodemap enrich . --dry-run                  # count fn/method symbols, no API call\n```\n\nExit codes follow `sysexits.h` (ADR-005); see\n[`docs/cli.md`](docs/cli.md#exit-codes) for the table.\n\n---\n\n## Output formats\n\n`codemap index` produces two parallel directories at the project root:\n\n```\n\u003cproject\u003e/\n├── .codemap/        ← deterministic, machine-friendly index (queried by `codemap …`)\n└── .ai-memory/      ← four-layer-memory-model L1 layout (consumed by AI agents)\n```\n\n### `.codemap/` — deterministic index (JSON, 7 files)\n\n| File | Contents |\n|---|---|\n| `symbols.json` | All symbols keyed by `SymbolID`. Each entry: `kind`, `language`, `file`, `range`, `signature`, `annotations`, `confidence`, `extra` (per-language metadata: `pending_calls`, `http_route`, `supertypes`, `imports`, `params`, `return_type`, `change_count_90d`, …). |\n| `edges.json` | Directed relations: `calls` / `extends` / `implements` / `overrides` / `references` / `routes_to` / `maps_to` / `imports` / `accesses_table`. Each carries `confidence` ∈ {`high`, `medium`, `low`}. |\n| `routes.json` | HTTP routes minted by the `http_route` bridge from `extra[\"http_route\"]`. |\n| `aliases.json` | Synthetic intermediate ↔ real symbol links (e.g. route → handler). |\n| `manifest.json` | Project root, `codemap_version`, registered indexers + bridges + their versions, per-file sha256 / mtime / language. |\n| `diagnostics.json` | Indexer / bridge warnings collected during the run (severity + code + message + producer). |\n| `.lock` | Cross-process write lock; do not edit. |\n\n### `.ai-memory/` — four-layer memory model\n\nWritten by `codemap-aimemory` (L0+L1, every `codemap index`) and\noptionally by [sibling tools](#integration-with-specode-distill-and-task-swarm)\n(`specode-distill` for L2/L3, `task-swarm` for the auto-ingested\n`cases` + `pitfalls`). AI agents read this tree directly. Stable\n`entity_id` slugs are derived from the SCIP `SymbolID`\n(e.g. `fn-calcPrice` / `cls-OrderService` / `tbl-sf_coupon`).\n\n```\n.ai-memory/\n├── project.yml              ← L0   (codemap-aimemory 0.3.2+)\n│                              tech stack / dependencies / git remote /\n│                              top dirs / configs — best-effort autodetect\n│\n├── entities/                ← L1   (codemap-aimemory 0.3.0+)\n│   ├── functions.yml          fn-/cls- entities with calls / called_by /\n│   │                          related_tables / signature / line_range /\n│   │                          confidence / change_count_90d /\n│   │                          business_meaning\n│   ├── tables.yml             tbl-* table entities\n│   ├── files.yml              file-* file entries\n│   └── modules.yml            mod-* per-file aggregates (0.3.3+):\n│                              {id, path, language, fn_count, cls_count,\n│                               functions[], classes[]}\n│\n├── relations/               ← L1\n│   ├── call-graph.yml         `{from, to, type=calls, confidence}`\n│   ├── table-relations.yml    `{from, to, type=accesses_table, confidence}`\n│   └── rule-constraints.yml   empty placeholder (L2 owns the channel)\n│\n├── enrichment/              ← L1 OPTIONAL — LLM-generated overlays\n│   └── \u003csha1[:12]\u003e.yml        `{symbol_id, business_meaning,\n│                                related_rules, confidence:\"llm\",\n│                                source_model, generated_at}`\n│\n├── _global/                 ← L1↔L2/L3 lookup (codemap-aimemory 0.3.4+)\n│   └── entities.yml           Cross-walk: every entity_id (code or\n│                              knowledge) with `source` ∈\n│                              {code, knowledge, both} +\n│                              `knowledge_refs` (which knowledge yml\n│                              mention this entity). Backs `codemap recall`.\n│\n├── _semantic/               ← P1-3, OPTIONAL — written by codemap-semantic-index\n│   ├── chunks.json            chunked text + metadata (model-independent)\n│   ├── vectors.npy            (n_chunks, 1024) float32 (model-specific)\n│   ├── model_id.txt           active backend fingerprint\n│   └── manifest.json          text_hash → chunk_id (drives incremental embed)\n│\n└── knowledge/               ← L2 + L3 (NOT written by codemap itself —\n                              produced by specode-distill / task-swarm;\n                              codemap-aimemory reads it to build\n                              _global/entities.yml and to power recall)\n    ├── rules/    rule-*.yml         L2 business rules / mechanisms\n    ├── business/ biz-*.yml          L2 business processes / UI features\n    ├── modules/  mod-*.yml          L2 module maps (table / call_chain)\n    ├── cases/    case-*.yml         L3 historical implementation cases\n    └── pitfalls/ pit-*.yml          L3 reusable failure / fix lessons\n```\n\nTwo-hop fan-out: when a Java method `maps_to` a `sql_mapping` that\n`accesses_table` T, T automatically lands on the method's\n`related_tables`. So `fn-selectByUser.related_tables = [tbl-sf_coupon]`\nwithout the agent needing to follow the chain itself.\n\n---\n\n### Integration with `specode-distill` and `task-swarm`\n\ncodemap-aimemory owns L0+L1; **L2+L3 (`knowledge/`) come from sibling\ntools in the [pluginhub](https://github.com/qxbyte/pluginhub) family**.\nThe integration is one-way and loose — codemap doesn't import the\nothers, just reads their yml output when present:\n\n| Layer | Writer | When |\n|---|---|---|\n| L0 `project.yml` | `codemap-aimemory` (this) | every `codemap index` |\n| L1 `entities/*`, `relations/*`, `enrichment/*` | `codemap-aimemory` (this) | every `codemap index` (enrichment is opt-in via `codemap enrich`) |\n| L1↔L2/L3 `_global/entities.yml` | `codemap-aimemory` (this) | every `codemap index`, mining `knowledge/*.yml` if present |\n| L1.5 `_semantic/*` (chunks + vectors) | `codemap-semantic-index` (opt-in plugin, P1-3) | explicit `codemap embed` |\n| L2/L3 `knowledge/rules,business,modules,cases,pitfalls/*.yml` | `specode-distill` (`pluginhub` plugin, specode 3.0+; 3.3.1 surfaces `CLAUDE.md / AGENT.md` paths into `requirements.md` via AI-EDS v0.9 痛点 #14 方案 D; 3.3.2 adds cache vs marketplace drift hint; 3.4.0 adds autonomous-mode defaults for CI / unattended use) | user runs `/specode:specode-distill \u003cslug\u003e` or accepts the prompt at end of specode's acceptance phase |\n| L3 `knowledge/cases/case-*.yml` + `knowledge/pitfalls/pit-*.yml` | `task-swarm` (`pluginhub` plugin, 0.7+ delegates yml/md writes to `codemap knowledge write`; 0.7.3 + 0.7.4 surface `CLAUDE.md / AGENT.md` paths into every subagent `task.md` + drop `_PROJECT_AGENT_DOCS.md` sentinel into inbox; 0.8.0 adds `init` dedupe with `--on-existing` flag) | every successful `task_swarm.py resolve` |\n\nWhen `codemap-semantic-index` is installed, `codemap recall` automatically becomes **hybrid (token + embedding) ranking via Reciprocal Rank Fusion** (k=60), then multiplied by `freshness_score`. Embedding hits that token recall missed surface naturally. Without the plugin installed, recall remains token-only — no behaviour change for users who don't want embeddings.\n\nEach `specode-distill` / `task-swarm` write **also** produces a twin\nmarkdown file under `\u003cproject_root\u003e/knowledge-base/\u003ccategory\u003e/\u003cid\u003e.md`\n(same stem as the yml). The twin md preserves narrative / ascii flow\ncharts / wikilink-style tables that field-level yml necessarily\nflattens, and is intended as the high-quality slicing source for a\nfuture embedding indexer. codemap itself doesn't read `knowledge-base/`\ntoday — `codemap recall` operates on the yml side; the md exists to\nserve human reading and future P1-3 semantic search.\n\n**Use `codemap recall '\u003cquery\u003e'` to query the union** (code-side entity\nhits + token overlap against every `knowledge/*.yml`). This is what\nspecode 2.1+ calls from its requirements phase to inject \"已知约束 /\n历史坑\" context before drafting a new spec. See `docs/integration.md`\n(coming) for the full agent-side workflow.\n\nNo part of `knowledge/` is required for codemap to function. On a\nproject that has never run `specode-distill` or `task-swarm`,\n`_global/entities.yml` simply lists code entities with\n`source: code`, and `codemap recall` returns matched code entities\nwith empty `knowledge: []`.\n\n---\n\n## LLM configuration (optional)\n\nThe core index is **always LLM-free** — `codemap index` never calls any\nLLM. Only the optional `codemap enrich` command in `codemap-aimemory`\nwrites the `enrichment/` overlay, and only when **you** invoke it. The\nexistence of an API key is the on/off switch: without one, `codemap\nenrich` exits with a clear error and no network call is made.\n\nThree configuration sources, **first non-empty wins**:\n\n1. **CLI flag** — `--api-key`, `--base-url`, `--model`, `--backend`\n2. **Environment variable** — `CODEMAP_LLM_API_KEY` (also\n   `ANTHROPIC_API_KEY`, `OPENAI_API_KEY`); `CODEMAP_LLM_BASE_URL`\n   (also `OPENAI_BASE_URL`, `ANTHROPIC_BASE_URL`);\n   `CODEMAP_LLM_MODEL`; `CODEMAP_LLM_BACKEND`\n3. **Persistent file config** — `~/.config/codemap/llm.yaml` (managed\n   by `codemap llm config set/unset/show`; written `chmod 600`)\n4. Built-in defaults — backend `openai`, model `gpt-4o-mini`\n\n### Common provider endpoints (OpenAI-compatible — `--backend openai`)\n\n| Provider | Model example | Base URL |\n|---|---|---|\n| OpenAI | `gpt-4o-mini` | `https://api.openai.com/v1` *(default)* |\n| DeepSeek | `deepseek-chat` | `https://api.deepseek.com/v1` |\n| 智谱 GLM | `glm-4-flash` | `https://open.bigmodel.cn/api/paas/v4/` |\n| MiniMax | `abab6.5s-chat` | `https://api.minimax.chat/v1` |\n| 月之暗面 Kimi | `moonshot-v1-8k` | `https://api.moonshot.cn/v1` |\n| 阿里通义 | `qwen-plus` | `https://dashscope.aliyuncs.com/compatible-mode/v1` |\n| 小米 MiMo | `mimo-large` | *(per vendor docs; OpenAI-compatible)* |\n| Ollama (local) | `llama3` | `http://localhost:11434/v1` — use `--backend ollama` (key not needed) |\n| Anthropic native | `claude-sonnet-4-5` | *(use `--backend anthropic`; requires `anthropic` SDK via `pip install codemap-aimemory[llm]`)* |\n\nExample with DeepSeek:\n\n```bash\ncodemap llm config set base-url https://api.deepseek.com/v1\ncodemap llm config set api-key sk-xxx\ncodemap llm config set model deepseek-chat\ncodemap enrich .\n```\n\n---\n\n## Configuration\n\nProject-level configuration lives at `.codemap/config.yaml` (committed\nor git-ignored — your choice). A user-level override at\n`~/.config/codemap/config.yaml` is layered on top of built-in defaults,\nand the project file is layered on top of that. CLI flags win over all\nthree.\n\n```yaml\n# .codemap/config.yaml\nstorage:\n  backend: json          # json | sqlite (sqlite reserved for a future sprint)\n\nindex:\n  ignore: []             # extra fnmatch patterns on names + project-relative paths\n  max_file_bytes: 10485760\n  follow_symlinks: false\n\nindexers:\n  enabled: all           # \"all\" or an explicit list of indexer names\n  disabled: []           # subtractive\n\nbridges:\n  enabled: all\n  disabled: []\n```\n\nFull reference: [`docs/configuration.md`](docs/configuration.md).\nRun `codemap config show` to inspect the merged result and see which\nfile contributed each value.\n\n---\n\n## Built-in indexers and bridges\n\n| Indexer | Files | Provided by | Status |\n|---|---|---|---|\n| `python` | `*.py`, `*.pyi` | main repo | first-class, dogfooded |\n| `typescript` | `*.ts`, `*.tsx` | [`plugins/codemap-typescript/`](plugins/codemap-typescript) | independent plugin |\n| `java` | `*.java` | [`plugins/codemap-java/`](plugins/codemap-java) | independent plugin |\n| `go` | `*.go` | [`plugins/codemap-go/`](plugins/codemap-go) | independent plugin |\n| `rust` | `*.rs` | [`plugins/codemap-rust/`](plugins/codemap-rust) | independent plugin |\n| `swift` | `*.swift` | [`plugins/codemap-swift/`](plugins/codemap-swift) | independent plugin |\n| `kotlin` | `*.kt`, `*.kts` | [`plugins/codemap-kotlin/`](plugins/codemap-kotlin) | independent plugin |\n| `ruby` | `*.rb` | [`plugins/codemap-ruby/`](plugins/codemap-ruby) | independent plugin |\n| `php` | `*.php` | [`plugins/codemap-php/`](plugins/codemap-php) | independent plugin |\n| `sql` | `*.sql`, `*.ddl` | [`plugins/codemap-sql/`](plugins/codemap-sql) | independent plugin (DDL only) |\n| `bash` | `*.sh`, `*.bash`, `*.bats` | [`plugins/codemap-bash/`](plugins/codemap-bash) | independent plugin |\n| `c` | `*.c`, `*.h` | [`plugins/codemap-c/`](plugins/codemap-c) | independent plugin |\n| `cpp` | `*.cpp`, `*.cc`, `*.cxx`, `*.hpp`, `*.hh`, `*.hxx` | [`plugins/codemap-cpp/`](plugins/codemap-cpp) | independent plugin |\n| `csharp` | `*.cs`, `*.csx` | [`plugins/codemap-csharp/`](plugins/codemap-csharp) | independent plugin |\n| `scala` | `*.scala`, `*.sc` | [`plugins/codemap-scala/`](plugins/codemap-scala) | independent plugin |\n| `_example_lang` | `*.example` | main repo | reference / smoke |\n\n| Bridge | Purpose |\n|---|---|\n| `http_route` | Mints `scip-route` intermediates from `Symbol.extra[\"http_route\"]` and `[\"http_calls\"]` metadata; links client callers to server handlers regardless of language |\n| `python_cross_module` | Resolves synthetic `scip-python . . . \u003cmodule\u003e/\u003cleaf\u003e.` targets emitted by the Python indexer to concrete local symbols when the file is in the index |\n\nNew language? You **never** need to PR the main repository — see\n[Writing a plugin](#writing-a-plugin).\n\n---\n\n## Architecture\n\n```\ncli  →  core  ←  indexers\n        ↑          ↑\n        └── io ────┘\n        ↑\n        mcp\n```\n\n- **core** — pure business logic, Pydantic data models, SymbolID (SCIP\n  format), call-graph algorithms (`walk_chain`, `shortest_path`)\n- **io** — persistence adapters (JSON today, SQLite reserved for scale)\n- **indexers** — pluggable language/asset indexers, discovered via\n  `codemap.indexers` entry-point group\n- **bridges** — pluggable cross-language resolvers, discovered via\n  `codemap.bridges` entry-point group\n- **cli** — Typer command surface\n- **mcp** — MCP server, later sprint\n\nStrict import-linter contracts (`pyproject.toml`) enforce the\ndependency direction `cli → core ← indexers`, `cli → core ← io` on\nevery PR.\n\n---\n\n## Writing a plugin\n\nCodeMap's indexers and bridges are plugin-first. Adding a new language is\na separate PyPI package — main repo is never touched. The\n`codemap-typescript` package under `plugins/` is the reference\nimplementation:\n\n```toml\n# your-plugin/pyproject.toml\n[project.entry-points.\"codemap.indexers\"]\nyourlang = \"codemap_yourlang:YourLangIndexer\"\n```\n\nThat one line is the only coupling. After `pip install your-plugin`\nyour indexer appears in `codemap doctor` on identical terms.\n\nStep-by-step guide: [`docs/plugin-guide.md`](docs/plugin-guide.md).\nReference: [`plugins/codemap-typescript/`](plugins/codemap-typescript).\n\n---\n\n## Performance\n\nBaseline numbers (median, M-series single core, indexing the CodeMap\nrepo itself, 437 symbols / 1232 edges):\n\n| Bench | Median | Target (design §21) |\n|---|---:|---:|\n| full index | 73 ms | ≤ 3 s |\n| `callers` | 4.7 µs | ≤ 50 ms |\n| `callees` | 26 µs | ≤ 50 ms |\n| `walk_chain` depth 10 | 72 µs | ≤ 200 ms |\n\nRe-run locally with `pytest -m bench -o addopts=\"\"`. PRs that regress\nany median by ≥ 20 % are blocked by CI (ADR-010). Full table and\nmethodology: [`docs/performance.md`](docs/performance.md).\n\n---\n\n## Documentation\n\n| File | Topic |\n|---|---|\n| [`docs/cli.md`](docs/cli.md) | Every command, flag, JSON envelope, exit code |\n| [`docs/configuration.md`](docs/configuration.md) | All config keys + merge order |\n| [`docs/plugin-guide.md`](docs/plugin-guide.md) | How to write an indexer / bridge plugin |\n| [`docs/performance.md`](docs/performance.md) | Baseline numbers + ADR-010 regression policy |\n| [`docs/indexers/python.md`](docs/indexers/python.md) | Python indexer details |\n| [`docs/bridges/http_route.md`](docs/bridges/http_route.md) | HTTP route bridge contract |\n| [`docs/adr/`](docs/adr/) | Architecture decision records (1–12 + L001) |\n| [`CHANGELOG.md`](CHANGELOG.md) | Release notes |\n\n---\n\n## Contributing\n\nSee [`CONTRIBUTING.md`](CONTRIBUTING.md). The key invariant: **no\nlanguage is a first-class citizen**. Proposals that special-case any\necosystem will be asked to refactor into the generic plugin protocol\n(ADR-L001).\n\nCI gates every PR through `ruff`, `mypy --strict`, `import-linter`,\n`pytest --cov 80%`, and the benchmark suite.\n\n---\n\n## License\n\nMIT — see [`LICENSE`](LICENSE).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fqxbyte%2Fcodemap","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fqxbyte%2Fcodemap","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fqxbyte%2Fcodemap/lists"}