You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
add walk-up config discovery and configurable source root (#270)
* add walk-up config discovery and source_root YAML field
Implements propose/active/DIRS-HIERARCHY-PROPOSE.md as a single PR.
- discover_project_root(start) walks from start upward looking for
.java-codebase-rag.yml/.yaml, first match wins, stops at $HOME
(inclusive). Mirrors git's .git discovery.
- resolve_operator_config() uses two-phase resolution: phase 1 finds
the config file directory via walk-up, phase 2 resolves effective
source root from CLI > env > YAML source_root > discovery > cwd.
- server.py _project_root() and _resolve_lancedb_uri() use walk-up
when JAVA_CODEBASE_RAG_SOURCE_ROOT is unset.
- cli.py init emits a soft warning when a parent config is detected.
- YAML config gains an optional source_root field resolved relative
to the config file directory (not cwd).
- mcp.json.example shows minimal zero-env-var config.
- README and CONFIGURATION docs updated for walk-up and source_root.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
* fix server YAML source_root resolution and add review tests
- server.py main() passes source_root=None to resolve_operator_config
so YAML source_root is resolved in Phase 2, not skipped. The previous
code passed _project_root() as source_root, which caused the CLI path
to skip YAML resolution (C1 from code review).
- cli.py _cmd_diagnose_ignore uses cfg.source_root instead of
server._project_root() to avoid divergence when YAML source_root
is set (I3 from code review).
- add test for YAML source_root resolution via server path.
- add tests for init parent-config warning detection.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
* fix server startup tests for source_root=None change
Update test_mcp_server_loads_yaml_config_at_startup and
test_mcp_server_yaml_config_precedence_env_over_yaml to expect
resolve_operator_config(source_root=None) instead of the old
resolve_operator_config(source_root=_project_root()).
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
---------
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
Copy file name to clipboardExpand all lines: README.md
+6-6Lines changed: 6 additions & 6 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -84,6 +84,8 @@ If vector hits come back and graph expansion adds neighbor symbols, the install
84
84
85
85
## Wire into an MCP host
86
86
87
+
The server discovers your project automatically: it walks up from cwd looking for `.java-codebase-rag.yml` (or `.yaml`), like git finds `.git`. No env vars required if you have a YAML config in your project tree. For full precedence details, see [`docs/CONFIGURATION.md`](./docs/CONFIGURATION.md).
88
+
87
89
### Claude Code
88
90
89
91
With the package installed, the console script `java-codebase-rag-mcp` is on your `PATH`. Register it project-scoped:
@@ -92,7 +94,7 @@ With the package installed, the console script `java-codebase-rag-mcp` is on you
92
94
claude mcp add --transport stdio java-codebase-rag -- java-codebase-rag-mcp
93
95
```
94
96
95
-
Then set env vars (`JAVA_CODEBASE_RAG_INDEX_DIR`, `JAVA_CODEBASE_RAG_SOURCE_ROOT`, `SBERT_MODEL`, …) in `.mcp.json` or your shell profile. For a project-scoped`.mcp.json` template, see [`mcp.json.example`](./mcp.json.example). Official docs: [Claude Code settings](https://docs.anthropic.com/en/docs/claude-code/settings).
97
+
No env vars needed — the server walks up from cwd to find `.java-codebase-rag.yml`. For a minimal`.mcp.json` template, see [`mcp.json.example`](./mcp.json.example). Official docs: [Claude Code settings](https://docs.anthropic.com/en/docs/claude-code/settings).
The server discovers the project via walk-up from the cwd of the MCP host process. If your Java project is not the cwd, either set `JAVA_CODEBASE_RAG_SOURCE_ROOT` in the `env` block or add a `source_root` field to `.java-codebase-rag.yml` (see [`docs/CONFIGURATION.md`](./docs/CONFIGURATION.md)).
114
+
115
115
See [`mcp.json.example`](./mcp.json.example) for the same shape in `.mcp.json` (Claude Code project-scoped) form.
Copy file name to clipboardExpand all lines: docs/CONFIGURATION.md
+30-5Lines changed: 30 additions & 5 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -22,6 +22,22 @@ For the architecture rationale (the GPS metaphor, three-layer design, future wor
22
22
23
23
The operator-facing surface is **six** variables (plus MCP-only `JAVA_CODEBASE_RAG_SOURCE_ROOT` below). Precedence for knobs that also exist as CLI flags or YAML entries is **CLI flag > env var > YAML > built-in default** (see [`JAVA-CODEBASE-RAG-CLI.md`](./JAVA-CODEBASE-RAG-CLI.md)).
24
24
25
+
### Source root discovery and precedence
26
+
27
+
The server and CLI resolve the effective Java source root through a precedence chain:
28
+
29
+
| Priority | Source | How it resolves |
30
+
|---|---|---|
31
+
| 1 (highest) | CLI `--source-root`| Absolute, or relative to cwd |
32
+
| 2 |`JAVA_CODEBASE_RAG_SOURCE_ROOT` env var | Absolute, or relative to cwd |
33
+
| 3 | YAML `source_root` field |**Relative to the config file directory** (not cwd) |
34
+
| 4 | Walk-up discovery | Walk from cwd upward to find `.java-codebase-rag.yml`; uses the config file's directory as source root |
35
+
| 5 (lowest) | cwd | No config found, no YAML override |
36
+
37
+
Walk-up checks each directory from cwd upward for `.java-codebase-rag.yml` or `.java-codebase-rag.yaml`. The **first match wins** (closest to cwd). The walk stops at `$HOME` (inclusive — `$HOME` itself is checked) or the filesystem root. This mirrors how git finds `.git`.
38
+
39
+
### Variables
40
+
25
41
| Variable | Purpose |
26
42
|---|---|
27
43
|`JAVA_CODEBASE_RAG_INDEX_DIR`| Local filesystem **directory** for Lance tables, the Kuzu file `code_graph.kuzu`, and cocoindex state (`cocoindex.db`). Not a `lancedb://` or cloud URI — use a path. Default: `./.java-codebase-rag/` under the resolved Java tree root. |
@@ -31,14 +47,14 @@ The operator-facing surface is **six** variables (plus MCP-only `JAVA_CODEBASE_R
31
47
|`JAVA_CODEBASE_RAG_RUN_HEAVY`| Test gate: set to `1` / `true` / `yes` to run the slow cocoindex + Lance end-to-end test (`pytest`); not used in normal operator workflows. |
32
48
|`JAVA_CODEBASE_RAG_HINTS_ENABLED`| When `0` / `false` / `no`, suppress `hints_structured` and `advisories` from all MCP tool responses. Overridable via `.java-codebase-rag.yml``hints.enabled`. Default: enabled. |
33
49
34
-
**MCP host launchers** also set `JAVA_CODEBASE_RAG_SOURCE_ROOT` to the Java repository root when it differs from the server process cwd (see `mcp.json.example` in the repo root).
50
+
**MCP host launchers** also set `JAVA_CODEBASE_RAG_SOURCE_ROOT` to the Java repository root when it differs from the server process cwd (see `mcp.json.example` in the repo root). When the env var is unset, the server walks up from cwd to discover the config automatically.
35
51
36
52
Only the names in the table above (plus `JAVA_CODEBASE_RAG_SOURCE_ROOT` for MCP hosts) are read as configuration. Project config belongs in **`.java-codebase-rag.yml`** (or `.yaml`).
37
53
38
54
**Paths and conventions** (for scripts and operators):
39
55
40
56
-**`JAVA_CODEBASE_RAG_INDEX_DIR`** — filesystem path to the index directory (not a URI). Lance opens this directory; Kuzu is always `<index-dir>/code_graph.kuzu`; cocoindex keeps **`cocoindex.db`** next to them.
41
-
-**Java tree root** — CLI: `--source-root` (else cwd). MCP stdio: set `JAVA_CODEBASE_RAG_SOURCE_ROOT`when the Java repo root differs from the server process cwd.
57
+
-**Java tree root** — CLI: `--source-root` (else walk-up discovery, else cwd). MCP stdio: `JAVA_CODEBASE_RAG_SOURCE_ROOT`env var (else walk-up from cwd). YAML: `source_root` field resolved relative to the config file directory.
42
58
-**`microservice_roots`** — configure only under **`microservice_roots:`** in `.java-codebase-rag.yml` (or `.yaml`).
43
59
-**Chunk context diagnostics / heavy tests** — `JAVA_CODEBASE_RAG_DEBUG_CONTEXT`, `JAVA_CODEBASE_RAG_RUN_HEAVY` (see the table above).
A single file at the project root (the directory you pass as `--source-root`, or cwd) holds everything that isn't an environment variable. The two accepted filenames are `.java-codebase-rag.yml` and `.java-codebase-rag.yaml`; if both exist, `.yml` wins.
67
+
A single file at the project root (the directory you pass as `--source-root`, or discovered via walk-up, or cwd) holds everything that isn't an environment variable. The two accepted filenames are `.java-codebase-rag.yml` and `.java-codebase-rag.yaml`; if both exist, `.yml` wins.
52
68
53
69
**All keys are optional.** A project with no YAML at all uses built-in defaults plus env vars. Add only the keys you need.
54
70
55
71
```yaml
56
72
# .java-codebase-rag.yml — full reference, every key annotated.
57
-
# Place at the project root (same directory you pass as --source-root).
73
+
# Place at the project root (same directory you pass as --source-root),
74
+
# or anywhere above it — the server walks up from cwd to find it.
# Index directory: where Lance tables, code_graph.kuzu, and cocoindex.db live.
62
86
# - Tilde (`~`) is expanded; `$VAR` is NOT (use absolute paths or `~`).
63
87
# - Relative paths resolve against source_root, not cwd.
@@ -171,6 +195,7 @@ async_producer_overrides:
171
195
172
196
| Field | Expanded? | Notes |
173
197
|---|---|---|
198
+
| `source_root` | partial | `~` expanded; `$VAR` is NOT expanded. Relative paths resolve against the **config file directory** (not cwd). |
174
199
| `index_dir` | partial | `~` expanded; `$VAR` is NOT expanded. Relative paths resolve against `source_root`. |
175
200
| `embedding.model` (when path-shaped) | yes | Path-shape = starts with `/`, `./`, `../`, `~`, or contains `$`. Plain `org/name` is treated as a hub id and passed through. Applies to the value after CLI > env > YAML > default precedence. Long-lived MCP hosts also apply the same expansion when reading `SBERT_MODEL` from the process environment (so table metadata and search agree with `index_common` defaults). |
- **The file must be at `source_root`**, not in `$HOME`. The MCP server reads `JAVA_CODEBASE_RAG_SOURCE_ROOT` to find it; the CLI uses `--source-root` (else cwd).
207
+
- **The file is discovered by walking up from cwd** — like git finds `.git`. Place it at or above your project root. The walk stops at `$HOME` (inclusive). You can also set `JAVA_CODEBASE_RAG_SOURCE_ROOT` or use `--source-root` to bypass discovery entirely.
183
208
- **Don't commit secrets** into this YAML — it sits next to your source tree and is read by every operator who clones it.
184
209
- **Rebuild after editing brownfield overrides.** Run a full `java-codebase-rag reprocess` (no flags) so Lance and Kuzu stay coherent, or use `--graph-only` / `--vectors-only` when you know only one store needs invalidation. Editing `embedding.model` requires a vector rebuild (`reprocess` or `--vectors-only`).
185
210
- **Diagnose what's loaded.** `java-codebase-rag meta` prints the resolved config and each value's `*_source` (`cli` / `env` / `yaml` / `default`) — see `embedding_model_source`, `embedding_device_source`, `index_dir_source`.
0 commit comments