{"id":48752116,"url":"https://github.com/zzet/gortex","last_synced_at":"2026-04-27T23:01:02.148Z","repository":{"id":349559649,"uuid":"1202875287","full_name":"zzet/gortex","owner":"zzet","description":"High-performance code intelligence engine that indexes repositories into an in-memory knowledge graph and exposes it via CLI, MCP Server, and web UI.  Built for AI coding agents - expose only needed information - one get_editing_context call replaces 5-10 file reads, cutting token usage by ~94%.","archived":false,"fork":false,"pushed_at":"2026-04-25T00:24:34.000Z","size":14912,"stargazers_count":22,"open_issues_count":1,"forks_count":3,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-04-25T02:41:06.402Z","etag":null,"topics":["ai-tools","antigravity","claude-code","code-analysis","code-assistant","context-window","context-window-optimization","context-window-optimizer","copilot","cursor","developer-tools","graphrag","kiro","knowledge-graph","local-first","mcp-server","prompts","skills","tokens","windsurf"],"latest_commit_sha":null,"homepage":"","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/zzet.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE.md","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":"SECURITY.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":"docs/agents.md","dco":null,"cla":null}},"created_at":"2026-04-06T13:47:15.000Z","updated_at":"2026-04-25T00:24:41.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/zzet/gortex","commit_stats":null,"previous_names":["zzet/gortex"],"tags_count":30,"template":false,"template_full_name":null,"purl":"pkg:github/zzet/gortex","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zzet%2Fgortex","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zzet%2Fgortex/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zzet%2Fgortex/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zzet%2Fgortex/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/zzet","download_url":"https://codeload.github.com/zzet/gortex/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zzet%2Fgortex/sbom","scorecard":{"id":1246107,"data":{"date":"2026-04-15T23:37:19Z","repo":{"name":"github.com/zzet/gortex","commit":"986067a2d807a45db702685b4a9bb08de6d309f1"},"scorecard":{"version":"v5.3.0","commit":"c22063e786c11f9dd714d777a687ff7c4599b600"},"score":4.6,"checks":[{"name":"Maintained","score":0,"reason":"project was created within the last 90 days. Please review its contents carefully","details":["Warn: Repository was created within the last 90 days."],"documentation":{"short":"Determines if the project is \"actively maintained\".","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#maintained"}},{"name":"Security-Policy","score":4,"reason":"security policy file detected","details":["Info: security policy file detected: SECURITY.md:1","Warn: no linked content found","Info: Found disclosure, vulnerability, and/or timelines in security policy: SECURITY.md:1","Info: Found text in security policy: SECURITY.md:1"],"documentation":{"short":"Determines if the project has published a security policy.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#security-policy"}},{"name":"Dependency-Update-Tool","score":10,"reason":"update tool detected","details":["Info: detected update tool: Dependabot: .github/dependabot.yml:1"],"documentation":{"short":"Determines if the project uses a dependency update tool.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#dependency-update-tool"}},{"name":"Code-Review","score":0,"reason":"Found 0/18 approved changesets -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project requires human code review before pull requests (aka merge requests) are merged.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#code-review"}},{"name":"Dangerous-Workflow","score":10,"reason":"no dangerous workflow patterns detected","details":null,"documentation":{"short":"Determines if the project's GitHub Action workflows avoid dangerous patterns.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#dangerous-workflow"}},{"name":"Packaging","score":-1,"reason":"packaging workflow not detected","details":["Warn: no GitHub/GitLab publishing workflow detected."],"documentation":{"short":"Determines if the project is published as a package that others can easily download, install, easily update, and uninstall.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#packaging"}},{"name":"Token-Permissions","score":0,"reason":"detected GitHub workflow tokens with excessive permissions","details":["Info: jobLevel 'actions' permission set to 'read': .github/workflows/release.yml:128","Info: jobLevel 'contents' permission set to 'read': .github/workflows/scorecard.yml:32","Info: jobLevel 'actions' permission set to 'read': .github/workflows/scorecard.yml:33","Warn: no topLevel permission defined: .github/workflows/ci.yml:1","Warn: topLevel 'contents' permission set to 'write': .github/workflows/release.yml:9","Info: topLevel permissions set to 'read-all': .github/workflows/scorecard.yml:20","Info: no jobLevel write permissions found"],"documentation":{"short":"Determines if the project's workflows follow the principle of least privilege.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#token-permissions"}},{"name":"Binary-Artifacts","score":10,"reason":"no binaries found in the repo","details":null,"documentation":{"short":"Determines if the project has generated executable (binary) artifacts in the source repository.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#binary-artifacts"}},{"name":"Pinned-Dependencies","score":0,"reason":"dependency not pinned by hash detected -- score normalized to 0","details":["Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:80: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:82: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:17: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:19: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/ci.yml:31: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:39: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:41: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/ci.yml:46: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:54: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yml:56: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/ci.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/release.yml:145: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/release.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/release.yml:159: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/release.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/release.yml:23: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/release.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/release.yml:33: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/release.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/release.yml:96: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/release.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/release.yml:131: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/release.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/scorecard.yml:37: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/scorecard.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/scorecard.yml:42: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/scorecard.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/scorecard.yml:54: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/scorecard.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/scorecard.yml:62: update your workflow using https://app.stepsecurity.io/secureworkflow/zzet/gortex/scorecard.yml/main?enable=pin","Info:   0 out of  13 GitHub-owned GitHubAction dependencies pinned","Info:   0 out of   7 third-party GitHubAction dependencies pinned"],"documentation":{"short":"Determines if the project has declared and pinned the dependencies of its build process.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#pinned-dependencies"}},{"name":"CII-Best-Practices","score":0,"reason":"no effort to earn an OpenSSF best practices badge detected","details":null,"documentation":{"short":"Determines if the project has an OpenSSF (formerly CII) Best Practices Badge.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#cii-best-practices"}},{"name":"SAST","score":0,"reason":"SAST tool is not run on all commits -- score normalized to 0","details":["Warn: 0 commits out of 12 are checked with a SAST tool"],"documentation":{"short":"Determines if the project uses static code analysis.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#sast"}},{"name":"Vulnerabilities","score":10,"reason":"0 existing vulnerabilities detected","details":null,"documentation":{"short":"Determines if the project has open, known unfixed vulnerabilities.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#vulnerabilities"}},{"name":"Fuzzing","score":0,"reason":"project is not fuzzed","details":["Warn: no fuzzer integrations found"],"documentation":{"short":"Determines if the project uses fuzzing.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#fuzzing"}},{"name":"License","score":9,"reason":"license file detected","details":["Info: project has a license file: LICENSE.md:0","Warn: project license file does not contain an FSF or OSI license."],"documentation":{"short":"Determines if the project has defined a license.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#license"}},{"name":"Signed-Releases","score":6,"reason":"3 out of the last 5 releases have a total of 6 signed artifacts.","details":["Info: signed release artifact: checksums.txt.sig: https://github.com/zzet/gortex/releases/tag/v0.6.1","Info: signed release artifact: checksums.txt.sig: https://github.com/zzet/gortex/releases/tag/v0.6.0","Info: signed release artifact: checksums.txt.sig: https://github.com/zzet/gortex/releases/tag/v0.5.4","Warn: release artifact v0.5.3 not signed: https://api.github.com/repos/zzet/gortex/releases/309498502","Warn: release artifact v0.5.2 not signed: https://api.github.com/repos/zzet/gortex/releases/309472495","Info: provenance for release artifact: multiple.intoto.jsonl: https://github.com/zzet/gortex/releases/tag/v0.6.1","Info: provenance for release artifact: multiple.intoto.jsonl: https://github.com/zzet/gortex/releases/tag/v0.6.0","Info: provenance for release artifact: multiple.intoto.jsonl: https://github.com/zzet/gortex/releases/tag/v0.5.4","Warn: release artifact v0.5.3 does not have provenance: https://api.github.com/repos/zzet/gortex/releases/309498502","Warn: release artifact v0.5.2 does not have provenance: https://api.github.com/repos/zzet/gortex/releases/309472495"],"documentation":{"short":"Determines if the project cryptographically signs release artifacts.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#signed-releases"}},{"name":"Branch-Protection","score":0,"reason":"branch protection not enabled on development/release branches","details":["Warn: branch protection not enabled for branch 'main'"],"documentation":{"short":"Determines if the default and release branches are protected with GitHub's branch protection settings.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#branch-protection"}},{"name":"Contributors","score":10,"reason":"project has 6 contributing companies or organizations","details":["Info: found contributions from: @viodotcom, FindHotel, QyuTeam, Undev, kaize, lenshq"],"documentation":{"short":"Determines if the project has a set of contributors from multiple organizations (e.g., companies).","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#contributors"}},{"name":"CI-Tests","score":10,"reason":"6 out of 6 merged PRs checked by a CI test -- score normalized to 10","details":null,"documentation":{"short":"Determines if the project runs tests before pull requests are merged.","url":"https://github.com/ossf/scorecard/blob/c22063e786c11f9dd714d777a687ff7c4599b600/docs/checks.md#ci-tests"}}]},"last_synced_at":"2026-04-16T01:28:29.416Z","repository_id":349559649,"created_at":"2026-04-16T01:28:29.417Z","updated_at":"2026-04-16T01:28:29.417Z"},"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":32358509,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-27T20:07:02.737Z","status":"ssl_error","status_checked_at":"2026-04-27T20:07:00.910Z","response_time":128,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"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-tools","antigravity","claude-code","code-analysis","code-assistant","context-window","context-window-optimization","context-window-optimizer","copilot","cursor","developer-tools","graphrag","kiro","knowledge-graph","local-first","mcp-server","prompts","skills","tokens","windsurf"],"created_at":"2026-04-12T20:02:49.866Z","updated_at":"2026-04-27T23:01:02.138Z","avatar_url":"https://github.com/zzet.png","language":"Go","readme":"# Gortex\n\n[![CI](https://github.com/zzet/gortex/actions/workflows/ci.yml/badge.svg)](https://github.com/zzet/gortex/actions/workflows/ci.yml)\n[![Go Report Card](https://goreportcard.com/badge/github.com/zzet/gortex)](https://goreportcard.com/report/github.com/zzet/gortex)\n[![Latest release](https://img.shields.io/github/v/release/zzet/gortex?logo=github\u0026sort=semver)](https://github.com/zzet/gortex/releases/latest)\n[![Go Reference](https://pkg.go.dev/badge/github.com/zzet/gortex.svg)](https://pkg.go.dev/github.com/zzet/gortex)\n[![Sigstore signed](https://img.shields.io/badge/sigstore-signed-66D4FF?logo=sigstore\u0026logoColor=white)](#verifying-releases-supply-chain-security)\n[![SLSA 3](https://img.shields.io/badge/SLSA-Level%203-green)](https://slsa.dev/spec/v1.0/levels#build-l3)\n[![OpenSSF Scorecard](https://api.scorecard.dev/projects/github.com/zzet/gortex/badge)](https://scorecard.dev/viewer/?uri=github.com/zzet/gortex)\n[![VirusTotal](https://img.shields.io/badge/VirusTotal-0%2F91-brightgreen?logo=virustotal)](https://www.virustotal.com/gui/url/00e1094b39c9bd7db4d5a179b1d56173f85c915075057fd3cc64bfbb9b735b11/detection)\n\n\n\nCode intelligence engine that indexes repositories into an in-memory knowledge graph and exposes it via CLI, MCP Server, and web UI.\n\nBuilt for 15 AI coding agents (Claude Code, Kiro, Cursor, Windsurf, VS Code / Copilot, Continue.dev, Cline, OpenCode, Antigravity, Codex CLI, Gemini CLI, Zed, Aider, Kilo Code, OpenClaw) — one `smart_context` call replaces 5-10 file reads, cutting token usage by ~94%.\n\nSee [docs/agents.md](docs/agents.md) for the adapter matrix, per-agent schema notes, and the `gortex init --agents=\u003ccsv\u003e` CLI contract.\n\n![Gortex Web UI — force-directed knowledge graph visualization](assets/graph.png)\n\n## Features\n\n- **Knowledge graph** — every file, symbol, import, call chain, and type relationship in one queryable structure\n- **Multi-repo workspaces** — index multiple repositories into a single graph with cross-repo symbol resolution, project grouping, reference tags, and per-repo scoping\n- **92 languages** — tree-sitter + regex extractors across core programming (Go, TypeScript, Python, Rust, Java, C#, Kotlin, Swift, C, C++, …), scripting (Bash, PowerShell, Perl, Lua, …), functional (Haskell, OCaml, Elixir, Clojure, …), template engines (Blade, EJS, Jinja, Twig, ERB, Liquid, Pug, Handlebars), blockchain (Solidity, Move, Cairo, Noir, Tact, Ballerina), scientific (Julia, R, MATLAB, Mathematica, SAS, Stata, Fortran, COBOL, Ada, Pascal, ABAP, Apex), emerging (Mojo, Odin, V, Hare, Carbon, ReScript, Gleam), build/data (Makefile, CMake, Dockerfile, SQL, Protobuf, JSON, YAML, TOML, HCL), and more. See [docs/languages.md](docs/languages.md) for the full table\n- **50 MCP tools** — symbol lookup, call chains, blast radius, community/process discovery, contract detection, unified `analyze` (dead code, hotspots, cycles), scaffolding, inline editing, symbol renaming, read-free file writes (`edit_file` / `write_file` — no Read-before-Edit roundtrip for docs/configs/specs), multi-axis structured retrieval (`winnow_symbols`), multi-repo management, agent feedback loop, context export, graph-validated config hygiene (`audit_agent_config`), opening-move routing (`plan_turn`), narrative repo overview (`get_repo_outline`), test-coverage gaps (`get_untested_symbols`), and 18 agent-optimized tools\n- **Semantic search** — hybrid BM25 + vector search with RRF fusion. Hugot (pure-Go ONNX runtime with MiniLM-L6-v2) is bundled by default and auto-downloads the model on first use — zero-config, no native dependencies. GloVe word vectors remain as fallback. Optional build tags switch to ONNX or GoMLX for higher throughput\n- **LSP-enriched call-graph tiers** — every edge carries an `origin` tier (`lsp_resolved` / `lsp_dispatch` / `ast_resolved` / `ast_inferred` / `text_matched`); pass `min_tier` to `get_callers`, `find_usages`, `find_implementations`, etc. to restrict results to compiler-verified edges for high-stakes refactors\n- **MCP progress notifications** — long-running indexing and track_repository calls emit `notifications/progress` with stage messages (walking files → parsing → resolving → semantic enrichment → search index → contracts → done) so hosts show real progress bars on large repos\n- **Type-aware resolution** — infers receiver types from variable declarations, composite literals, and Go constructor conventions to disambiguate same-named methods across types\n- **On-disk persistence** — snapshots the graph on shutdown, restores on startup with incremental re-indexing of only changed files (~200ms vs 3-5s full re-index)\n- **HTTP server (`gortex server`)** — versioned `/v1/*` JSON API exposing all MCP tools (`/v1/health`, `/v1/tools`, `/v1/tools/{name}`, `/v1/stats`, `/v1/graph`, `/v1/events` SSE) for IDE plugins, CI, and the Next.js web UI. Localhost bind + bearer-token auth (`--auth-token` / `$GORTEX_SERVER_TOKEN`) by default; CORS configurable for separate frontend origins\n- **Semantic enrichment** — pluggable SCIP, go/types, and LSP providers upgrade edge confidence from ~70-85% (tree-sitter) to 95-100% (compiler-verified). Additive — graceful degradation when external tools unavailable\n- **Agent feedback loop** — unified `feedback` tool (`action: \"record\"` / `\"query\"`) lets agents report which symbols were useful/missing. Cross-session persistence improves future `smart_context` quality via feedback-aware reranking\n- **Context export** — `export_context` tool + `gortex context` CLI render graph context as portable markdown/JSON briefings for sharing outside MCP (Slack, PRs, docs, non-MCP AI tools)\n- **ETag conditional fetch** — content-hash based `if_none_match` on source-reading tools avoids re-transmitting unchanged symbols during iterative editing\n- **Token savings tracking** — per-call `tokens_saved` field on source-reading tools + session-level metrics in `graph_stats` (calls counted, tokens returned, tokens saved, efficiency ratio)\n- **GCX1 compact wire format** — published, round-trippable text format for MCP tool responses. Opt-in per call via `format: \"gcx\"` on 13 tools. **Median −27.4% tiktoken savings** vs JSON across a 20-case benchmark (best case −38.3%), 100% round-trip integrity. Spec: [`docs/wire-format.md`](docs/wire-format.md). Standalone MIT-licensed reference implementations: Go ([`github.com/gortexhq/gcx-go`](https://github.com/gortexhq/gcx-go)) and TypeScript ([`github.com/gortexhq/gcx-ts`](https://github.com/gortexhq/gcx-ts), npm [`@gortex/wire`](https://www.npmjs.com/package/@gortex/wire)). Reproducible harness: [`bench/wire-format/`](bench/wire-format/)\n- **7 MCP resources** — lightweight graph context without tool calls\n- **3 MCP prompts** — `pre_commit`, `orientation`, `safe_to_change` for guided workflows\n- **Two-tier config** — global config (`~/.config/gortex/config.yaml`) for projects and repo lists, per-repo `.gortex.yaml` for guards, excludes, and local overrides\n- **Guard rules** — project-specific constraints (co-change, boundary) enforced via `check_guards`\n- **Watch mode** — surgical graph updates on file change across all tracked repos, live sync with agents\n- **Web UI** — standalone Next.js 15 app (`web/`) that talks to `gortex server` over `/v1/*`, with Sigma.js 2D graphs and five react-three-fiber 3D views (City, Strata, Galaxies, Constellation, Graph3D)\n- **IMPLEMENTS inference** — structural interface satisfaction for Go, TypeScript, Java, Rust, C#, Scala, Swift, Protobuf\n- **PreToolUse + PreCompact + Stop hooks** — PreToolUse enriches Read/Grep/Glob/Bash (`codebase-search` / `rg` / `grep` probes routed through graph tools) with graph context and redirects to Gortex MCP tools; matching `Task` also briefs spawned subagents with an inline tool-swap table + task-scoped `smart_context` so subagents don't fall back to grep/Read. PreCompact injects a condensed orientation snapshot (index stats, recently-modified symbols, top hotspots, feedback-ranked symbols) before Claude Code compacts the conversation. Stop runs post-task diagnostics (`detect_changes` → `get_test_targets`, `check_guards`, `analyze dead_code`, `contracts check` on modified symbols) so the agent self-corrects before handoff. All hooks degrade silently when the server is unreachable\n- **Long-living daemon (optional)** — `gortex daemon start` runs a single shared process that holds the graph for every tracked repo. Each Claude Code / Cursor / Kiro window connects as a thin stdio proxy over a Unix socket, getting per-client session isolation (recent activity, token stats) + cross-repo queries by default. Live fsnotify watching on every tracked repo so file edits flow into the graph without manual reload. `gortex install` sets up user-level config; `gortex daemon install-service` installs a LaunchAgent (macOS) or systemd `--user` unit (Linux) so the OS supervises lifecycle and auto-starts at login — no sudo required. Binaries fall back to embedded mode if the daemon isn't running; the feature is additive\n- **Benchmarked** — per-language parsing, query engine, indexer benchmarks\n- **Per-community skills** — `gortex init --skills` (default on) auto-generates SKILL.md per detected community with key files, entry points, cross-community connections, and MCP tool invocations for Claude Code auto-discovery; the same routing table lands in every detected agent's per-repo instructions file\n- **Eval framework** — SWE-bench harness for A/B benchmarking tool effectiveness with Docker-based environments and multi-model support\n- **`gortex eval` CLI** — first-class evaluation harness. Subcommands: `recall` (fixture-driven any-hit R@1/5/20 + MRR per ranker, per-tier breakdown, p50/p95 latency, tokens-returned, optional LLM judge for CQS-style dual-judge scoring), `embedders` (ONNX variant comparison — size + init + embed latency + end-to-end quality across MiniLM variants, BGE, Jina), `swebench` (passthrough), `tokens` (GCX1 wire-format bench). Seed fixture at [`bench/fixtures/retrieval.yaml`](bench/fixtures/retrieval.yaml); published BM25 baseline on Gortex: **R@1 42.3% · R@5 56.4% · R@20 69.9% · exact R@5 95.2%**\n- **Zero dependencies** — everything runs in-process, in memory, no external services\n\n## Installation\n\nPre-built binaries are published to [GitHub Releases](https://github.com/zzet/gortex/releases) for linux/amd64, linux/arm64, darwin/amd64 (Intel Mac), and darwin/arm64 (Apple Silicon). Every release is **cosign-signed**, ships **SLSA-3 provenance**, and is **VirusTotal-scanned** — see [Verifying releases](#verifying-releases-supply-chain-security) below. Windows support is planned.\n\n**New to Gortex?** After installing, see [docs/onboarding.md](docs/onboarding.md) for the 15-minute walkthrough: `gortex install` (once per machine) → `gortex init` (once per repo) → verify your AI assistant uses graph tools → what to do if it doesn't.\n\n### macOS — Homebrew\n\n```bash\nbrew install zzet/tap/gortex\n```\n\nHomebrew strips the `homebrew-` prefix from tap repositories, so `zzet/homebrew-tap` is installed as `zzet/tap`. Updates via `brew upgrade`. No Gatekeeper prompt — `brew` doesn't set the quarantine attribute on downloads.\n\n### Linux — Debian / Ubuntu (.deb)\n\n```bash\nARCH=$(dpkg --print-architecture)  # amd64 or arm64\ncurl -LO \"https://github.com/zzet/gortex/releases/latest/download/gortex_linux_${ARCH}.deb\"\nsudo dpkg -i \"gortex_linux_${ARCH}.deb\"\n```\n\n### Linux — RHEL / Fedora / CentOS (.rpm)\n\n```bash\nARCH=$(uname -m); [ \"$ARCH\" = x86_64 ] \u0026\u0026 ARCH=amd64; [ \"$ARCH\" = aarch64 ] \u0026\u0026 ARCH=arm64\ncurl -LO \"https://github.com/zzet/gortex/releases/latest/download/gortex_linux_${ARCH}.rpm\"\nsudo rpm -ivh \"gortex_linux_${ARCH}.rpm\"\n```\n\n### Linux — Alpine (.apk)\n\n```bash\nARCH=$(uname -m); [ \"$ARCH\" = x86_64 ] \u0026\u0026 ARCH=amd64; [ \"$ARCH\" = aarch64 ] \u0026\u0026 ARCH=arm64\ncurl -LO \"https://github.com/zzet/gortex/releases/latest/download/gortex_linux_${ARCH}.apk\"\nsudo apk add --allow-untrusted \"gortex_linux_${ARCH}.apk\"\n```\n\n### Direct binary download (any Linux or macOS)\n\n```bash\n# Pick the right asset for your OS/arch\nOS=$(uname -s | tr '[:upper:]' '[:lower:]')  # linux or darwin\nARCH=$(uname -m)\ncase $ARCH in\n  x86_64) ARCH=amd64 ;;\n  aarch64|arm64) ARCH=arm64 ;;\nesac\n\ncurl -LO \"https://github.com/zzet/gortex/releases/latest/download/gortex_${OS}_${ARCH}.tar.gz\"\ntar -xzf \"gortex_${OS}_${ARCH}.tar.gz\"\nsudo mv gortex /usr/local/bin/\n```\n\nOn macOS, if you downloaded via browser (not `curl`), remove the quarantine flag once:\n\n```bash\nxattr -d com.apple.quarantine /usr/local/bin/gortex\n```\n\n### Verify the install\n\n```bash\ngortex version\n```\n\n### Verifying releases (supply-chain security)\n\nEvery GitHub release is:\n\n- **Signed with [cosign](https://github.com/sigstore/cosign)** — keyless via GitHub's OIDC identity. Each artifact ships with matching `.sig` and `.pem` files that cryptographically prove the binary came from this repo's release workflow.\n- **Attested with [SLSA-3 provenance](https://slsa.dev/spec/v1.0/levels#build-l3)** — a `multiple.intoto.jsonl` file attached to each release records the exact commit, builder, and workflow that produced every artifact. Tamper-evident and non-forgeable.\n- **Scanned against ~72 AV engines via [VirusTotal](https://virustotal.com)** — the detection count (e.g. `0 / 72`) is posted in each release's notes, with a link to the full per-engine report.\n\nYou don't need to verify manually if you're installing via `brew` / `dpkg` / `rpm` — those paths go through package managers that check integrity themselves. Verification matters when you're redistributing Gortex downstream, running it inside a locked-down enterprise environment, or writing your own installer.\n\n**cosign** — install once via `brew install cosign`, `apt install cosign`, or from [the cosign releases page](https://github.com/sigstore/cosign/releases). Then:\n\n```bash\nTAG=v0.5.4                           # replace with the release you downloaded\nFILE=gortex_linux_amd64.tar.gz       # pick your artifact\n\nBASE=\"https://github.com/zzet/gortex/releases/download/${TAG}\"\ncurl -LO \"${BASE}/${FILE}\"\ncurl -LO \"${BASE}/${FILE}.sig\"\ncurl -LO \"${BASE}/${FILE}.pem\"\n\ncosign verify-blob \\\n  --certificate \"${FILE}.pem\" \\\n  --signature \"${FILE}.sig\" \\\n  --certificate-identity-regexp 'https://github\\.com/zzet/gortex/\\.github/workflows/.+@refs/tags/v.+' \\\n  --certificate-oidc-issuer https://token.actions.githubusercontent.com \\\n  \"${FILE}\"\n```\n\nExpected output: `Verified OK`. Anything else — stop and delete the binary.\n\n**SLSA-3** — install [`slsa-verifier`](https://github.com/slsa-framework/slsa-verifier/releases) once. Then:\n\n```bash\ncurl -LO \"${BASE}/multiple.intoto.jsonl\"\n\nslsa-verifier verify-artifact \"${FILE}\" \\\n  --provenance-path multiple.intoto.jsonl \\\n  --source-uri github.com/zzet/gortex \\\n  --source-tag \"${TAG}\"\n```\n\nExpected output ends with `PASSED: SLSA verification passed`.\n\n**VirusTotal** — open the release page on GitHub. The notes include a per-asset scan table like `gortex_linux_amd64.tar.gz — 0 / 72` with a link to the full report. A non-zero detection on a Go binary is usually a false positive (Go's static linking + stripped symbols trips heuristics), but you should still compare against prior releases before trusting the download.\n\n### From source\n\nRequires Go 1.25+ and a C toolchain (the tree-sitter extractors are CGO — no way around it).\n\n```bash\ngit clone https://github.com/zzet/gortex.git\ncd gortex\ngo build -o gortex ./cmd/gortex/\nsudo mv gortex /usr/local/bin/\n```\n\nOr without cloning:\n\n```bash\ngo install github.com/zzet/gortex/cmd/gortex@latest\n```\n\n`go install` drops the binary into `$(go env GOBIN)` (default `~/go/bin`) — make sure that's on your `PATH`.\n\n## Quick Start\n\nSetup is split into two commands — `gortex install` runs once per machine, `gortex init` runs once per repo:\n\n- **`gortex install`** writes user-level artifacts: `~/.claude.json` MCP config, `~/.claude/skills/gortex-*` (tool-usage skills), `~/.claude/commands/gortex-*.md` (slash commands), `~/.gemini/antigravity/` Knowledge Items, and (optionally) user-level Claude Code hooks. Codebase-agnostic content lives here so it isn't duplicated into every repo.\n- **`gortex init`** writes per-repo artifacts: `.mcp.json`, `.claude/settings.{json,local.json}`, `CLAUDE.md` with the codebase overview and community routing, `.claude/skills/generated/` per-community SKILL.md files, and a marker-guarded community routing block in every other detected agent's per-repo instructions file (`AGENTS.md`, `.windsurfrules`, `GEMINI.md`, `.cursor/rules/gortex-communities.mdc`, etc.).\n\n### One-time machine setup\n\n```bash\ngortex install                      # interactive-free: MCP + skills + slash commands at ~/.claude/\ngortex install --start --track      # also spawn the daemon and track the current directory\ngortex install --no-hooks           # skip user-level hook installation\n\n# Daemon lifecycle (also spawned by `gortex install --start`):\ngortex daemon start --detach        # spawn in background\ngortex daemon status                # PID, uptime, memory, tracked repos, sessions\ngortex daemon stop                  # graceful shutdown + final snapshot\ngortex daemon restart               # stop + start\ngortex daemon reload                # re-read config, pick up new/removed repos\ngortex daemon logs -n 50            # tail the log file\n\n# Auto-start at login (launchd on macOS, systemd --user on Linux):\ngortex daemon install-service\ngortex daemon service-status\ngortex daemon uninstall-service\n\n# Track / untrack repos (daemon-first dispatch; falls back to config-only when no daemon):\ngortex track ~/projects/backend\ngortex untrack backend\n\n# Per-repo status + daemon-wide status share the same command — it picks:\ngortex status\n```\n\n### Per-repo setup\n\n```bash\ncd ~/projects/myapp\ngortex init                             # writes .mcp.json, .claude/settings.*, CLAUDE.md with community routing\ngortex init --analyze                   # also index first for a richer CLAUDE.md overview\ngortex init --no-skills                 # skip community-routing generation\ngortex init --skills-min-size 5 --skills-max 10   # tune the generator\ngortex init --hooks-only                # (re)install repo-local hooks only, skip everything else\ngortex init --no-hooks                  # full init but skip hook installation\n\n# Run the MCP server standalone (auto-detects daemon via stdio; --no-daemon forces embedded):\ngortex mcp --index /path/to/repo --watch\ngortex mcp --no-daemon --watch          # explicit embedded mode\n```\n\n### Other commands\n\n```bash\ngortex server --index .                  # HTTP/JSON API on :4747 (/v1/*). Run `cd web \u0026\u0026 npm run dev` for the UI.\ngortex savings                           # cumulative tokens saved + $ avoided across sessions\ngortex version\n```\n\n## Multi-Repo Workspaces\n\nGortex can index multiple repositories into a single shared graph, enabling cross-repo symbol resolution, impact analysis, and navigation.\n\n### Configuration\n\nTwo-tier config hierarchy:\n\n- **Global config** (`~/.config/gortex/config.yaml`) — projects, repo lists, active project, reference tags\n- **Workspace config** (`.gortex.yaml` per repo) — guards, excludes, local overrides\n\nExcludes are layered — builtin → global → per-repo entry → workspace — with gitignore semantics. Use `!pattern` in a later layer to re-include something an earlier layer excluded.\n\n```yaml\n# ~/.config/gortex/config.yaml\nactive_project: my-saas\n\nexclude:                            # Applies to every tracked repo\n  - \"**/*.generated.*\"\n  - \"node_modules/\"                 # Already in the builtin baseline\n\nrepos:\n  - path: /home/user/projects/gortex\n    name: gortex\n    exclude:                        # Extra patterns just for this repo\n      - \"results/**\"\n\nprojects:\n  my-saas:\n    repos:\n      - path: /home/user/projects/frontend\n        name: frontend\n        ref: work\n      - path: /home/user/projects/backend\n        name: backend\n        ref: work\n      - path: /home/user/projects/shared-lib\n        name: shared-lib\n        ref: opensource\n```\n\n### Daemon tuning (optional)\n\nThe daemon's defaults handle typical workflows without configuration. These knobs exist for monorepos, branch-heavy workflows, or filesystems without fsnotify support.\n\n```yaml\n# ~/.config/gortex/config.yaml (or per-repo .gortex.yaml)\nwatch:\n  debounce_ms: 150            # per-file patch debounce (default 150)\n\n  # Storm mode — when more than N events land within the window,\n  # switch from per-file debounced patching to a batched reconcile\n  # that defers cross-file resolver + search work until a quiet\n  # period has passed. Amortises the cost of bulk operations\n  # (rsync, npm install, branch checkout, bulk format-on-save,\n  # find-and-replace). Zero = disabled (default).\n  storm_threshold: 0          # 0 disables; try 50 on monorepos\n  storm_window_ms: 500\n  storm_quiet_period_ms: 500\n```\n\nEnvironment variables:\n\n- `GORTEX_RECONCILE_INTERVAL` — janitor tick that walks every tracked repo and runs `IncrementalReindex` against disk. Insurance against fsnotify gaps on NFS/SMB mounts, inotify watch-limit exhaustion, or daemon downtime where edits happened offline. Default `1h`; `\"0\"` or `\"off\"` disables; otherwise any Go duration string (e.g., `15m`).\n- The daemon also watches each tracked repo's `.git/HEAD`, so branch switches and rebases reconcile incrementally (via `git diff --name-status`) rather than by re-indexing every changed file individually — no configuration needed.\n\n### CLI\n\n```bash\ngortex track /path/to/repo          # Add a repo to the workspace\ngortex untrack /path/to/repo        # Remove a repo from the workspace\ngortex mcp --track /path/to/repo    # Track additional repos on startup\ngortex mcp --project my-saas        # Set active project scope\ngortex index repo-a/ repo-b/        # Index multiple repos\ngortex status                       # Per-repo and per-project stats\n\n# Manage the effective ignore list used by indexing + watching\ngortex config exclude list                          # Show all layers (builtin, global, repo entry, workspace)\ngortex config exclude add pkg/generated             # Default target: workspace .gortex.yaml\ngortex config exclude add '**/*.bak' --global       # Write to ~/.config/gortex/config.yaml\ngortex config exclude add testdata/ --repo backend  # Write to a RepoEntry\ngortex config exclude remove pkg/generated          # Remove from the same target\n```\n\n### MCP Tools\n\nAgents can manage repos at runtime without CLI access:\n\n| Tool | Description |\n|------|-------------|\n| `track_repository` | Add a repo, index immediately, persist to config |\n| `untrack_repository` | Remove a repo, evict nodes/edges, persist to config |\n| `set_active_project` | Switch project scope for all subsequent queries |\n| `get_active_project` | Return current project name and repo list |\n\nAll query tools (`search_symbols`, `get_symbol`, `find_usages`, `get_file_summary`, `get_call_chain`, `smart_context`) accept optional `repo`, `project`, and `ref` parameters for scoping. When an active project is set, it applies as the default scope.\n\n### How It Works\n\n- **Qualified Node IDs** — in multi-repo mode, IDs become `\u003crepo_prefix\u003e/\u003cpath\u003e::\u003cSymbol\u003e` (e.g., `frontend/src/app.ts::App`). Single-repo mode keeps the existing `\u003cpath\u003e::\u003cSymbol\u003e` format.\n- **Cross-repo edges** — the resolver links symbols across repo boundaries with same-repo preference. Cross-repo edges carry a `cross_repo: true` flag.\n- **Impact analysis** — `explain_change_impact`, `verify_change`, and `get_test_targets` follow cross-repo edges automatically, grouping results by repository.\n- **Shared repos** — the same repo can appear in multiple projects with different reference tags. It's indexed once and shared across projects.\n- **Auto-detection** — set `workspace.auto_detect: true` in `.gortex.yaml` to auto-discover Git repos in a parent directory.\n\n## Usage with Claude Code\n\nAfter `gortex install` (once per machine) and `gortex init` (once per repo), Claude Code automatically starts Gortex via `.mcp.json`. The agent gets:\n\n- **Slash commands:** `/gortex-guide`, `/gortex-explore`, `/gortex-debug`, `/gortex-impact`, `/gortex-refactor` — installed to `~/.claude/commands/` by `gortex install`\n- **Tool-usage skills:** installed to `~/.claude/skills/` by `gortex install` — one copy per user, used across every repo\n- **PreToolUse hook:** automatic graph context + graph-tool suggestions on Read/Grep/Glob\n- **PreCompact hook:** condensed orientation snapshot injected before context compaction so the agent resumes without re-exploring\n- **Stop hook:** post-task diagnostics — tests to run, guard violations, dead code, and contract issues on the changed symbols — injected as context before the agent hands off\n- **CLAUDE.md:** per-repo codebase overview (via `--analyze`) plus a marker-guarded community routing block written by `gortex init --skills`\n\n## Usage with other agents\n\n`gortex install` (user-level) and `gortex init` (repo-level) together auto-detect and configure 14 other AI coding assistants — Kiro, Cursor, VS Code / Copilot, Windsurf, Continue.dev, Cline, OpenCode, Antigravity, Codex CLI, Gemini CLI, Zed, Aider, Kilo Code, OpenClaw. Each adapter writes only when its host is present on the machine, and every re-run is idempotent.\n\nTool-usage guidance for agents that have a user-level surface (Claude Code, Antigravity) lives once per user; for the rest, MCP tool descriptions carry the teaching and `gortex init` adds only a per-repo community-routing block — no more duplicated instructions blocks in every repo.\n\n- **Adapter matrix + per-agent schema notes:** [`docs/agents.md`](docs/agents.md)\n- **Audit what's currently configured:** `gortex init doctor` (zero-op; `--json` for CI consumers)\n- **Constrain setup:** `gortex init --agents=claude-code,cursor` or `--agents-skip=antigravity` (same flags accepted by `gortex install`)\n- **CI / scripted install:** `gortex install --yes --json` then `gortex init --yes --json --dry-run`\n\n## CLI Commands\n\n```\ngortex install               One-time machine-wide setup (user-level MCP, skills, hooks, daemon wiring)\ngortex init [path]           Per-repo setup (.mcp.json, hooks, community routing, per-community SKILL.md)\ngortex init doctor           Zero-op drift report across all detected agents (human or --json)\ngortex mcp [flags]            Start the MCP stdio server (auto-detects daemon; --no-daemon / --proxy; --server adds HTTP API)\ngortex server [flags]         Start the HTTP/JSON API under /v1/* (--bind, --auth-token, --watch, --cors-origin)\ngortex daemon \u003csubcommand\u003e   start / stop / restart / reload / status / logs / install-service / service-status / uninstall-service\ngortex eval \u003csubcommand\u003e     Retrieval + token benchmarks — recall, embedders, swebench, tokens\ngortex eval-server [flags]   HTTP server used by the swebench harness\ngortex context [flags]       Generate portable context briefing for a task\ngortex savings [flags]       Show cumulative token savings + cost avoided across sessions\ngortex index [path...]       Index one or more repositories and print stats\ngortex status [flags]        Show index status (per-repo and per-project in multi-repo mode)\ngortex track \u003cpath\u003e          Add a repository to the tracked workspace\ngortex untrack \u003cpath\u003e        Remove a repository from the tracked workspace\ngortex config exclude ...    add / list / remove entries in the effective ignore list\ngortex query \u003csubcommand\u003e    Query the knowledge graph from the CLI\ngortex clean                 Remove Gortex files from a project\ngortex version               Print version\n```\n\n### Query Subcommands\n\n```\ngortex query symbol \u003cname\u003e              Find symbols matching name\ngortex query deps \u003cid\u003e                  Show dependencies\ngortex query dependents \u003cid\u003e            Show blast radius\ngortex query callers \u003cfunc-id\u003e          Show who calls a function\ngortex query calls \u003cfunc-id\u003e            Show what a function calls\ngortex query implementations \u003ciface\u003e    Show interface implementations\ngortex query usages \u003cid\u003e                Show all usages\ngortex query stats                      Show graph statistics\n```\n\nAll query commands support `--format text|json|dot` (DOT output for Graphviz visualization).\n\n## MCP Tools (50)\n\n### Core Navigation\n| Tool | Description |\n|------|-------------|\n| `graph_stats` | Node/edge counts by kind, language, per-repo stats, and session token savings |\n| `search_symbols` | Find symbols by name (replaces Grep). Accepts `repo`, `project`, `ref` params |\n| `winnow_symbols` | Structured constraint-chain retrieval — `kind`, `language`, `community`, `path_prefix`, `min_fan_in`, `min_fan_out`, `min_churn`, `text_match` with per-axis score contributions |\n| `get_symbol` | Symbol location and signature (replaces Read). Accepts `repo`, `project`, `ref` params |\n| `get_file_summary` | All symbols and imports in a file. Accepts `repo`, `project`, `ref` params |\n| `get_editing_context` | **Primary pre-edit tool** — symbols, signatures, callers, callees |\n| `get_repo_outline` | Narrative single-call repo overview — top languages, communities, hotspots, most-imported files, entry points |\n| `plan_turn` | Opening-move router — returns ranked next calls with pre-filled args for a task description (~200 tokens) |\n\n### Graph Traversal\n| Tool | Description |\n|------|-------------|\n| `get_dependencies` | What a symbol depends on |\n| `get_dependents` | What depends on a symbol (blast radius) |\n| `get_call_chain` | Forward call graph |\n| `get_callers` | Reverse call graph |\n| `find_usages` | Every reference to a symbol |\n| `find_implementations` | Types implementing an interface |\n| `get_cluster` | Bidirectional neighborhood |\n\n### Coding Workflow\n| Tool | Description |\n|------|-------------|\n| `get_symbol_source` | Source code of a single symbol (80% fewer tokens than Read). Returns `tokens_saved` per call |\n| `batch_symbols` | Multiple symbols with source/callers/callees in one call |\n| `find_import_path` | Correct import path for a symbol |\n| `explain_change_impact` | Risk-tiered blast radius with affected processes |\n| `get_recent_changes` | Files/symbols changed since timestamp |\n| `edit_symbol` | Edit a symbol's source directly by ID — no Read needed |\n| `edit_file` | Edit any file (markdown, config, spec, template, source) by exact string replacement — accepts absolute paths or repo-rooted paths. Kills the Read-before-Edit stall on files not in the graph |\n| `write_file` | Create or overwrite any file with given content — atomic temp+rename, re-indexes on write |\n| `rename_symbol` | Coordinated multi-file rename with all references |\n\n### Agent-Optimized (token efficiency)\n| Tool | Description |\n|------|-------------|\n| `smart_context` | Task-aware minimal context — replaces 5-10 exploration calls |\n| `get_edit_plan` | Dependency-ordered edit sequence for multi-file refactors |\n| `get_test_targets` | Maps changed symbols to test files and run commands |\n| `get_untested_symbols` | Inverse of `get_test_targets` — functions/methods not reached from any test file, ranked by fan-in |\n| `suggest_pattern` | Extracts code pattern from an example — source, registration, tests |\n| `export_context` | Portable markdown/JSON context briefing for sharing outside MCP |\n| `feedback` | `action: \"record\"`: report useful/missing symbols. `action: \"query\"`: aggregated stats — most useful, most missed, accuracy metrics |\n\n### Analysis\n| Tool | Description |\n|------|-------------|\n| `get_communities` | Functional clusters (Louvain). Without `id`: list all. With `id`: members and cohesion for one community |\n| `get_processes` | Discovered execution flows. Without `id`: list all. With `id`: step-by-step trace |\n| `detect_changes` | Git diff mapped to affected symbols |\n| `index_repository` | Index or re-index a repository path |\n| `contracts` | API contracts. `action: \"list\"` (default): detected HTTP/gRPC/GraphQL/topics/WebSocket/env/OpenAPI. `action: \"check\"`: orphan providers/consumers |\n\n### Proactive Safety\n| Tool | Description |\n|------|-------------|\n| `verify_change` | Check proposed signature changes against all callers and interface implementors |\n| `check_guards` | Evaluate project guard rules (`.gortex.yaml`) against changed symbols |\n| `audit_agent_config` | Scan CLAUDE.md / AGENTS.md / `.cursor/rules` / `.github/copilot-instructions.md` / `.windsurf/rules` / `.antigravity/rules` for stale symbol references, dead file paths, and bloat — validated against the Gortex graph (no other competitor does this) |\n\n### Code Quality\n| Tool | Description |\n|------|-------------|\n| `analyze` | Unified graph analysis. `kind: \"dead_code\"`: symbols with zero incoming edges. `kind: \"hotspots\"`: high fan-in/out symbols. `kind: \"cycles\"`: Tarjan's SCC cycle detection. `kind: \"would_create_cycle\"`: check if a new dependency would form a cycle |\n| `index_health` | Health score, parse failures, stale files, language coverage |\n| `get_symbol_history` | Symbols modified this session with counts; flags churning (3+ edits) |\n\n### Code Generation\n| Tool | Description |\n|------|-------------|\n| `scaffold` | Generate code, registration wiring, and test stubs from an example symbol |\n| `batch_edit` | Apply multiple edits in dependency order, re-index between steps |\n| `diff_context` | Git diff enriched with callers, callees, community, processes, per-file risk |\n| `prefetch_context` | Predict needed symbols from task description and recent activity |\n\n### Multi-Repo Management\n| Tool | Description |\n|------|-------------|\n| `track_repository` | Add a repo at runtime — indexes immediately, persists to global config |\n| `untrack_repository` | Remove a repo — evicts nodes/edges, persists to global config |\n| `set_active_project` | Switch active project scope for all subsequent queries |\n| `get_active_project` | Return current project name and its member repositories |\n\n## MCP Resources (7)\n\n| Resource | Description |\n|----------|-------------|\n| `gortex://session` | Current session state and activity |\n| `gortex://stats` | Graph statistics (node/edge counts) |\n| `gortex://schema` | Graph schema reference |\n| `gortex://communities` | Community list with cohesion scores |\n| `gortex://community/{id}` | Single community detail |\n| `gortex://processes` | Execution flow list |\n| `gortex://process/{id}` | Single process trace |\n\n## MCP Prompts (3)\n\n| Prompt | Description |\n|--------|-------------|\n| `pre_commit` | Review uncommitted changes — shows changed symbols, blast radius, risk level, affected tests |\n| `orientation` | Orient in an unfamiliar codebase — graph stats, communities, execution flows, key symbols |\n| `safe_to_change` | Analyze whether it's safe to change specific symbols — blast radius, edit plan, affected tests |\n\n## Web UI\n\nGortex ships a standalone Next.js 15 application under `web/`. It runs separately from the backend and talks to `gortex server` over `/v1/*`:\n\n```bash\n# 1) Start the HTTP backend (localhost:4747 by default, bearer-auth in non-localhost binds)\ngortex server --index /path/to/repo --watch\n\n# 2) Start the frontend in another terminal\ncd web\n# point the UI at the backend (and at an auth token if you set one on the server)\necho 'NEXT_PUBLIC_GORTEX_URL=http://localhost:4747' \u003e .env.local\nnpm install \u0026\u0026 npm run dev\n# Open http://localhost:3000\n```\n\n| Page | Features |\n|------|----------|\n| **Dashboard** | Health, stats, language pie chart, node kind bar chart |\n| **Graph Explorer** | Sigma.js 2D + five react-three-fiber 3D modes (City / Strata / Galaxies / Constellation / Graph3D), node filters, selection, detail panel |\n| **Search** | Semantic + BM25 search via `/v1/*`, results grouped by kind |\n| **Symbol Detail** | Source code, signature, callers/callees/usages/deps tabs |\n| **Communities** | Community cards with cohesion bars, expandable members |\n| **Processes** | Collapsible call-tree steps, product vs test process split |\n| **Analysis** | Dead code, hotspots, cycles, index health — 4 tabs |\n| **Contracts** | API contracts (HTTP, gRPC, GraphQL, topics, WebSocket, env vars) with provider/consumer matching, request/response type tracing, `yours / tests / deps / all` scope filter |\n| **Services** | Service-level graph visualization with per-repo stats |\n| **AI Chat** | LLM-powered chat with code context (placeholder) |\n\n## Server Mode\n\nThe `gortex server` command exposes all MCP tools as an HTTP/JSON API under versioned `/v1/*` routes:\n\n```bash\n# Standalone HTTP backend (default bind 127.0.0.1:4747)\ngortex server --index /path/to/repo --watch\n\n# Non-localhost bind requires an auth token\ngortex server --index . --bind 0.0.0.0 --auth-token \"$(openssl rand -hex 32)\"\n\n# HTTP API alongside MCP stdio (same process)\ngortex mcp --index /path/to/repo --server --port 8765\n```\n\n**Endpoints (all under `/v1/`):**\n| Endpoint | Method | Description |\n|----------|--------|-------------|\n| `/v1/health` | GET | Status, node/edge counts, uptime |\n| `/v1/tools` | GET | List all available tools with descriptions |\n| `/v1/tools/{name}` | POST | Invoke any MCP tool with JSON arguments. Accepts `?format=gcx` or top-level `\"format\"` in the body |\n| `/v1/stats` | GET | Graph statistics by kind and language, plus `server_id` + `started_at` |\n| `/v1/graph` | GET | Full brief-graph dump (nodes + edges + stats); accepts `?project=` and/or `?repo=` for scoping |\n| `/v1/events` | GET | SSE stream of graph-change events (requires `--watch`). Accepts `?token=\u003ct\u003e` for `EventSource` auth |\n\n**Auth \u0026 binding.** The server defaults to `--bind 127.0.0.1` and runs unauthenticated on localhost only (logs `server: unauthenticated mode; localhost only`). Set `--auth-token \u003ctoken\u003e` or `$GORTEX_SERVER_TOKEN` to require `Authorization: Bearer \u003ctoken\u003e` on every `/v1/*` request (constant-time compare; CORS preflights bypass). Non-localhost binds without a token are rejected at startup. CORS origin is configurable via `--cors-origin` (default `*`).\n\n## Cross-Repo API Contracts\n\nGortex detects API contracts across repos and matches providers to consumers:\n\n```bash\n# After indexing, contracts are auto-detected\ngortex server --index .\n\n# Via MCP tools\ncontracts                        # list all detected contracts (default action)\ncontracts {action: \"check\"}      # find mismatches and orphans\n```\n\n| Contract Type | Detection | Provider | Consumer |\n|--------------|-----------|----------|----------|\n| **HTTP Routes** | Framework annotations (gin, Express, FastAPI, Spring, etc.) | Route handler | HTTP client calls (fetch, http.Get) |\n| **gRPC** | Proto service definitions | Service RPC | Client stub calls |\n| **GraphQL** | Schema type/field definitions | Schema | Query/mutation strings |\n| **Message Topics** | Pub/sub patterns (Kafka, NATS, RabbitMQ) | Publish calls | Subscribe calls |\n| **WebSocket** | Event emit/listen patterns | emit() | on() |\n| **Env Vars** | os.Getenv, process.env, .env files | Setenv / .env | Getenv / process.env |\n| **OpenAPI** | Swagger/OpenAPI spec files | Spec paths | (linked to HTTP routes) |\n\nContracts are normalized to canonical IDs (e.g., `http::GET::/api/users/{id}`) and matched across repos to detect orphan providers/consumers and mismatches.\n\n## Per-Community Skills\n\n`gortex init --skills` (default on) analyzes your codebase, detects functional communities via Louvain clustering, and generates targeted SKILL.md files that Claude Code auto-discovers:\n\n```bash\n# Runs as part of `gortex init` by default — community generation is folded in\ngortex init\n\n# Tune or disable:\ngortex init --skills-min-size 5 --skills-max 10\ngortex init --no-skills\n```\n\nEach generated skill includes:\n- **Community metadata** — size, file count, cohesion score\n- **Key files table** — files and their symbols\n- **Entry points** — main functions, handlers, controllers detected via process analysis\n- **Cross-community connections** — which other areas this community interacts with\n- **MCP tool invocations** — pre-written `get_communities`, `smart_context`, `find_usages` calls\n\nFor Claude Code, skills are written to `.claude/skills/generated/\u003cDirName\u003e/SKILL.md`, and a routing table is inserted into `CLAUDE.md` between `\u003c!-- gortex:communities:start/end --\u003e` markers. Every other detected agent gets the same routing table inside its per-repo instructions surface (`AGENTS.md` for Codex/OpenCode, `.windsurfrules` for Windsurf, `GEMINI.md` for Gemini CLI, `.cursor/rules/gortex-communities.mdc` for Cursor, etc.) — so the routing is consistent across tools on the same repo.\n\n## Semantic Search\n\nHybrid BM25 + vector search with Reciprocal Rank Fusion (RRF). Multiple embedding tiers:\n\n```bash\n# Built-in word vectors (always available, zero setup)\ngortex mcp --index . --embeddings\n\n# Ollama (best quality, local)\nollama pull nomic-embed-text\ngortex mcp --index . --embeddings-url http://localhost:11434\n\n# OpenAI (best quality, cloud)\ngortex mcp --index . --embeddings-url https://api.openai.com/v1 \\\n  --embeddings-model text-embedding-3-small\n```\n\n| Tier | Flag | Quality | Offline | Default build? |\n|------|------|---------|---------|----------------|\n| Hugot (pure Go) | `--embeddings` | Good (MiniLM-L6-v2) | Yes (model auto-downloads on first use) | **Yes** |\n| Built-in | `--embeddings` (when Hugot unavailable) | Basic (GloVe word averaging) | Yes | Yes |\n| API | `--embeddings-url` | Best (transformer model) | No | Yes |\n| ONNX | `--embeddings` + build tag | Best | Yes (model + libonnxruntime required) | No |\n| GoMLX | `--embeddings` + build tag | Good | Yes (XLA plugin auto-downloads) | No |\n\nThe default build ships with Hugot using the pure-Go ONNX runtime — no native dependencies, no manual model placement. The MiniLM-L6-v2 model downloads to `~/.cache/gortex/models/` on first use (~90 MB).\n\nOpt-in faster backends via build tags:\n```bash\ngo build -tags embeddings_onnx ./cmd/gortex/   # needs: brew install onnxruntime\ngo build -tags embeddings_gomlx ./cmd/gortex/  # auto-downloads XLA plugin\n```\n\n## Token Savings\n\nGortex tracks how many tokens it saves compared to naive file reads — per-call, per-session, and cumulative across restarts:\n\n- **Per-call:** `get_symbol_source` and other source-reading tools include a `tokens_saved` field in the response, showing the difference between reading the full file vs the targeted symbol.\n- **Session-level:** `graph_stats` returns a `token_savings` object with `calls_counted`, `tokens_returned`, `tokens_saved`, `efficiency_ratio`.\n- **Cumulative (cross-session):** `graph_stats` also returns `cumulative_savings` when persistence is wired — includes `first_seen`, `last_updated`, and `cost_avoided_usd` per model (Claude Opus/Sonnet/Haiku, GPT-4o, GPT-4o-mini). Backed by `~/.cache/gortex/savings.json`.\n\n```bash\n# Show totals + cost across all default models\ngortex savings\n\n# Highlight a single model (fuzzy match: \"opus\" → claude-opus-4)\ngortex savings --model opus\n\n# Machine-readable output\ngortex savings --json\n\n# Wipe cumulative totals\ngortex savings --reset\n\n# Override pricing (JSON array of {model, usd_per_m_input})\nGORTEX_MODEL_PRICING_JSON='[{\"model\":\"mycorp\",\"usd_per_m_input\":5}]' gortex savings\n```\n\nToken counts use **tiktoken (`cl100k_base`)** — the tokenizer Claude and GPT-4 actually use — via `github.com/pkoukk/tiktoken-go` with an embedded offline BPE loader, so no runtime downloads. The BPE is lazy-loaded on first call. If init fails for any reason, the package falls back to the legacy `chars/4` heuristic so metrics stay usable.\n\n## Graph Persistence\n\nGortex snapshots the graph to disk on shutdown and restores it on startup, with incremental re-indexing of only changed files:\n\n```bash\n# Default cache directory: ~/.cache/gortex/\ngortex mcp --index /path/to/repo\n\n# Custom cache directory\ngortex mcp --index /path/to/repo --cache-dir /tmp/gortex-cache\n\n# Disable caching\ngortex mcp --index /path/to/repo --no-cache\n```\n\nThe persistence layer uses a pluggable backend interface (`persistence.Store`). The default backend serializes as gob+gzip. Cache is keyed by repo path + git commit hash, with version validation to invalidate on binary upgrades.\n\n## Scale — battle-tested on large repos\n\nMeasured on an Apple Silicon laptop with the default CGO build:\n\n| Repository | Files | Nodes | Edges | Index time | Throughput | Peak heap |\n| ---------- | ----: | ----: | ----: | ---------: | ---------: | --------: |\n| [torvalds/linux](https://github.com/torvalds/linux) | 70,333 | 1,690,174 | 6,239,570 | ~3 min | 300 files/s | 5.07 GB |\n| [microsoft/vscode](https://github.com/microsoft/vscode) | 10,762 | 204,501 | 808,902 | ~1 min | 143 files/s | 580 MB |\n| zzet/gortex (self) | 430 | 5,583 | 53,830 | 3.4s | 127 files/s | 52 MB |\n\nParsing dominates wall time (65–80%); reference resolution and search-index build scale sub-linearly. Everything runs in-process — no external services, no database, no network.\n\n## Architecture\n\n```\ngortex binary\n  CLI (cobra)    ──\u003e MultiIndexer ──\u003e In-Memory Graph (shared, per-repo indexed)\n  MCP (stdio)    ──────────────────\u003e Query Engine (repo/project/ref scoping)\n  HTTP /v1/*     ──────────────────\u003e same tools + /v1/graph + /v1/events (SSE)\n  Daemon (unix)  ──────────────────\u003e shared graph for every MCP client, session isolation\n  MCP Prompts    ──────────────────\u003e (pre_commit, orientation, safe_to_change)\n  MCP Resources  ──────────────────\u003e (session, stats, schema, communities, processes)\n                   MultiWatcher \u003c── filesystem events (fsnotify, per-repo)\n                   CrossRepoResolver ──\u003e cross-repo edge creation (type-aware)\n                   Persistence ──\u003e gob+gzip snapshot (pluggable backend)\n```\n\n**Data flow:**\n1. On startup, loads cached graph snapshot if available; otherwise performs full indexing\n2. MultiIndexer walks each repo directory concurrently, dispatches files to language-specific extractors (tree-sitter)\n3. Extractors produce nodes (files, functions, types, etc.) and edges (calls, imports, defines, etc.) with type environment metadata\n4. In multi-repo mode, nodes get `RepoPrefix` and IDs become `\u003crepo_prefix\u003e/\u003cpath\u003e::\u003cSymbol\u003e`\n5. Resolver links cross-file references with type-aware method matching; CrossRepoResolver links cross-repo references with same-repo preference\n6. Query Engine answers traversal queries with optional repo/project/ref scoping\n7. MultiWatcher detects changes per-repo and surgically patches the graph (debounced per-file), then re-resolves cross-repo edges\n8. On shutdown, persists graph snapshot for fast restart\n\n## Graph Schema\n\n**Node kinds:** `file`, `function`, `method`, `type`, `interface`, `variable`, `import`, `package`\n\n**Edge kinds:** `calls`, `imports`, `defines`, `implements`, `extends`, `references`, `member_of`, `instantiates`\n\n**Multi-repo fields:** Nodes carry `repo_prefix` (empty in single-repo mode). Edges carry `cross_repo` (true when connecting nodes in different repos). Node IDs use `\u003crepo_prefix\u003e/\u003cpath\u003e::\u003cSymbol\u003e` format in multi-repo mode.\n\n## Language Support\n\nGortex indexes **92 languages** — see **[docs/languages.md](docs/languages.md)** for the full table (extensions, engine, extracted symbols per language).\n\n## Building\n\n```bash\nmake build          # Build with version from git tags\nmake test           # go test -race ./...\nmake bench          # Run all benchmarks\nmake lint           # golangci-lint\nmake fmt            # gofmt -s\nmake install        # go install with version ldflags\n```\n\nRequires Go 1.21+ and CGO enabled (for tree-sitter C bindings).\n\n## License\n\nGortex is **source-available** under a custom license based on PolyForm Small Business. See [LICENSE.md](LICENSE.md) for full terms.\n\n**Free for:** individuals, open-source projects, small businesses (\u003c50 employees / \u003c$500K revenue), nonprofits, education, government, socially critical orgs.\n\n**Commercial license required for:** organizations with 50+ employees or $500K+ revenue, competing products, resale/bundling. Contact [license@zzet.org](mailto:license@zzet.org).\n\n**Contributors:** active contributors listed in [CONTRIBUTORS.md](CONTRIBUTORS.md) receive a free non-competing commercial license for their employer.\n\n## Contributing\n\nSee [CONTRIBUTING.md](CONTRIBUTING.md) for guidelines on adding features, language extractors, and submitting PRs. Active contributors receive a [contributor commercial license](LICENSE.md#part-3-contributor-license).\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fzzet%2Fgortex","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fzzet%2Fgortex","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fzzet%2Fgortex/lists"}