feat: inject a neutral per-project workspace layout#1244
Conversation
There was a problem hiding this comment.
Pull request overview
Introduces a validated, typed WorkspaceLayout to support a neutral per-project runtime state directory (defaulting exactly to .astrid) and threads that selection through daemon boot, kernel, capsule lifecycle/discovery, hooks, gateway trust checks, WIT GC, and readiness metadata—while preserving existing public entry points via default-layout wrappers.
Changes:
- Add
astrid_core::dirs::WorkspaceLayout(with validation) plus a stable workspace-selection fingerprint used for daemon/CLI coherency. - Propagate workspace layout (and explicit workspace roots where needed) across kernel boot, discovery/install/remove/update paths, hooks discovery, gateway trusted source verification, and WIT GC.
- Publish atomic readiness metadata bound to
{workspace_root, layout}and reject CLI connections to daemons serving a different selection; document behavior inCHANGELOG.md.
Reviewed changes
Copilot reviewed 50 out of 51 changed files in this pull request and generated no comments.
Show a summary per file
| File | Description |
|---|---|
| crates/astrid-kernel/src/socket.rs | Writes atomic readiness metadata including workspace selection fingerprint. |
| crates/astrid-kernel/src/lib.rs | Stores and threads WorkspaceLayout through kernel boot and discovery/config wiring with default wrappers. |
| crates/astrid-kernel/src/kernel_router/mod.rs | Uses injected workspace layout for capsule discovery in router inventory. |
| crates/astrid-kernel/src/kernel_router/install.rs | Installs capsules with explicit workspace root/layout in blocking install paths. |
| crates/astrid-hooks/src/discovery.rs | Discovers/saves workspace hooks under the selected state directory (with layout-aware helpers). |
| crates/astrid-gateway/src/routes/sessions.rs | Routes session endpoints using workspace context to scope trusted capsule source verification. |
| crates/astrid-gateway/src/routes/models.rs | Threads workspace context through registry round-trips for trusted source verification. |
| crates/astrid-gateway/src/routes/mod.rs | Adds WorkspaceContext extension and builds routers with explicit workspace inputs. |
| crates/astrid-gateway/src/routes/capsule_sources.rs | Computes trusted capsule source IDs using explicit workspace root/layout (no implicit .astrid). |
| crates/astrid-gateway/src/lib.rs | Runs/builds gateway with explicit workspace root/layout and preserves defaults. |
| crates/astrid-daemon/src/lib.rs | Reads layout selection, loads config with layout, boots kernel with layout, spawns gateway with explicit workspace inputs, writes readiness metadata. |
| crates/astrid-core/src/dirs.rs | Defines WorkspaceLayout, validation rules, layout-aware workspace paths, and workspace selection fingerprinting. |
| crates/astrid-core/src/dirs_tests.rs | Adds regressions for layout validation, fingerprint identity, detection, and accessors. |
| crates/astrid-config/src/show.rs | Exposes config path reporting with explicit workspace layout. |
| crates/astrid-config/src/merge/types.rs | Updates workspace layer labeling to match selectable workspace state directory. |
| crates/astrid-config/src/loader.rs | Loads workspace config using injected layout (and tests to ensure no dual-scan). |
| crates/astrid-config/src/lib.rs | Adds public config loaders accepting an explicit WorkspaceLayout. |
| crates/astrid-config/src/defaults.toml | Updates documentation comment to reflect selectable workspace config. |
| crates/astrid-config/Cargo.toml | Adds astrid-core dependency for WorkspaceLayout. |
| crates/astrid-cli/src/workspace_layout.rs | Adds process-wide WorkspaceLayout storage (OnceLock) for CLI-wide access. |
| crates/astrid-cli/src/socket_client.rs | Adds connect_for_workspace helper ensuring daemon workspace selection coherency. |
| crates/astrid-cli/src/main.rs | Initializes workspace layout once from CLI parsing. |
| crates/astrid-cli/src/commands/wit.rs | Scopes WIT GC mark collection to selected workspace root/layout (no dual-scan). |
| crates/astrid-cli/src/commands/mcp/watch.rs | Connects MCP watch uplink via workspace-aware daemon validation. |
| crates/astrid-cli/src/commands/mcp/session_guard.rs | Connects MCP guard uplink via workspace-aware daemon validation. |
| crates/astrid-cli/src/commands/mcp/mod.rs | Connects MCP serve uplink via workspace-aware daemon validation. |
| crates/astrid-cli/src/commands/init.rs | Creates workspace dir using injected layout rather than hard-coded .astrid. |
| crates/astrid-cli/src/commands/headless.rs | Connects headless/snapshot flows using workspace-aware daemon validation. |
| crates/astrid-cli/src/commands/daemon.rs | Propagates workspace layout to spawned daemons and validates readiness metadata matches selection. |
| crates/astrid-cli/src/commands/config.rs | Loads/prints config using injected workspace layout. |
| crates/astrid-cli/src/commands/capsule/remove.rs | Resolves removal targets using injected workspace layout. |
| crates/astrid-cli/src/commands/capsule/meta.rs | Re-exports layout-aware capsule meta scanning helpers. |
| crates/astrid-cli/src/commands/capsule/live_load.rs | Avoids live reload/unload against mismatched daemon workspace selection. |
| crates/astrid-cli/src/commands/capsule/list.rs | Lists installed capsules using layout-aware scan. |
| crates/astrid-cli/src/commands/capsule/install.rs | Installs/unpacks and resolves targets using injected workspace layout. |
| crates/astrid-cli/src/commands/capsule/install_update.rs | Updates capsules without mixing user/workspace scopes and uses layout-aware scanning/target resolution. |
| crates/astrid-cli/src/commands/capsule/deps.rs | Builds dependency view from layout-aware installed capsule scan. |
| crates/astrid-cli/src/commands/capsule_verb.rs | Connects to daemon for capsule verb registry/execution via workspace-aware validation. |
| crates/astrid-cli/src/cli.rs | Adds global --workspace-state-dir / ASTRID_WORKSPACE_STATE_DIR typed option and tests. |
| crates/astrid-cli/src/bootstrap.rs | Loads config and connects to daemon using injected workspace layout for interactive flows. |
| crates/astrid-capsule/src/discovery.rs | Discovers manifests in an explicit workspace root/layout (no implicit .astrid). |
| crates/astrid-capsule-install/src/wit.rs | Updates docs to reflect workspace installs under selected project state dir. |
| crates/astrid-capsule-install/src/paths.rs | Resolves install targets using explicit workspace root/layout; adds tests. |
| crates/astrid-capsule-install/src/meta.rs | Scans installed capsules using explicit workspace root/layout; adds tests. |
| crates/astrid-capsule-install/src/manifest_check.rs | Checks imports/exports using explicit workspace root/layout (no implicit scan). |
| crates/astrid-capsule-install/src/local.rs | Installs from local path using explicit workspace root/layout and layout-aware checks/paths. |
| crates/astrid-capsule-install/src/lib.rs | Re-exports new layout-aware install/discovery APIs. |
| crates/astrid-capsule-install/src/contracts.rs | Updates comments to reflect “no project state” reads on daemon fail-closed path. |
| crates/astrid-capsule-install/src/archive.rs | Unpacks/installs using explicit workspace root/layout and layout-aware local install. |
| CHANGELOG.md | Documents new workspace layout selection and coherency behavior under [Unreleased]. |
| Cargo.lock | Records astrid-config’s new dependency on astrid-core. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
b802249 to
225b2da
Compare
## Linked Issue Closes #1241 Refs #1237 and astrid-runtime/rfcs#36. ## Summary Replaces gateway-side audit authority inference with the kernel's live principal/device capability evaluator. Historical and streaming audit views now narrow through the same runtime policy, with no AOS-specific role, key exposure or caller-selected identity. ## Changes - add an additive borrowed `CapabilityCheck` constructor while preserving the existing constructor and owned errors - expose one doc-hidden boolean kernel evaluator for a principal, optional device and capability - inject the in-process evaluator through the gateway runner and an additive embedded-router builder; the default router remains self-only - evaluate historical audit authority after the asynchronous log read and at every pagination record boundary - re-evaluate `audit:read_all` for every live SSE event - preserve self visibility after malformed, unknown, revoked, disabled, group-revoked or scope-denied authority - keep raw audit cursor positions stable while live principal narrowing filters same-second batches - bind new cursors to immutable audit-entry identity and effective visibility scope so same-second appends cannot shift the page boundary and widening or a principal change requires a restart - reject unsafe scope changes before visible, hidden and cursor-skipped rows instead of returning a partial page or false end-of-results - accept legacy timestamp/raw-offset cursors only for the unambiguous default self view - suppress continuation cursors at true physical EOF while retaining a scope-bound cursor when hidden rows make a later widening unsafe - pin the gateway's live `audit:read_all` enforcement constant and require it to resolve through capability-registry revision 1 - retain the pair-device terminal audit distinctions already present on `main` - add a race-free pre-bound listener entrypoint for the real HTTP SSE regression - expose the same live evaluator boundary to trusted in-process router embeddings without exposing the internal probe type - document the connect-info make-service requirement for both public router builders so unauthenticated redeem throttling keeps the real peer address, and make the default builder's self-only audit policy explicit - document the additive runner/router migration path for co-located callers that need audit firehose visibility - accept hyphen-leading opaque invite tokens in both CLI redeem and revoke paths so every base64url token the runtime issues remains usable ## Verification - exact signed head: `bf3eb251164f1c20e47fb9f3e841677d9efecc02` - all 20 commits above `d85fb10663c21d08fc43d39d939cfbb5a023cafd` have good Joshua committer signatures - `cargo fmt --all -- --check` - `git diff --check` - `cargo doc -p astrid-gateway --no-deps` - `cargo test -p astrid-gateway` — 160 unit, 7 CORS, 10 models and 18 router tests pass - `cargo test -p astrid-kernel runtime_policy_tests` — 8 tests pass - focused audit pagination suite — 17 tests pass, including same-second insertion, missing-anchor and pre-anchor authority-widening regressions - focused registry enforcement assertion — 1 test passes - `cargo clippy -p astrid-gateway -p astrid-kernel --all-targets -- -D warnings` - all 12 production-root CLI parser tests pass, including redeem and revoke with a generated-token shape beginning in `-` - `cargo clippy -p astrid --all-targets -- -D warnings` - the replacement GitHub matrix is the execution gate for the combined workspace ## Compatibility The public HTTP shape, WIT contracts, persisted authority, gateway state and existing runner entrypoints remain unchanged. The new kernel evaluator is boolean and doc-hidden. The internal typed gateway probe remains private; trusted in-process embedders receive an additive generic callback builder with the same fail-closed policy boundary. When #1244 is refreshed after this PR, its workspace-aware gateway runner must retain this live capability probe across normal, TLS and pre-bound listener paths. ## Checklist - [x] Linked to an issue - [x] `CHANGELOG.md` updated under `[Unreleased]` --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
1c8ddd3 to
73a8ea0
Compare
|
@copilot review |
Reviewed the current state of the PR. Full test suite passes (0 failures). Key areas checked:
Readiness metadata — written atomically via temp-file rename with Handshake ordering —
Minor observation (no change required): the trailing No actionable issues found. |
Linked Issue
Closes #1243
Summary
Introduces one validated neutral project workspace layout while preserving
.astridas standalone Astrid's exact default and leaving existing public Rust entry points compatible.Changes
WorkspaceSelectionand global CLI--workspace-state-dir/ASTRID_WORKSPACE_STATE_DIRselectionps,top, andwhopaths0700without rewriting its contentsThe filesystem checks reject persistent redirects and special files. As with ordinary path-based filesystem APIs, a malicious process running as the same user could still race an individual path after validation; descriptor-relative traversal is outside this change.
Verification
cargo metadata --lockedcargo fmt --all -- --checkgit diff --checkcargo test --workspace --locked -- --quietcargo clippy --workspace --all-targets --all-features --locked -- -D warningsNo release, tag, or publication is created by this pull request.
Checklist
CHANGELOG.mdupdated under[Unreleased]