cairn-intel 0.6.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- cairn_intel-0.6.1/LICENSE +21 -0
- cairn_intel-0.6.1/NOTICE +82 -0
- cairn_intel-0.6.1/PKG-INFO +310 -0
- cairn_intel-0.6.1/README.md +250 -0
- cairn_intel-0.6.1/pyproject.toml +124 -0
- cairn_intel-0.6.1/setup.cfg +4 -0
- cairn_intel-0.6.1/src/cairn/__init__.py +3 -0
- cairn_intel-0.6.1/src/cairn/agent_install/__init__.py +329 -0
- cairn_intel-0.6.1/src/cairn/agent_install/_common.py +300 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/__init__.py +6 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/agy.py +52 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/claude.py +151 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/claude_desktop.py +60 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/cursor.py +70 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/droid.py +78 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/opencode.py +75 -0
- cairn_intel-0.6.1/src/cairn/agent_install/clients/zcode.py +102 -0
- cairn_intel-0.6.1/src/cairn/agent_install/detect.py +178 -0
- cairn_intel-0.6.1/src/cairn/agent_install/merge.py +452 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/__init__.py +0 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/commands/cairn-audit.md +24 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/commands/cairn-prep.md +23 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/commands/cairn-refresh.md +18 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/commands/cairn-ship.md +21 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/commands/cairn.md +18 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/cursor/cairn-explorer.json +36 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/cursor/cairn.mdc +132 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/cursor/knowledge-steward.json +26 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/SKILL.md +146 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/evals/README.md +44 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/evals/rule01-ambiguous-name.md +55 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/evals/rule06-impact-common-name.md +65 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/evals/rule08-precise-then-fuzzy.md +54 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/evals/rule08b-empty-precise-gave-up.md +65 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/evals/rule09-impact-plus-cross-repo.md +90 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/evals/rule10-mutations-via-cli.md +107 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/references/cli-fallback.md +25 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/references/golden-rules.md +159 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/references/task-queue.md +64 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/references/tool-behaviors.md +18 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/references/tools.md +41 -0
- cairn_intel-0.6.1/src/cairn/agent_integration/skill/scripts/impact_guard.py +126 -0
- cairn_intel-0.6.1/src/cairn/bench/__init__.py +34 -0
- cairn_intel-0.6.1/src/cairn/bench/corpus.py +104 -0
- cairn_intel-0.6.1/src/cairn/bench/perf_suite.py +215 -0
- cairn_intel-0.6.1/src/cairn/bench/report.py +170 -0
- cairn_intel-0.6.1/src/cairn/bench/scaling_suite.py +123 -0
- cairn_intel-0.6.1/src/cairn/bench/timing.py +127 -0
- cairn_intel-0.6.1/src/cairn/cli/__init__.py +41 -0
- cairn_intel-0.6.1/src/cairn/cli/_helpers.py +38 -0
- cairn_intel-0.6.1/src/cairn/cli/agents.py +248 -0
- cairn_intel-0.6.1/src/cairn/cli/ask_context.py +74 -0
- cairn_intel-0.6.1/src/cairn/cli/bench.py +180 -0
- cairn_intel-0.6.1/src/cairn/cli/compass.py +455 -0
- cairn_intel-0.6.1/src/cairn/cli/core.py +460 -0
- cairn_intel-0.6.1/src/cairn/cli/dataflow.py +60 -0
- cairn_intel-0.6.1/src/cairn/cli/display.py +549 -0
- cairn_intel-0.6.1/src/cairn/cli/embed.py +228 -0
- cairn_intel-0.6.1/src/cairn/cli/hooks_viz.py +107 -0
- cairn_intel-0.6.1/src/cairn/cli/knowledge.py +529 -0
- cairn_intel-0.6.1/src/cairn/cli/main.py +27 -0
- cairn_intel-0.6.1/src/cairn/cli/memory.py +412 -0
- cairn_intel-0.6.1/src/cairn/cli/query.py +207 -0
- cairn_intel-0.6.1/src/cairn/cli/serve.py +241 -0
- cairn_intel-0.6.1/src/cairn/cli/system.py +222 -0
- cairn_intel-0.6.1/src/cairn/cli/task.py +130 -0
- cairn_intel-0.6.1/src/cairn/cli/tree.py +24 -0
- cairn_intel-0.6.1/src/cairn/cli/uninstall.py +357 -0
- cairn_intel-0.6.1/src/cairn/cli/update.py +89 -0
- cairn_intel-0.6.1/src/cairn/cli/upgrade.py +146 -0
- cairn_intel-0.6.1/src/cairn/cli/validate.py +66 -0
- cairn_intel-0.6.1/src/cairn/cli/wiki.py +86 -0
- cairn_intel-0.6.1/src/cairn/compass/__init__.py +19 -0
- cairn_intel-0.6.1/src/cairn/compass/critic.py +166 -0
- cairn_intel-0.6.1/src/cairn/compass/flow_gaps.py +124 -0
- cairn_intel-0.6.1/src/cairn/compass/gaps.py +62 -0
- cairn_intel-0.6.1/src/cairn/compass/generator.py +557 -0
- cairn_intel-0.6.1/src/cairn/compass/router.py +341 -0
- cairn_intel-0.6.1/src/cairn/eval.py +167 -0
- cairn_intel-0.6.1/src/cairn/graph/__init__.py +77 -0
- cairn_intel-0.6.1/src/cairn/graph/ann_index.py +140 -0
- cairn_intel-0.6.1/src/cairn/graph/builder.py +926 -0
- cairn_intel-0.6.1/src/cairn/graph/config.py +157 -0
- cairn_intel-0.6.1/src/cairn/graph/cross_repo.py +176 -0
- cairn_intel-0.6.1/src/cairn/graph/dataflow.py +218 -0
- cairn_intel-0.6.1/src/cairn/graph/embeddings.py +792 -0
- cairn_intel-0.6.1/src/cairn/graph/explore.py +317 -0
- cairn_intel-0.6.1/src/cairn/graph/fusion.py +44 -0
- cairn_intel-0.6.1/src/cairn/graph/incremental.py +446 -0
- cairn_intel-0.6.1/src/cairn/graph/lexical.py +173 -0
- cairn_intel-0.6.1/src/cairn/graph/queries.py +48 -0
- cairn_intel-0.6.1/src/cairn/graph/reranker.py +103 -0
- cairn_intel-0.6.1/src/cairn/graph/resolver.py +437 -0
- cairn_intel-0.6.1/src/cairn/graph/scanner.py +536 -0
- cairn_intel-0.6.1/src/cairn/graph/schema.py +520 -0
- cairn_intel-0.6.1/src/cairn/graph/semantic.py +279 -0
- cairn_intel-0.6.1/src/cairn/graph/stats.py +91 -0
- cairn_intel-0.6.1/src/cairn/graph/tests.py +113 -0
- cairn_intel-0.6.1/src/cairn/graph/tokenize.py +41 -0
- cairn_intel-0.6.1/src/cairn/graph/traversal.py +407 -0
- cairn_intel-0.6.1/src/cairn/graph/vector_math.py +28 -0
- cairn_intel-0.6.1/src/cairn/graph/watcher.py +113 -0
- cairn_intel-0.6.1/src/cairn/hooks/__init__.py +0 -0
- cairn_intel-0.6.1/src/cairn/hooks/claude_hooks.py +185 -0
- cairn_intel-0.6.1/src/cairn/hooks/cursor_hooks.py +19 -0
- cairn_intel-0.6.1/src/cairn/hooks/git_hooks.py +78 -0
- cairn_intel-0.6.1/src/cairn/knowledge/__init__.py +15 -0
- cairn_intel-0.6.1/src/cairn/knowledge/search.py +309 -0
- cairn_intel-0.6.1/src/cairn/knowledge/store.py +214 -0
- cairn_intel-0.6.1/src/cairn/knowledge/workflow.py +345 -0
- cairn_intel-0.6.1/src/cairn/llm/__init__.py +12 -0
- cairn_intel-0.6.1/src/cairn/llm/client.py +176 -0
- cairn_intel-0.6.1/src/cairn/llm/tasks.py +505 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/__init__.py +13 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/_server_core.py +213 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/lifecycle.py +322 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/metric_buffering.py +200 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/server.py +278 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/structured.py +132 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/tools_compass.py +250 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/tools_graph.py +831 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/tools_knowledge.py +183 -0
- cairn_intel-0.6.1/src/cairn/mcp_server/tools_memory.py +308 -0
- cairn_intel-0.6.1/src/cairn/memory/__init__.py +19 -0
- cairn_intel-0.6.1/src/cairn/memory/privacy.py +52 -0
- cairn_intel-0.6.1/src/cairn/memory/promotion.py +589 -0
- cairn_intel-0.6.1/src/cairn/memory/scoring.py +228 -0
- cairn_intel-0.6.1/src/cairn/memory/store.py +332 -0
- cairn_intel-0.6.1/src/cairn/memory/store_protocol.py +167 -0
- cairn_intel-0.6.1/src/cairn/okf/__init__.py +12 -0
- cairn_intel-0.6.1/src/cairn/okf/bundle.py +182 -0
- cairn_intel-0.6.1/src/cairn/okf/concept.py +227 -0
- cairn_intel-0.6.1/src/cairn/okf/conformance.py +55 -0
- cairn_intel-0.6.1/src/cairn/okf/provenance.py +20 -0
- cairn_intel-0.6.1/src/cairn/okf/utils.py +20 -0
- cairn_intel-0.6.1/src/cairn/parsers/__init__.py +0 -0
- cairn_intel-0.6.1/src/cairn/parsers/_registry.py +128 -0
- cairn_intel-0.6.1/src/cairn/parsers/_scip_pb2.py +111 -0
- cairn_intel-0.6.1/src/cairn/parsers/base.py +213 -0
- cairn_intel-0.6.1/src/cairn/parsers/dart.py +376 -0
- cairn_intel-0.6.1/src/cairn/parsers/go.py +373 -0
- cairn_intel-0.6.1/src/cairn/parsers/inference/__init__.py +7 -0
- cairn_intel-0.6.1/src/cairn/parsers/java.py +275 -0
- cairn_intel-0.6.1/src/cairn/parsers/kotlin.py +677 -0
- cairn_intel-0.6.1/src/cairn/parsers/objc.py +353 -0
- cairn_intel-0.6.1/src/cairn/parsers/python_parser.py +229 -0
- cairn_intel-0.6.1/src/cairn/parsers/routes.py +398 -0
- cairn_intel-0.6.1/src/cairn/parsers/scip_importer.py +777 -0
- cairn_intel-0.6.1/src/cairn/parsers/scip_indexers.py +248 -0
- cairn_intel-0.6.1/src/cairn/parsers/service_calls.py +133 -0
- cairn_intel-0.6.1/src/cairn/parsers/swift.py +287 -0
- cairn_intel-0.6.1/src/cairn/parsers/typescript.py +527 -0
- cairn_intel-0.6.1/src/cairn/paths.py +176 -0
- cairn_intel-0.6.1/src/cairn/refs.py +111 -0
- cairn_intel-0.6.1/src/cairn/retrieval/__init__.py +25 -0
- cairn_intel-0.6.1/src/cairn/retrieval/protocols.py +90 -0
- cairn_intel-0.6.1/src/cairn/retrieval/vector_scan.py +77 -0
- cairn_intel-0.6.1/src/cairn/utils/__init__.py +0 -0
- cairn_intel-0.6.1/src/cairn/utils/git.py +31 -0
- cairn_intel-0.6.1/src/cairn/viz/__init__.py +9 -0
- cairn_intel-0.6.1/src/cairn/viz/query.py +145 -0
- cairn_intel-0.6.1/src/cairn/viz/renderers.py +119 -0
- cairn_intel-0.6.1/src/cairn/wiki/__init__.py +9 -0
- cairn_intel-0.6.1/src/cairn/wiki/generator.py +106 -0
- cairn_intel-0.6.1/src/cairn_intel.egg-info/PKG-INFO +310 -0
- cairn_intel-0.6.1/src/cairn_intel.egg-info/SOURCES.txt +239 -0
- cairn_intel-0.6.1/src/cairn_intel.egg-info/dependency_links.txt +1 -0
- cairn_intel-0.6.1/src/cairn_intel.egg-info/entry_points.txt +2 -0
- cairn_intel-0.6.1/src/cairn_intel.egg-info/requires.txt +42 -0
- cairn_intel-0.6.1/src/cairn_intel.egg-info/top_level.txt +1 -0
- cairn_intel-0.6.1/tests/test_agent_install_dry.py +78 -0
- cairn_intel-0.6.1/tests/test_agent_surface.py +813 -0
- cairn_intel-0.6.1/tests/test_ann_index.py +164 -0
- cairn_intel-0.6.1/tests/test_atomic_config_writes.py +140 -0
- cairn_intel-0.6.1/tests/test_auto_decay_hook.py +93 -0
- cairn_intel-0.6.1/tests/test_backup_to_atomic.py +203 -0
- cairn_intel-0.6.1/tests/test_bench.py +195 -0
- cairn_intel-0.6.1/tests/test_big_tech_improvements.py +110 -0
- cairn_intel-0.6.1/tests/test_build_graph_connection_cleanup.py +155 -0
- cairn_intel-0.6.1/tests/test_build_graph_decomposition.py +182 -0
- cairn_intel-0.6.1/tests/test_build_graph_periodic_commit.py +111 -0
- cairn_intel-0.6.1/tests/test_build_inmemory.py +149 -0
- cairn_intel-0.6.1/tests/test_build_scip_hybrid.py +244 -0
- cairn_intel-0.6.1/tests/test_chunk_spike.py +68 -0
- cairn_intel-0.6.1/tests/test_cli_init_rail.py +82 -0
- cairn_intel-0.6.1/tests/test_cli_smoke.py +44 -0
- cairn_intel-0.6.1/tests/test_clients.py +92 -0
- cairn_intel-0.6.1/tests/test_compass_critic.py +160 -0
- cairn_intel-0.6.1/tests/test_core_smoke.py +514 -0
- cairn_intel-0.6.1/tests/test_cross_repo_namespaces.py +160 -0
- cairn_intel-0.6.1/tests/test_dataflow_transitive_closure.py +175 -0
- cairn_intel-0.6.1/tests/test_display_rail.py +214 -0
- cairn_intel-0.6.1/tests/test_efficiency_hygiene.py +41 -0
- cairn_intel-0.6.1/tests/test_embed_commit_tracking.py +94 -0
- cairn_intel-0.6.1/tests/test_embedding_backend_quality.py +256 -0
- cairn_intel-0.6.1/tests/test_embedding_model.py +77 -0
- cairn_intel-0.6.1/tests/test_embeddings_freshness.py +169 -0
- cairn_intel-0.6.1/tests/test_fusion.py +95 -0
- cairn_intel-0.6.1/tests/test_gitignore_and_router_fixes.py +100 -0
- cairn_intel-0.6.1/tests/test_golden_parsers.py +24 -0
- cairn_intel-0.6.1/tests/test_header_disambiguation.py +83 -0
- cairn_intel-0.6.1/tests/test_impact_test_labeling.py +151 -0
- cairn_intel-0.6.1/tests/test_import_validation.py +162 -0
- cairn_intel-0.6.1/tests/test_invariants.py +275 -0
- cairn_intel-0.6.1/tests/test_knowledge_status.py +119 -0
- cairn_intel-0.6.1/tests/test_knowledge_workflow.py +159 -0
- cairn_intel-0.6.1/tests/test_kotlin_operator_invoke.py +271 -0
- cairn_intel-0.6.1/tests/test_layer_direction.py +163 -0
- cairn_intel-0.6.1/tests/test_mcp_connection_leaks.py +226 -0
- cairn_intel-0.6.1/tests/test_mcp_phase3.py +281 -0
- cairn_intel-0.6.1/tests/test_memory_lifecycle.py +308 -0
- cairn_intel-0.6.1/tests/test_memory_store_fixes.py +234 -0
- cairn_intel-0.6.1/tests/test_memory_store_protocol.py +110 -0
- cairn_intel-0.6.1/tests/test_okf_concept.py +214 -0
- cairn_intel-0.6.1/tests/test_parsers_language_adapter.py +151 -0
- cairn_intel-0.6.1/tests/test_port_dry_and_unload_fixes.py +130 -0
- cairn_intel-0.6.1/tests/test_portable_paths.py +220 -0
- cairn_intel-0.6.1/tests/test_reindex_resolution_invariant.py +123 -0
- cairn_intel-0.6.1/tests/test_reranker.py +153 -0
- cairn_intel-0.6.1/tests/test_resolver_type_scoped_fallback.py +182 -0
- cairn_intel-0.6.1/tests/test_retrieval.py +147 -0
- cairn_intel-0.6.1/tests/test_router_eval.py +86 -0
- cairn_intel-0.6.1/tests/test_schema_versioning.py +156 -0
- cairn_intel-0.6.1/tests/test_scip_importer.py +650 -0
- cairn_intel-0.6.1/tests/test_scip_incremental.py +125 -0
- cairn_intel-0.6.1/tests/test_scip_indexers.py +226 -0
- cairn_intel-0.6.1/tests/test_scoring_fixes.py +304 -0
- cairn_intel-0.6.1/tests/test_search_symbols.py +200 -0
- cairn_intel-0.6.1/tests/test_semantic_enrichment.py +88 -0
- cairn_intel-0.6.1/tests/test_server_robustness.py +141 -0
- cairn_intel-0.6.1/tests/test_single_repo.py +155 -0
- cairn_intel-0.6.1/tests/test_staleness_banner.py +96 -0
- cairn_intel-0.6.1/tests/test_tasks_safety.py +373 -0
- cairn_intel-0.6.1/tests/test_tool_annotations.py +179 -0
- cairn_intel-0.6.1/tests/test_tools_graph_fallback.py +113 -0
- cairn_intel-0.6.1/tests/test_trace_flow.py +996 -0
- cairn_intel-0.6.1/tests/test_tree_sitter_parser_base.py +131 -0
- cairn_intel-0.6.1/tests/test_type_tier.py +210 -0
- cairn_intel-0.6.1/tests/test_uninstall_cmd.py +101 -0
- cairn_intel-0.6.1/tests/test_upgrade.py +188 -0
- cairn_intel-0.6.1/tests/test_workflow_audit_fixes.py +291 -0
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025–2026 Tan Le
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
cairn_intel-0.6.1/NOTICE
ADDED
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
cairn
|
|
2
|
+
Copyright (c) 2025–2026 Tan Le
|
|
3
|
+
|
|
4
|
+
Licensed under the MIT License; see LICENSE for full text.
|
|
5
|
+
|
|
6
|
+
This NOTICE file documents the third-party open-source software used by cairn.
|
|
7
|
+
cairn depends on these packages at runtime (resolved via pip/uv from PyPI) and
|
|
8
|
+
does not redistribute their source. Each package retains its own license; the
|
|
9
|
+
summaries below are for convenience and are not legal substitutes for the
|
|
10
|
+
upstream license texts.
|
|
11
|
+
|
|
12
|
+
================================================================================
|
|
13
|
+
Dependencies (by license family)
|
|
14
|
+
================================================================================
|
|
15
|
+
|
|
16
|
+
This product depends on software distributed under the following licenses. Each
|
|
17
|
+
entry lists the package and its declared license.
|
|
18
|
+
|
|
19
|
+
----------------------------------------
|
|
20
|
+
MIT License
|
|
21
|
+
----------------------------------------
|
|
22
|
+
annotated-types, anyio, attrs, build, h11, httpx-sse, iniconfig, jsonschema,
|
|
23
|
+
jsonschema-specifications, markdown-it-py, mcp, mdurl, pluggy, pydantic,
|
|
24
|
+
pydantic-settings, pydantic_core, PyJWT, pyproject_hooks, pytest,
|
|
25
|
+
referencing, rich, rpds-py, ruff, PyYAML, tree-sitter, tree-sitter-dart,
|
|
26
|
+
tree-sitter-go, tree-sitter-java, tree-sitter-javascript, tree-sitter-kotlin,
|
|
27
|
+
tree-sitter-objc, tree-sitter-python, tree-sitter-swift, tree-sitter-typescript,
|
|
28
|
+
typing-inspection, cffi (MIT-0)
|
|
29
|
+
|
|
30
|
+
----------------------------------------
|
|
31
|
+
BSD License (BSD-2-Clause / BSD-3-Clause)
|
|
32
|
+
----------------------------------------
|
|
33
|
+
click (BSD-3-Clause), httpcore (BSD-3-Clause), httpx (BSD-3-Clause),
|
|
34
|
+
idna (BSD-3-Clause), pycparser (BSD-3-Clause), Pygments (BSD-2-Clause),
|
|
35
|
+
python-dotenv (BSD-3-Clause), sse-starlette (BSD-3-Clause),
|
|
36
|
+
starlette (BSD-3-Clause), uvicorn (BSD-3-Clause)
|
|
37
|
+
|
|
38
|
+
----------------------------------------
|
|
39
|
+
Apache License 2.0
|
|
40
|
+
----------------------------------------
|
|
41
|
+
python-multipart (Apache-2.0), watchdog (Apache-2.0)
|
|
42
|
+
|
|
43
|
+
----------------------------------------
|
|
44
|
+
Dual: Apache License 2.0 OR BSD
|
|
45
|
+
----------------------------------------
|
|
46
|
+
cryptography (Apache-2.0 OR BSD-3-Clause)
|
|
47
|
+
packaging (Apache-2.0 OR BSD-2-Clause)
|
|
48
|
+
|
|
49
|
+
----------------------------------------
|
|
50
|
+
Mozilla Public License 2.0 (MPL-2.0)
|
|
51
|
+
----------------------------------------
|
|
52
|
+
certifi, pathspec
|
|
53
|
+
Note: MPL-2.0 is file-level weak copyleft. It is satisfied by keeping the
|
|
54
|
+
MPL-licensed files' source and notice available (they remain in the upstream
|
|
55
|
+
PyPI packages). cairn does not copy or vendor these files into its source
|
|
56
|
+
tree, so no additional obligation attaches to distributing cairn itself.
|
|
57
|
+
|
|
58
|
+
----------------------------------------
|
|
59
|
+
Python Software Foundation License (PSF-2.0)
|
|
60
|
+
----------------------------------------
|
|
61
|
+
typing_extensions
|
|
62
|
+
|
|
63
|
+
----------------------------------------
|
|
64
|
+
Dual: MIT License OR Apache License 2.0
|
|
65
|
+
----------------------------------------
|
|
66
|
+
sqlite-vec
|
|
67
|
+
|
|
68
|
+
================================================================================
|
|
69
|
+
Optional extras
|
|
70
|
+
================================================================================
|
|
71
|
+
|
|
72
|
+
The `[semantic]` extra (sentence-transformers, numpy) is not installed by
|
|
73
|
+
default. On Linux it additionally pulls torch and its transitive NVIDIA CUDA
|
|
74
|
+
runtime packages (e.g. nvidia-cublas, nvidia-cudnn, nvidia-cufft, triton),
|
|
75
|
+
which are governed by NVIDIA's CUDA EULA / Apache-2.0 and torch's BSD-style
|
|
76
|
+
license. These are resolved and accepted by the end user; cairn does not
|
|
77
|
+
bundle or redistribute them.
|
|
78
|
+
|
|
79
|
+
The embedding model `BAAI/bge-m3` (referenced by name, downloaded on demand
|
|
80
|
+
to ~/.cairn/lib/ when a user runs `cg embed --install-deps`) is released
|
|
81
|
+
under the MIT License on Hugging Face. cairn does not redistribute the
|
|
82
|
+
model weights.
|
|
@@ -0,0 +1,310 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: cairn-intel
|
|
3
|
+
Version: 0.6.1
|
|
4
|
+
Summary: Local codebase intelligence system: structural graph + compass + wiki + agent memory
|
|
5
|
+
Author: Tan Le
|
|
6
|
+
License-Expression: MIT
|
|
7
|
+
Project-URL: Homepage, https://github.com/tanlnm512/cairn
|
|
8
|
+
Keywords: code-intelligence,tree-sitter,mcp,knowledge-graph,code-graph
|
|
9
|
+
Classifier: Development Status :: 4 - Beta
|
|
10
|
+
Classifier: Intended Audience :: Developers
|
|
11
|
+
Classifier: Programming Language :: Python :: 3
|
|
12
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
13
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
14
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
15
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
17
|
+
Classifier: Topic :: Software Development
|
|
18
|
+
Classifier: Topic :: Software Development :: Libraries
|
|
19
|
+
Requires-Python: >=3.10
|
|
20
|
+
Description-Content-Type: text/markdown
|
|
21
|
+
License-File: LICENSE
|
|
22
|
+
License-File: NOTICE
|
|
23
|
+
Requires-Dist: tree-sitter==0.26.0
|
|
24
|
+
Requires-Dist: tree-sitter-kotlin==1.1.0
|
|
25
|
+
Requires-Dist: tree-sitter-java==0.23.5
|
|
26
|
+
Requires-Dist: tree-sitter-python==0.23.6
|
|
27
|
+
Requires-Dist: tree-sitter-swift==0.7.3
|
|
28
|
+
Requires-Dist: tree-sitter-typescript==0.23.2
|
|
29
|
+
Requires-Dist: tree-sitter-javascript==0.23.0
|
|
30
|
+
Requires-Dist: tree-sitter-dart==0.1.0
|
|
31
|
+
Requires-Dist: tree-sitter-objc==3.0.2
|
|
32
|
+
Requires-Dist: tree-sitter-go==0.25.0
|
|
33
|
+
Requires-Dist: click>=8.0
|
|
34
|
+
Requires-Dist: pyyaml>=6.0
|
|
35
|
+
Requires-Dist: mcp<2.0.0,>=0.9.0
|
|
36
|
+
Requires-Dist: pydantic>=2.0
|
|
37
|
+
Requires-Dist: pathspec>=0.12
|
|
38
|
+
Requires-Dist: packaging>=21.0
|
|
39
|
+
Requires-Dist: sqlite-vec>=0.1.0
|
|
40
|
+
Requires-Dist: rich>=13.0
|
|
41
|
+
Requires-Dist: questionary>=2.0
|
|
42
|
+
Provides-Extra: watch
|
|
43
|
+
Requires-Dist: watchdog>=3.0; extra == "watch"
|
|
44
|
+
Provides-Extra: test
|
|
45
|
+
Requires-Dist: pytest>=7.0; extra == "test"
|
|
46
|
+
Provides-Extra: dev
|
|
47
|
+
Requires-Dist: pytest>=7.0; extra == "dev"
|
|
48
|
+
Requires-Dist: watchdog>=3.0; extra == "dev"
|
|
49
|
+
Requires-Dist: build; extra == "dev"
|
|
50
|
+
Requires-Dist: ruff>=0.6; extra == "dev"
|
|
51
|
+
Requires-Dist: grpcio-tools>=1.60; extra == "dev"
|
|
52
|
+
Provides-Extra: semantic
|
|
53
|
+
Requires-Dist: sentence-transformers>=3.0; extra == "semantic"
|
|
54
|
+
Requires-Dist: numpy>=1.24; extra == "semantic"
|
|
55
|
+
Provides-Extra: ann
|
|
56
|
+
Requires-Dist: sqlite-vec>=0.1.0; extra == "ann"
|
|
57
|
+
Provides-Extra: scip
|
|
58
|
+
Requires-Dist: protobuf>=7.35.1; extra == "scip"
|
|
59
|
+
Dynamic: license-file
|
|
60
|
+
|
|
61
|
+
# cairn
|
|
62
|
+
|
|
63
|
+
> Local codebase intelligence system: structural graph + compass + wiki + agent memory.
|
|
64
|
+
|
|
65
|
+
[](https://pypi.org/project/cairn-intel/)
|
|
66
|
+
[](LICENSE)
|
|
67
|
+
[](https://pypi.org/project/cairn-intel/)
|
|
68
|
+
[](https://github.com/tanlnm512/cairn/actions/workflows/ci.yml)
|
|
69
|
+
|
|
70
|
+
cairn builds a precise, language-aware structural graph of your codebase and
|
|
71
|
+
exposes it to both humans (the `cairn` CLI) and AI agents (a stdio MCP server with
|
|
72
|
+
27 tools). Symbols, call edges, definitions, blast radius, and tribal memory all
|
|
73
|
+
live in a local SQLite store — no network call, no torch in the default install.
|
|
74
|
+
|
|
75
|
+
## What is cairn?
|
|
76
|
+
|
|
77
|
+
cairn is a **local** codebase intelligence system. It parses your repos with
|
|
78
|
+
tree-sitter into a **structural graph** (definitions, call edges, cross-repo
|
|
79
|
+
dependencies) stored in SQLite, then layers a **compass** (per-module navigation
|
|
80
|
+
guides), a **wiki** (architecture docs), **memory** (decisions / patterns /
|
|
81
|
+
mistakes / workarounds), and a **knowledge** store on top. It is **MCP-native**:
|
|
82
|
+
the same store backs the `cairn` CLI and a 27-tool MCP server, making it
|
|
83
|
+
**agent-first** — your coding agents query one local source of truth instead of
|
|
84
|
+
re-reading the whole repo every turn.
|
|
85
|
+
|
|
86
|
+
## Why cairn? Resolution-labeled edges
|
|
87
|
+
|
|
88
|
+
Every code graph can tell you "who calls this." cairn is the one that tells
|
|
89
|
+
you **whether to trust the answer.** The resolver labels each call edge:
|
|
90
|
+
|
|
91
|
+
- **`exact`** — pinned to one definition. Trusted.
|
|
92
|
+
- **`ambiguous`** — multiple candidates; the resolver declined to guess.
|
|
93
|
+
- **`unresolved`** — external or stdlib.
|
|
94
|
+
|
|
95
|
+
Graph tools default to **precise mode** — they follow *only* `exact` edges. So
|
|
96
|
+
blast radius is **never inflated by name collisions**. A common name like
|
|
97
|
+
`invoke` can have hundreds of call sites across a polyglot repo that merely
|
|
98
|
+
share the name; precise mode returns only the real callers, while **fuzzy mode**
|
|
99
|
+
(`--fuzzy` / `fuzzy=True`) adds the name-only matches as an explicitly-labelled
|
|
100
|
+
candidate list to verify.
|
|
101
|
+
|
|
102
|
+
```bash
|
|
103
|
+
cairn impact invoke # precise (default): real callers only — ground truth
|
|
104
|
+
cairn impact invoke --fuzzy # candidate list (name matches), each labelled unverified
|
|
105
|
+
```
|
|
106
|
+
|
|
107
|
+
An empty precise result means "no *resolvable* callers," **not** "unused" —
|
|
108
|
+
retry with `--fuzzy` before concluding a symbol is dead. And `explore` surfaces
|
|
109
|
+
`ambiguous` dispatch hops — polymorphism that grep fundamentally cannot see.
|
|
110
|
+
|
|
111
|
+
This is measurable: see [docs/benchmarks.md](docs/benchmarks.md#the-resolution-label-methodology-cairns-differentiator)
|
|
112
|
+
for the precise-vs-fuzzy false-positive methodology, and
|
|
113
|
+
[docs/examples/resolution-walkthrough.md](docs/examples/resolution-walkthrough.md)
|
|
114
|
+
for a worked example. Full design at
|
|
115
|
+
[docs/architecture.md § Resolution model](docs/architecture.md#resolution-model).
|
|
116
|
+
|
|
117
|
+
## Quick start
|
|
118
|
+
|
|
119
|
+
```bash
|
|
120
|
+
pip install cairn-intel # install from PyPI (the recommended path)
|
|
121
|
+
cairn build # parse the workspace and build the graph (first run)
|
|
122
|
+
cairn update # incremental reindex after the first build
|
|
123
|
+
cairn def SomeSymbol # find where a symbol is defined
|
|
124
|
+
cairn ask "how does auth work" # natural-language query across all layers
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
The graph lives under `~/.cairn` by default (override with `CAIRN_HOME`).
|
|
128
|
+
|
|
129
|
+
> **First run vs later runs.** `cairn build` parses every file from scratch.
|
|
130
|
+
> `cairn update` reindexes only what changed since the last build (via `git diff
|
|
131
|
+
> HEAD` plus the existing graph) — so on a fresh clone with a clean working tree,
|
|
132
|
+
> use `cairn build` first, since `cairn update` would see no changes.
|
|
133
|
+
|
|
134
|
+
## Upgrading
|
|
135
|
+
|
|
136
|
+
cairn can update itself in place — it detects how it was installed
|
|
137
|
+
(`uv tool`, `pipx`, or `pip`) and re-installs the latest version from PyPI:
|
|
138
|
+
|
|
139
|
+
```bash
|
|
140
|
+
cairn upgrade # update to the latest published version
|
|
141
|
+
cairn upgrade --check # only check what's latest, don't change anything
|
|
142
|
+
cairn version # print the installed version
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
If PyPI is unreachable, `cairn upgrade` prints the manual command instead.
|
|
146
|
+
|
|
147
|
+
## Install for AI agents
|
|
148
|
+
|
|
149
|
+
cairn ships a stdio MCP server (`cairn serve`). To wire it into your AI coding
|
|
150
|
+
clients (Claude Code, Cursor, Droid, ZCode, Claude Desktop, agy, opencode):
|
|
151
|
+
|
|
152
|
+
```bash
|
|
153
|
+
cairn install-agents
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
This detects which clients are installed, shows whether cairn is already
|
|
157
|
+
wired in, and interactively prompts you to choose:
|
|
158
|
+
|
|
159
|
+
```
|
|
160
|
+
Client detection:
|
|
161
|
+
[✓] claude claude CLI on PATH cairn: [ ] not installed
|
|
162
|
+
[✓] cursor Cursor.app in /Applications cairn: [ ] not installed
|
|
163
|
+
[✓] zcode ~/.zcode exists cairn: [✓] installed
|
|
164
|
+
|
|
165
|
+
Install cairn for which clients?
|
|
166
|
+
Clients [claude,cursor]:
|
|
167
|
+
|
|
168
|
+
Config scope:
|
|
169
|
+
workspace — write to ./.claude/, ./.cursor/ etc. (per-project)
|
|
170
|
+
global — write to ~/.claude/, ~/.cursor/ etc. (all projects inherit)
|
|
171
|
+
Scope [workspace]:
|
|
172
|
+
```
|
|
173
|
+
|
|
174
|
+
**Scope:** `workspace` (default) writes configs to the current project dir
|
|
175
|
+
(`./.claude/`, `./.cursor/`); `global` writes to your home dir (`~/.claude/`,
|
|
176
|
+
`~/.cursor/`) so all projects inherit cairn without per-project setup.
|
|
177
|
+
|
|
178
|
+
Non-interactive flags for scripts/CI:
|
|
179
|
+
|
|
180
|
+
```bash
|
|
181
|
+
cairn install-agents --yes # auto-install detected-not-installed
|
|
182
|
+
cairn install-agents --client claude --client cursor # force specific clients
|
|
183
|
+
cairn install-agents --scope global # write to ~/.claude/ etc.
|
|
184
|
+
cairn install-agents --force # overwrite existing files
|
|
185
|
+
cairn install-agents --dry-run # preview without writing
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
Or wire manually — the MCP config is:
|
|
189
|
+
|
|
190
|
+
```json
|
|
191
|
+
{
|
|
192
|
+
"mcpServers": {
|
|
193
|
+
"cairn": {
|
|
194
|
+
"command": "cairn",
|
|
195
|
+
"args": ["serve"]
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
The recommended first call from an agent is `explore(query)`, which returns
|
|
202
|
+
matching symbols' verbatim source, the call paths between them, and a
|
|
203
|
+
blast-radius summary in a single round trip.
|
|
204
|
+
|
|
205
|
+
## Supported languages
|
|
206
|
+
|
|
207
|
+
Kotlin, Java, Python, Swift, TypeScript, JavaScript, Dart, Objective-C, Go
|
|
208
|
+
|
|
209
|
+
## Optional features
|
|
210
|
+
|
|
211
|
+
The default install is dependency-light and network-free. Opt in with extras:
|
|
212
|
+
|
|
213
|
+
| Extra | Adds | Key env var |
|
|
214
|
+
|-------|------|-------------|
|
|
215
|
+
| `[semantic]` | `sentence-transformers` + `numpy` — real embeddings and CrossEncoder reranking | `CAIRN_RERANK=1`; fusion is governed by `CAIRN_FUSION` (default on) |
|
|
216
|
+
| `[ann]` | `sqlite-vec` — native approximate-nearest-neighbour index for large corpora | `CAIRN_ANN_BACKEND=sqlite-vec` |
|
|
217
|
+
| `[scip]` | `protobuf` — consume pre-built [SCIP](docs/scip.md) indexes for compiler-grade exact call edges (Kotlin/Java/Swift/TypeScript) alongside tree-sitter | declare indexes in `cairn.json` under `scip` |
|
|
218
|
+
| `[watch]` | `watchdog` — live graph rebuilds on filesystem change | — |
|
|
219
|
+
|
|
220
|
+
## Architecture (5 layers)
|
|
221
|
+
|
|
222
|
+
The MCP server exposes 27 tools across five layers:
|
|
223
|
+
|
|
224
|
+
| Layer | Purpose |
|
|
225
|
+
|-------|---------|
|
|
226
|
+
| **graph** (9 tools) | Structural graph: `find_definition`, `get_callers` / `get_callees`, `impact_analysis`, `cross_repo_deps`, `semantic_search`, `search_symbols`, `explore` (the graph aggregator and recommended first call), and `visualize_graph` |
|
|
227
|
+
| **compass + knowledge base** (5 tools) | `get_compass`, `search_knowledge`, `ask_compass` (cross-layer router), `trace_flow`, `generate_flow` |
|
|
228
|
+
| **memory** (8 tools) | Tribal memory: recall / record / lifecycle (promote, demote, evolve, decay, delete, digest) |
|
|
229
|
+
| **knowledge** (5 tools) | The OKF knowledge store — add / search / status business docs and workflows |
|
|
230
|
+
|
|
231
|
+
## CLI
|
|
232
|
+
|
|
233
|
+
The `cairn` command groups the main functionality. Run `cairn --help`
|
|
234
|
+
(or `cairn <group> --help`) for the authoritative, full list.
|
|
235
|
+
|
|
236
|
+
| Command | What it does |
|
|
237
|
+
|---------|--------------|
|
|
238
|
+
| `cairn serve` | Run the stdio MCP server |
|
|
239
|
+
| `cairn build` | Parse the workspace and build the graph (full; first run) |
|
|
240
|
+
| `cairn update` | Incremental reindex of changed files (after the first build) |
|
|
241
|
+
| `cairn def <symbol>` | Find a symbol's definition |
|
|
242
|
+
| `cairn impact <symbol>` | Within-repo blast radius (precise by default; `--fuzzy` to audit) |
|
|
243
|
+
| `cairn ask "<question>"` | Natural-language query routed across all layers |
|
|
244
|
+
| `cairn context <file>` | Load compass + memory + wiki context for a file |
|
|
245
|
+
| `cairn memory …` | Record / list / search tribal memory |
|
|
246
|
+
| `cairn task …` | Optional LLM task queue (`list` / `show` / `claim` / `complete`) |
|
|
247
|
+
| `cairn knowledge …` | Inspect and export the knowledge store |
|
|
248
|
+
| `cairn compass …` | Generate / list / validate module compass guides |
|
|
249
|
+
| `cairn wiki …` | Generate / search the architecture wiki |
|
|
250
|
+
| `cairn install-agents` | Drop integration files into supported AI agents |
|
|
251
|
+
| `cairn upgrade` | Update cairn in place from PyPI (detects install method; `--check` to preview) |
|
|
252
|
+
| `cairn bench` | Performance / scalability benchmarks (`--save`/`--compare` for regression checks) |
|
|
253
|
+
|
|
254
|
+
## Development
|
|
255
|
+
|
|
256
|
+
```bash
|
|
257
|
+
pip install -e ".[dev]" # pytest + watchdog + build
|
|
258
|
+
pytest -m core # fast <3s smoke subset (one test per core function)
|
|
259
|
+
```
|
|
260
|
+
|
|
261
|
+
## Semantic search
|
|
262
|
+
|
|
263
|
+
The default install is network- and torch-free. Semantic search deps
|
|
264
|
+
(torch + sentence-transformers) are a one-time separate download that
|
|
265
|
+
persists in `~/.cairn/lib/` (survives reinstalls):
|
|
266
|
+
|
|
267
|
+
```bash
|
|
268
|
+
cairn embed --install-deps # one-time: downloads bge-m3 (~836 MB)
|
|
269
|
+
cairn embed # builds the embedding index
|
|
270
|
+
```
|
|
271
|
+
|
|
272
|
+
## Development
|
|
273
|
+
|
|
274
|
+
cairn is developed on GitHub and released to PyPI. The recommended install
|
|
275
|
+
for end users is `pip install cairn-intel` (see Quick start above). The
|
|
276
|
+
following is for contributors only:
|
|
277
|
+
|
|
278
|
+
```bash
|
|
279
|
+
pip install -e ".[dev]" # editable install: pytest + watchdog + build + ruff
|
|
280
|
+
pytest -m core # fast <3s smoke subset (one test per core function)
|
|
281
|
+
pytest # full suite (the CI path)
|
|
282
|
+
make dist # build wheel + sdist into dist/ (for releases)
|
|
283
|
+
```
|
|
284
|
+
|
|
285
|
+
Releases are cut by tagging `vX.Y.Z` — see the tag-triggered workflow in
|
|
286
|
+
`.github/workflows/release.yml` and the pre-release checklist in
|
|
287
|
+
`docs/release-checklist.md`.
|
|
288
|
+
|
|
289
|
+
## Dependency licenses
|
|
290
|
+
|
|
291
|
+
cairn is MIT-licensed. Its dependencies are all permissive (MIT, BSD,
|
|
292
|
+
Apache-2.0, MPL-2.0, PSF); see [NOTICE](NOTICE) for the full list.
|
|
293
|
+
|
|
294
|
+
The optional `[semantic]` extra is not installed by default. If you opt into it
|
|
295
|
+
on Linux, `pip` resolves `torch` and its transitive NVIDIA CUDA runtime
|
|
296
|
+
packages, which carry their own licenses (torch: BSD; NVIDIA CUDA components:
|
|
297
|
+
NVIDIA EULA / Apache-2.0). The embedding model `BAAI/bge-m3` (MIT) is
|
|
298
|
+
downloaded on demand to `~/.cairn/lib/` and is not redistributed with cairn.
|
|
299
|
+
None of these are bundled with cairn — they are resolved and accepted by the
|
|
300
|
+
end user at install time.
|
|
301
|
+
|
|
302
|
+
## Status
|
|
303
|
+
|
|
304
|
+
**Beta — pre-1.0 (v0.6.1).** Public surfaces (CLI flags, MCP tool shapes,
|
|
305
|
+
knowledge-file layout) may still shift before 1.0. Feedback welcome via
|
|
306
|
+
[GitHub issues](https://github.com/tanlnm512/cairn/issues).
|
|
307
|
+
|
|
308
|
+
## License
|
|
309
|
+
|
|
310
|
+
[MIT](LICENSE) — © 2025–2026 Tan Le
|
|
@@ -0,0 +1,250 @@
|
|
|
1
|
+
# cairn
|
|
2
|
+
|
|
3
|
+
> Local codebase intelligence system: structural graph + compass + wiki + agent memory.
|
|
4
|
+
|
|
5
|
+
[](https://pypi.org/project/cairn-intel/)
|
|
6
|
+
[](LICENSE)
|
|
7
|
+
[](https://pypi.org/project/cairn-intel/)
|
|
8
|
+
[](https://github.com/tanlnm512/cairn/actions/workflows/ci.yml)
|
|
9
|
+
|
|
10
|
+
cairn builds a precise, language-aware structural graph of your codebase and
|
|
11
|
+
exposes it to both humans (the `cairn` CLI) and AI agents (a stdio MCP server with
|
|
12
|
+
27 tools). Symbols, call edges, definitions, blast radius, and tribal memory all
|
|
13
|
+
live in a local SQLite store — no network call, no torch in the default install.
|
|
14
|
+
|
|
15
|
+
## What is cairn?
|
|
16
|
+
|
|
17
|
+
cairn is a **local** codebase intelligence system. It parses your repos with
|
|
18
|
+
tree-sitter into a **structural graph** (definitions, call edges, cross-repo
|
|
19
|
+
dependencies) stored in SQLite, then layers a **compass** (per-module navigation
|
|
20
|
+
guides), a **wiki** (architecture docs), **memory** (decisions / patterns /
|
|
21
|
+
mistakes / workarounds), and a **knowledge** store on top. It is **MCP-native**:
|
|
22
|
+
the same store backs the `cairn` CLI and a 27-tool MCP server, making it
|
|
23
|
+
**agent-first** — your coding agents query one local source of truth instead of
|
|
24
|
+
re-reading the whole repo every turn.
|
|
25
|
+
|
|
26
|
+
## Why cairn? Resolution-labeled edges
|
|
27
|
+
|
|
28
|
+
Every code graph can tell you "who calls this." cairn is the one that tells
|
|
29
|
+
you **whether to trust the answer.** The resolver labels each call edge:
|
|
30
|
+
|
|
31
|
+
- **`exact`** — pinned to one definition. Trusted.
|
|
32
|
+
- **`ambiguous`** — multiple candidates; the resolver declined to guess.
|
|
33
|
+
- **`unresolved`** — external or stdlib.
|
|
34
|
+
|
|
35
|
+
Graph tools default to **precise mode** — they follow *only* `exact` edges. So
|
|
36
|
+
blast radius is **never inflated by name collisions**. A common name like
|
|
37
|
+
`invoke` can have hundreds of call sites across a polyglot repo that merely
|
|
38
|
+
share the name; precise mode returns only the real callers, while **fuzzy mode**
|
|
39
|
+
(`--fuzzy` / `fuzzy=True`) adds the name-only matches as an explicitly-labelled
|
|
40
|
+
candidate list to verify.
|
|
41
|
+
|
|
42
|
+
```bash
|
|
43
|
+
cairn impact invoke # precise (default): real callers only — ground truth
|
|
44
|
+
cairn impact invoke --fuzzy # candidate list (name matches), each labelled unverified
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
An empty precise result means "no *resolvable* callers," **not** "unused" —
|
|
48
|
+
retry with `--fuzzy` before concluding a symbol is dead. And `explore` surfaces
|
|
49
|
+
`ambiguous` dispatch hops — polymorphism that grep fundamentally cannot see.
|
|
50
|
+
|
|
51
|
+
This is measurable: see [docs/benchmarks.md](docs/benchmarks.md#the-resolution-label-methodology-cairns-differentiator)
|
|
52
|
+
for the precise-vs-fuzzy false-positive methodology, and
|
|
53
|
+
[docs/examples/resolution-walkthrough.md](docs/examples/resolution-walkthrough.md)
|
|
54
|
+
for a worked example. Full design at
|
|
55
|
+
[docs/architecture.md § Resolution model](docs/architecture.md#resolution-model).
|
|
56
|
+
|
|
57
|
+
## Quick start
|
|
58
|
+
|
|
59
|
+
```bash
|
|
60
|
+
pip install cairn-intel # install from PyPI (the recommended path)
|
|
61
|
+
cairn build # parse the workspace and build the graph (first run)
|
|
62
|
+
cairn update # incremental reindex after the first build
|
|
63
|
+
cairn def SomeSymbol # find where a symbol is defined
|
|
64
|
+
cairn ask "how does auth work" # natural-language query across all layers
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
The graph lives under `~/.cairn` by default (override with `CAIRN_HOME`).
|
|
68
|
+
|
|
69
|
+
> **First run vs later runs.** `cairn build` parses every file from scratch.
|
|
70
|
+
> `cairn update` reindexes only what changed since the last build (via `git diff
|
|
71
|
+
> HEAD` plus the existing graph) — so on a fresh clone with a clean working tree,
|
|
72
|
+
> use `cairn build` first, since `cairn update` would see no changes.
|
|
73
|
+
|
|
74
|
+
## Upgrading
|
|
75
|
+
|
|
76
|
+
cairn can update itself in place — it detects how it was installed
|
|
77
|
+
(`uv tool`, `pipx`, or `pip`) and re-installs the latest version from PyPI:
|
|
78
|
+
|
|
79
|
+
```bash
|
|
80
|
+
cairn upgrade # update to the latest published version
|
|
81
|
+
cairn upgrade --check # only check what's latest, don't change anything
|
|
82
|
+
cairn version # print the installed version
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
If PyPI is unreachable, `cairn upgrade` prints the manual command instead.
|
|
86
|
+
|
|
87
|
+
## Install for AI agents
|
|
88
|
+
|
|
89
|
+
cairn ships a stdio MCP server (`cairn serve`). To wire it into your AI coding
|
|
90
|
+
clients (Claude Code, Cursor, Droid, ZCode, Claude Desktop, agy, opencode):
|
|
91
|
+
|
|
92
|
+
```bash
|
|
93
|
+
cairn install-agents
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
This detects which clients are installed, shows whether cairn is already
|
|
97
|
+
wired in, and interactively prompts you to choose:
|
|
98
|
+
|
|
99
|
+
```
|
|
100
|
+
Client detection:
|
|
101
|
+
[✓] claude claude CLI on PATH cairn: [ ] not installed
|
|
102
|
+
[✓] cursor Cursor.app in /Applications cairn: [ ] not installed
|
|
103
|
+
[✓] zcode ~/.zcode exists cairn: [✓] installed
|
|
104
|
+
|
|
105
|
+
Install cairn for which clients?
|
|
106
|
+
Clients [claude,cursor]:
|
|
107
|
+
|
|
108
|
+
Config scope:
|
|
109
|
+
workspace — write to ./.claude/, ./.cursor/ etc. (per-project)
|
|
110
|
+
global — write to ~/.claude/, ~/.cursor/ etc. (all projects inherit)
|
|
111
|
+
Scope [workspace]:
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
**Scope:** `workspace` (default) writes configs to the current project dir
|
|
115
|
+
(`./.claude/`, `./.cursor/`); `global` writes to your home dir (`~/.claude/`,
|
|
116
|
+
`~/.cursor/`) so all projects inherit cairn without per-project setup.
|
|
117
|
+
|
|
118
|
+
Non-interactive flags for scripts/CI:
|
|
119
|
+
|
|
120
|
+
```bash
|
|
121
|
+
cairn install-agents --yes # auto-install detected-not-installed
|
|
122
|
+
cairn install-agents --client claude --client cursor # force specific clients
|
|
123
|
+
cairn install-agents --scope global # write to ~/.claude/ etc.
|
|
124
|
+
cairn install-agents --force # overwrite existing files
|
|
125
|
+
cairn install-agents --dry-run # preview without writing
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
Or wire manually — the MCP config is:
|
|
129
|
+
|
|
130
|
+
```json
|
|
131
|
+
{
|
|
132
|
+
"mcpServers": {
|
|
133
|
+
"cairn": {
|
|
134
|
+
"command": "cairn",
|
|
135
|
+
"args": ["serve"]
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
```
|
|
140
|
+
|
|
141
|
+
The recommended first call from an agent is `explore(query)`, which returns
|
|
142
|
+
matching symbols' verbatim source, the call paths between them, and a
|
|
143
|
+
blast-radius summary in a single round trip.
|
|
144
|
+
|
|
145
|
+
## Supported languages
|
|
146
|
+
|
|
147
|
+
Kotlin, Java, Python, Swift, TypeScript, JavaScript, Dart, Objective-C, Go
|
|
148
|
+
|
|
149
|
+
## Optional features
|
|
150
|
+
|
|
151
|
+
The default install is dependency-light and network-free. Opt in with extras:
|
|
152
|
+
|
|
153
|
+
| Extra | Adds | Key env var |
|
|
154
|
+
|-------|------|-------------|
|
|
155
|
+
| `[semantic]` | `sentence-transformers` + `numpy` — real embeddings and CrossEncoder reranking | `CAIRN_RERANK=1`; fusion is governed by `CAIRN_FUSION` (default on) |
|
|
156
|
+
| `[ann]` | `sqlite-vec` — native approximate-nearest-neighbour index for large corpora | `CAIRN_ANN_BACKEND=sqlite-vec` |
|
|
157
|
+
| `[scip]` | `protobuf` — consume pre-built [SCIP](docs/scip.md) indexes for compiler-grade exact call edges (Kotlin/Java/Swift/TypeScript) alongside tree-sitter | declare indexes in `cairn.json` under `scip` |
|
|
158
|
+
| `[watch]` | `watchdog` — live graph rebuilds on filesystem change | — |
|
|
159
|
+
|
|
160
|
+
## Architecture (5 layers)
|
|
161
|
+
|
|
162
|
+
The MCP server exposes 27 tools across five layers:
|
|
163
|
+
|
|
164
|
+
| Layer | Purpose |
|
|
165
|
+
|-------|---------|
|
|
166
|
+
| **graph** (9 tools) | Structural graph: `find_definition`, `get_callers` / `get_callees`, `impact_analysis`, `cross_repo_deps`, `semantic_search`, `search_symbols`, `explore` (the graph aggregator and recommended first call), and `visualize_graph` |
|
|
167
|
+
| **compass + knowledge base** (5 tools) | `get_compass`, `search_knowledge`, `ask_compass` (cross-layer router), `trace_flow`, `generate_flow` |
|
|
168
|
+
| **memory** (8 tools) | Tribal memory: recall / record / lifecycle (promote, demote, evolve, decay, delete, digest) |
|
|
169
|
+
| **knowledge** (5 tools) | The OKF knowledge store — add / search / status business docs and workflows |
|
|
170
|
+
|
|
171
|
+
## CLI
|
|
172
|
+
|
|
173
|
+
The `cairn` command groups the main functionality. Run `cairn --help`
|
|
174
|
+
(or `cairn <group> --help`) for the authoritative, full list.
|
|
175
|
+
|
|
176
|
+
| Command | What it does |
|
|
177
|
+
|---------|--------------|
|
|
178
|
+
| `cairn serve` | Run the stdio MCP server |
|
|
179
|
+
| `cairn build` | Parse the workspace and build the graph (full; first run) |
|
|
180
|
+
| `cairn update` | Incremental reindex of changed files (after the first build) |
|
|
181
|
+
| `cairn def <symbol>` | Find a symbol's definition |
|
|
182
|
+
| `cairn impact <symbol>` | Within-repo blast radius (precise by default; `--fuzzy` to audit) |
|
|
183
|
+
| `cairn ask "<question>"` | Natural-language query routed across all layers |
|
|
184
|
+
| `cairn context <file>` | Load compass + memory + wiki context for a file |
|
|
185
|
+
| `cairn memory …` | Record / list / search tribal memory |
|
|
186
|
+
| `cairn task …` | Optional LLM task queue (`list` / `show` / `claim` / `complete`) |
|
|
187
|
+
| `cairn knowledge …` | Inspect and export the knowledge store |
|
|
188
|
+
| `cairn compass …` | Generate / list / validate module compass guides |
|
|
189
|
+
| `cairn wiki …` | Generate / search the architecture wiki |
|
|
190
|
+
| `cairn install-agents` | Drop integration files into supported AI agents |
|
|
191
|
+
| `cairn upgrade` | Update cairn in place from PyPI (detects install method; `--check` to preview) |
|
|
192
|
+
| `cairn bench` | Performance / scalability benchmarks (`--save`/`--compare` for regression checks) |
|
|
193
|
+
|
|
194
|
+
## Development
|
|
195
|
+
|
|
196
|
+
```bash
|
|
197
|
+
pip install -e ".[dev]" # pytest + watchdog + build
|
|
198
|
+
pytest -m core # fast <3s smoke subset (one test per core function)
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
## Semantic search
|
|
202
|
+
|
|
203
|
+
The default install is network- and torch-free. Semantic search deps
|
|
204
|
+
(torch + sentence-transformers) are a one-time separate download that
|
|
205
|
+
persists in `~/.cairn/lib/` (survives reinstalls):
|
|
206
|
+
|
|
207
|
+
```bash
|
|
208
|
+
cairn embed --install-deps # one-time: downloads bge-m3 (~836 MB)
|
|
209
|
+
cairn embed # builds the embedding index
|
|
210
|
+
```
|
|
211
|
+
|
|
212
|
+
## Development
|
|
213
|
+
|
|
214
|
+
cairn is developed on GitHub and released to PyPI. The recommended install
|
|
215
|
+
for end users is `pip install cairn-intel` (see Quick start above). The
|
|
216
|
+
following is for contributors only:
|
|
217
|
+
|
|
218
|
+
```bash
|
|
219
|
+
pip install -e ".[dev]" # editable install: pytest + watchdog + build + ruff
|
|
220
|
+
pytest -m core # fast <3s smoke subset (one test per core function)
|
|
221
|
+
pytest # full suite (the CI path)
|
|
222
|
+
make dist # build wheel + sdist into dist/ (for releases)
|
|
223
|
+
```
|
|
224
|
+
|
|
225
|
+
Releases are cut by tagging `vX.Y.Z` — see the tag-triggered workflow in
|
|
226
|
+
`.github/workflows/release.yml` and the pre-release checklist in
|
|
227
|
+
`docs/release-checklist.md`.
|
|
228
|
+
|
|
229
|
+
## Dependency licenses
|
|
230
|
+
|
|
231
|
+
cairn is MIT-licensed. Its dependencies are all permissive (MIT, BSD,
|
|
232
|
+
Apache-2.0, MPL-2.0, PSF); see [NOTICE](NOTICE) for the full list.
|
|
233
|
+
|
|
234
|
+
The optional `[semantic]` extra is not installed by default. If you opt into it
|
|
235
|
+
on Linux, `pip` resolves `torch` and its transitive NVIDIA CUDA runtime
|
|
236
|
+
packages, which carry their own licenses (torch: BSD; NVIDIA CUDA components:
|
|
237
|
+
NVIDIA EULA / Apache-2.0). The embedding model `BAAI/bge-m3` (MIT) is
|
|
238
|
+
downloaded on demand to `~/.cairn/lib/` and is not redistributed with cairn.
|
|
239
|
+
None of these are bundled with cairn — they are resolved and accepted by the
|
|
240
|
+
end user at install time.
|
|
241
|
+
|
|
242
|
+
## Status
|
|
243
|
+
|
|
244
|
+
**Beta — pre-1.0 (v0.6.1).** Public surfaces (CLI flags, MCP tool shapes,
|
|
245
|
+
knowledge-file layout) may still shift before 1.0. Feedback welcome via
|
|
246
|
+
[GitHub issues](https://github.com/tanlnm512/cairn/issues).
|
|
247
|
+
|
|
248
|
+
## License
|
|
249
|
+
|
|
250
|
+
[MIT](LICENSE) — © 2025–2026 Tan Le
|