Skip to content

feat: client-agnostic backend — workspace-relative source_uri (client + infra)#189

Open
riley0227 wants to merge 2 commits intodevfrom
feat/client-backend-separation
Open

feat: client-agnostic backend — workspace-relative source_uri (client + infra)#189
riley0227 wants to merge 2 commits intodevfrom
feat/client-backend-separation

Conversation

@riley0227
Copy link
Copy Markdown
Contributor

@riley0227 riley0227 commented Apr 10, 2026

Summary

Client + infra half of the client/backend separation. Removes the HOME bind mount entirely and switches the client to emit workspace-relative paths as the canonical source_uri so no absolute host paths ever cross the wire.

What changed

Client (ingestion pipeline)

  • core-ingestion/src/types.ts, ix-cli/src/client/types.tsPatchSource gains workspaceId?: string; source.uri is now documented as a workspace-relative POSIX path. HealthResponse gains schema_version?: number.
  • ix-cli/src/cli/commands/ingest.ts:
    • Computes workspaceRoot + workspaceId (SHA-256 of workspaceRoot abs path) once per run.
    • Converts absolute paths to workspace-relative before dispatching to parseFile, buildGlobalResolutionIndex, and the parse pool, so every deterministic node/patch/edge/chunk ID hashes relative paths.
    • Tags every built patch's source with workspaceId.
    • loadExistingHashes now queries the backend with relative paths and maps the response back onto absolute keys.
    • On startup, compares /v1/health schema_version against CLIENT_EXPECTED_SCHEMA_VERSION = 2 and forces a clean re-ingest on mismatch (node IDs change when the graph format flips from absolute to relative).
  • ix-cli/src/cli/config.ts — new absoluteFromSourceUri helper that joins a workspace-relative source_uri against the active workspace root for commands that still need to open files off disk.
  • ix-cli/src/cli/format.tsrelativePath is a no-op for already-relative input.
  • ix-cli/src/cli/commands/read.ts — resolves sourceUri via absoluteFromSourceUri before any fs.* call so the graph's relative paths still map to real files.

Infra

  • docker-compose.standalone.yml — removed the HOME bind mount from the memory-layer service. Closes the privacy hole where the entire user HOME directory was bind-mounted (read-only) into the backend container.
  • scripts/backend.sh, scripts/dev/shutdown.sh, scripts/install/install.sh — removed IX_HOST_MOUNT_ROOT / IX_CONTAINER_MOUNT_ROOT exports. dc() wrappers preserved for Windows/MINGW compose dispatch.

Must land with

ix-infrastructure/ix-memory-layer PR on feat/client-agnostic-backenddev:

  • Rewrites StalenessDetector to pure graph comparison (no java.nio.file).
  • Bumps /v1/health schema_version to 2.
  • Updates RoutesSpec / StalenessDetectorSpec accordingly.

Test plan

  • Run ix map --force against a backend built from the paired backend branch. Confirm every patch's source.uri is workspace-relative and source.workspaceId is populated.
  • Run ix read <symbol> and ix read <file> — confirm files still resolve via absoluteFromSourceUri.
  • Confirm docker compose -f docker-compose.standalone.yml up starts cleanly with no HOME bind mount and memory-layer still serves /v1/health.
  • Verify schema mismatch forces re-ingest: start backend on old image (schema_version 1 or absent) and confirm the CLI prints the mismatch warning and flips opts.force.
  • Audit a handful of graph queries end-to-end (ix impact, ix overview, ix search).

NEEDS HEAVY REVIEW: "needs heavy review as didnt verify this change for
additional bug for all of this, this could be completely wrong"

Client half of the client/backend separation. The backend no longer needs
host filesystem access; this side makes the client emit workspace-relative
paths as the canonical source_uri so no absolute host paths ever leave the
client process.

Client:
- core-ingestion/src/types.ts, ix-cli/src/client/types.ts:
  PatchSource gains an optional workspaceId field. Documented that source.uri
  is now a workspace-relative POSIX path, not an absolute host path.
- ix-cli/src/cli/commands/ingest.ts:
  Compute workspaceRoot + workspaceId (SHA-256 of workspaceRoot abs path)
  once per run. Convert absolute paths to workspace-relative before
  dispatching to parseFile, buildGlobalResolutionIndex, and the parse pool,
  so every deterministic node/patch/edge/chunk ID hashes relative paths.
  Keep absolute paths only for local fs reads. Tag every built patch's
  source with workspaceId. loadExistingHashes now queries the backend with
  relative paths and maps the response back onto absolute keys.
  On ingest startup, compare backend /v1/health schema_version against
  CLIENT_EXPECTED_SCHEMA_VERSION=2 and force full re-ingest on mismatch
  (node IDs change when the graph format flips from absolute to relative).
- ix-cli/src/cli/config.ts:
  New absoluteFromSourceUri helper — joins a workspace-relative source_uri
  against the active workspace root so commands that need to open files off
  disk (ix read) can still do so.
- ix-cli/src/cli/format.ts:
  relativePath now treats already-relative input as a no-op.
- ix-cli/src/cli/commands/read.ts:
  Resolves sourceUri via absoluteFromSourceUri before any fs.* call so the
  graph's workspace-relative paths still map to real files.

Infra:
- docker-compose.standalone.yml:
  Removed the HOME bind mount (source: ${IX_HOST_MOUNT_ROOT:-$HOME},
  target: $HOME, read_only: true) from the memory-layer service. The backend
  is now client-agnostic and never reads host files. Closes the privacy hole
  where the entire user HOME directory was bind-mounted into the backend
  container.
- scripts/backend.sh, scripts/dev/shutdown.sh, scripts/install/install.sh:
  Removed the IX_HOST_MOUNT_ROOT / IX_CONTAINER_MOUNT_ROOT exports that fed
  that bind mount. dc() helpers remain so Windows/MINGW compose dispatch
  still works.

Requires the matching ix-memory-layer change (StalenessDetector rewrite +
schema_version bump) on feat/client-agnostic-backend.

Every modified file carries a "NEEDS HEAVY REVIEW" banner. This change has
NOT been verified end-to-end and may be completely wrong — reviewers should
treat every line as suspect until validated against a real ingest + ix read
round-trip with the client-agnostic backend image.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant