feat: add sealed probes for private repositories - #6673
Conversation
Add trusted offline repository staging and a no-network probe broker. Run Python in hardened per-invocation sandboxes and expose a narrow CLI with four-symbol result closure. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: 21364940-ae16-48b5-a577-321ef7f3fc74
|
| Metric | Base | PR | Delta |
|---|---|---|---|
| Lines | 99.11% | 98.82% | 📉 -0.29% |
| Statements | 99.03% | 98.48% | 📉 -0.55% |
| Functions | 99.53% | 99.24% | 📉 -0.29% |
| Branches | 95.67% | 95.15% | 📉 -0.52% |
📁 Per-file Coverage Changes (4 files)
| File | Lines (Before → After) | Statements (Before → After) |
|---|---|---|
src/services/optional-services.ts |
100.0% → 100.0% (+0.00%) | 100.0% → 99.1% (-0.94%) |
src/commands/main-action.ts |
99.3% → 99.3% (+0.01%) | 98.7% → 98.7% (+0.02%) |
src/commands/build-config.ts |
97.1% → 97.2% (+0.08%) | 97.1% → 97.2% (+0.08%) |
src/log-directory-setup.ts |
96.2% → 100.0% (+3.78%) | 96.3% → 100.0% (+3.71%) |
✨ New Files (10 files)
src/parsers/sealed-probe-parser.ts: 100.0% linessrc/sealed-probe/manager.ts: 91.5% linessrc/sealed-probe/paths.ts: 100.0% linessrc/sealed-probe/preflight.ts: 88.7% linessrc/sealed-probe/protocol.ts: 93.0% linessrc/sealed-probe/skill.ts: 100.0% linessrc/sealed-probe/staging.ts: 95.7% linessrc/sealed-probe/types.ts: 100.0% linessrc/services/sealed-probe-service.ts: 100.0% linessrc/types/sealed-probe-options.ts: 100.0% lines
Coverage comparison generated by scripts/ci/compare-coverage.ts
There was a problem hiding this comment.
Pull request overview
Adds sealed probes for bounded computation over staged private repositories.
Changes:
- Adds configuration, validation, staging, protocol, broker, and lifecycle integration.
- Adds hardened probe containers, agent wrapper/skill, and extensive tests.
- Publishes the sealed-probe image through the release workflow.
Show a summary per file
| File | Description |
|---|---|
src/types/wrapper-config.ts |
Adds sealed-probe options. |
src/types/sealed-probe-options.ts |
Defines configuration and defaults. |
src/types/index.ts |
Exports sealed-probe types. |
src/services/sealed-probe-service.ts |
Builds broker and agent wiring. |
src/services/sealed-probe-service.test.ts |
Tests service assembly. |
src/services/sealed-probe-compose.test.ts |
Tests Compose integration. |
src/services/optional-services.ts |
Registers the optional broker. |
src/services/agent-volumes/docker-socket.ts |
Shares Docker socket resolution. |
src/services/agent-environment/excluded-vars.ts |
Excludes GitHub tokens. |
src/services/agent-environment/excluded-vars.test.ts |
Tests credential exclusion. |
src/sealed-probe/wrapper.test.ts |
Tests agent wrapper behavior. |
src/sealed-probe/workflow-integration.test.ts |
Tests staging order. |
src/sealed-probe/types.ts |
Defines staging data types. |
src/sealed-probe/skill.ts |
Generates agent guidance. |
src/sealed-probe/skill.test.ts |
Tests generated guidance. |
src/sealed-probe/protocol.ts |
Implements protocol validation. |
src/sealed-probe/protocol.test.ts |
Tests protocol behavior. |
src/sealed-probe/protocol-parity.test.ts |
Checks TS/JS parity. |
src/sealed-probe/probe-seccomp.test.ts |
Checks seccomp invariants. |
src/sealed-probe/preflight.ts |
Adds fail-closed preflight. |
src/sealed-probe/preflight.test.ts |
Tests preflight checks. |
src/sealed-probe/paths.ts |
Defines artifact paths. |
src/sealed-probe/paths.test.ts |
Tests path derivation. |
src/sealed-probe/staging.ts |
Stages private repository seeds. |
src/sealed-probe/staging.test.ts |
Tests secure staging. |
src/sealed-probe/manager.ts |
Orchestrates setup and teardown. |
src/sealed-probe/manager.test.ts |
Tests lifecycle management. |
src/sealed-probe/broker.test.ts |
Tests broker and launcher behavior. |
src/sealed-probe/end-to-end.test.ts |
Tests wrapper-to-broker flow. |
src/schema.test.ts |
Registers the schema section. |
src/parsers/sealed-probe-parser.ts |
Normalizes configuration. |
src/parsers/sealed-probe-parser.test.ts |
Tests normalization. |
src/image-tag.ts |
Adds sealed-probe digests. |
src/image-tag.test.ts |
Tests digest handling. |
src/container-start.test.ts |
Updates cleanup expectations. |
src/container-lifecycle.ts |
Cleans conflicting brokers. |
src/constants.ts |
Defines the broker name. |
src/config-mapper.ts |
Maps file configuration. |
src/config-file.ts |
Adds raw config typing. |
src/config-file-sealed-probes-validation.test.ts |
Tests schema validation. |
src/config-file-mapping.test.ts |
Tests config mapping. |
src/config-file-loading.test.ts |
Tests stdin loading. |
src/commands/main-action.ts |
Integrates lifecycle cleanup. |
src/commands/build-config.ts |
Builds normalized configuration. |
src/commands/build-config.test.ts |
Tests config construction. |
src/cli-workflow.ts |
Stages seeds before startup. |
src/awf-config-schema.json |
Adds runtime schema. |
docs/awf-config.schema.json |
Publishes configuration schema. |
docs/awf-config-spec.md |
Documents the security model. |
containers/sealed-probe/probe-seccomp.json |
Defines probe syscall policy. |
containers/sealed-probe/Dockerfile |
Builds broker/probe image. |
containers/sealed-probe/broker/workspace.js |
Manages invocation copies. |
containers/sealed-probe/broker/server.js |
Serves the Unix-socket API. |
containers/sealed-probe/broker/protocol.js |
Implements broker protocol. |
containers/sealed-probe/broker/probe-runner.js |
Launches probe containers. |
containers/sealed-probe/broker/healthcheck.js |
Checks broker health. |
containers/sealed-probe/broker/framing.js |
Parses bounded requests. |
containers/sealed-probe/broker/config.js |
Loads broker configuration. |
containers/sealed-probe/broker/broker.js |
Coordinates probe execution. |
containers/sealed-probe/broker/audit.js |
Writes protected diagnostics. |
containers/agent/sealed-probe-wrapper.sh |
Adds the agent CLI. |
containers/agent/entrypoint.sh |
Activates the CLI. |
containers/agent/Dockerfile |
Packages the wrapper. |
CLAUDE.md |
Documents the architecture. |
.github/workflows/release.yml |
Publishes and signs the image. |
Review details
Tip
Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
- Files reviewed: 65/65 changed files
- Comments generated: 10
- Review effort level: Medium
|
@copilot Fix the code for all comments in this review thread. When a review comment includes a suggested change, apply the suggestion exactly. Do not make changes beyond what is described in the linked review thread. |
All ten review comments addressed in commit
|
Build and publish both container targets, keep readiness broker-private, and materialize writable repository copies inside bounded tmpfs. Add a real Docker isolation integration test for the probe runtime. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: 21364940-ae16-48b5-a577-321ef7f3fc74
|
✅ Copilot review passed with no inline comments. @lpcox Add the |
Validate opened descriptors directly before reading credential-scan fixtures. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: 21364940-ae16-48b5-a577-321ef7f3fc74
|
| Metric | Base | PR | Delta |
|---|---|---|---|
| Lines | 99.11% | 98.76% | 📉 -0.35% |
| Statements | 99.03% | 98.41% | 📉 -0.62% |
| Functions | 99.53% | 99.13% | 📉 -0.40% |
| Branches | 95.67% | 95.03% | 📉 -0.64% |
📁 Per-file Coverage Changes (4 files)
| File | Lines (Before → After) | Statements (Before → After) |
|---|---|---|
src/services/optional-services.ts |
100.0% → 100.0% (+0.00%) | 100.0% → 99.1% (-0.93%) |
src/commands/main-action.ts |
99.3% → 99.3% (+0.01%) | 98.7% → 98.7% (+0.02%) |
src/commands/build-config.ts |
97.1% → 97.2% (+0.08%) | 97.1% → 97.2% (+0.08%) |
src/log-directory-setup.ts |
96.2% → 100.0% (+3.78%) | 96.3% → 100.0% (+3.71%) |
✨ New Files (10 files)
src/parsers/sealed-probe-parser.ts: 100.0% linessrc/sealed-probe/manager.ts: 88.5% linessrc/sealed-probe/paths.ts: 100.0% linessrc/sealed-probe/preflight.ts: 88.7% linessrc/sealed-probe/protocol.ts: 93.0% linessrc/sealed-probe/skill.ts: 100.0% linessrc/sealed-probe/staging.ts: 95.9% linessrc/sealed-probe/types.ts: 100.0% linessrc/services/sealed-probe-service.ts: 95.3% linessrc/types/sealed-probe-options.ts: 100.0% lines
Coverage comparison generated by scripts/ci/compare-coverage.ts
1 similar comment
|
| Metric | Base | PR | Delta |
|---|---|---|---|
| Lines | 99.11% | 98.76% | 📉 -0.35% |
| Statements | 99.03% | 98.41% | 📉 -0.62% |
| Functions | 99.53% | 99.13% | 📉 -0.40% |
| Branches | 95.67% | 95.03% | 📉 -0.64% |
📁 Per-file Coverage Changes (4 files)
| File | Lines (Before → After) | Statements (Before → After) |
|---|---|---|
src/services/optional-services.ts |
100.0% → 100.0% (+0.00%) | 100.0% → 99.1% (-0.93%) |
src/commands/main-action.ts |
99.3% → 99.3% (+0.01%) | 98.7% → 98.7% (+0.02%) |
src/commands/build-config.ts |
97.1% → 97.2% (+0.08%) | 97.1% → 97.2% (+0.08%) |
src/log-directory-setup.ts |
96.2% → 100.0% (+3.78%) | 96.3% → 100.0% (+3.71%) |
✨ New Files (10 files)
src/parsers/sealed-probe-parser.ts: 100.0% linessrc/sealed-probe/manager.ts: 88.5% linessrc/sealed-probe/paths.ts: 100.0% linessrc/sealed-probe/preflight.ts: 88.7% linessrc/sealed-probe/protocol.ts: 93.0% linessrc/sealed-probe/skill.ts: 100.0% linessrc/sealed-probe/staging.ts: 95.9% linessrc/sealed-probe/types.ts: 100.0% linessrc/services/sealed-probe-service.ts: 95.3% linessrc/types/sealed-probe-options.ts: 100.0% lines
Coverage comparison generated by scripts/ci/compare-coverage.ts
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: 21364940-ae16-48b5-a577-321ef7f3fc74
|
| Metric | Base | PR | Delta |
|---|---|---|---|
| Lines | 99.11% | 99.20% | 📈 +0.09% |
| Statements | 99.03% | 99.10% | 📈 +0.07% |
| Functions | 99.53% | 99.45% | 📉 -0.08% |
| Branches | 95.67% | 95.75% | 📈 +0.08% |
📁 Per-file Coverage Changes (4 files)
| File | Lines (Before → After) | Statements (Before → After) |
|---|---|---|
src/services/optional-services.ts |
100.0% → 100.0% (+0.00%) | 100.0% → 99.1% (-0.93%) |
src/commands/main-action.ts |
99.3% → 99.3% (+0.01%) | 98.7% → 98.7% (+0.02%) |
src/commands/build-config.ts |
97.1% → 97.2% (+0.08%) | 97.1% → 97.2% (+0.08%) |
src/log-directory-setup.ts |
96.2% → 100.0% (+3.78%) | 96.3% → 100.0% (+3.71%) |
✨ New Files (10 files)
src/parsers/sealed-probe-parser.ts: 100.0% linessrc/sealed-probe/manager.ts: 100.0% linessrc/sealed-probe/paths.ts: 100.0% linessrc/sealed-probe/preflight.ts: 100.0% linessrc/sealed-probe/protocol.ts: 100.0% linessrc/sealed-probe/skill.ts: 100.0% linessrc/sealed-probe/staging.ts: 100.0% linessrc/sealed-probe/types.ts: 100.0% linessrc/services/sealed-probe-service.ts: 100.0% linessrc/types/sealed-probe-options.ts: 100.0% lines
Coverage comparison generated by scripts/ci/compare-coverage.ts
|
@copilot address the failed codeql ci checks |
Fixed in the latest commit. Both |
|
📰 VERDICT: Smoke Docker Sbx has concluded. All systems operational. This is a developing story. 🎤 |
|
🔌 Smoke Services — All services reachable! ✅ |
|
✨ The prophecy is fulfilled... Smoke Codex has completed its mystical journey. The stars align. 🌟 |
|
❌ Security Guard failed. Please review the logs for details. |
|
📡 Smoke OTel Tracing completed. All tracing scenarios validated. ✅ |
| // O_EXCL | O_NOFOLLOW: atomically create; fail if a symlink or existing file | ||
| // is already at this path (insecure-temp-file guard). | ||
| const fd = fs.openSync( | ||
| paths.seedMapPath, |
| // O_EXCL | O_NOFOLLOW: atomically create; fail if a symlink or existing file | ||
| // is already at this path (insecure-temp-file guard). | ||
| const fd = fs.openSync( | ||
| paths.skillPath, |
|
Chroot tests passed! Smoke Chroot - All security and functionality tests succeeded. |
|
✅ Build Test Suite completed successfully! |
|
| Metric | Base | PR | Delta |
|---|---|---|---|
| Lines | 99.11% | 99.20% | 📈 +0.09% |
| Statements | 99.03% | 99.10% | 📈 +0.07% |
| Functions | 99.53% | 99.45% | 📉 -0.08% |
| Branches | 95.67% | 95.75% | 📈 +0.08% |
📁 Per-file Coverage Changes (4 files)
| File | Lines (Before → After) | Statements (Before → After) |
|---|---|---|
src/services/optional-services.ts |
100.0% → 100.0% (+0.00%) | 100.0% → 99.1% (-0.93%) |
src/commands/main-action.ts |
99.3% → 99.3% (+0.01%) | 98.7% → 98.7% (+0.02%) |
src/commands/build-config.ts |
97.1% → 97.2% (+0.08%) | 97.1% → 97.2% (+0.08%) |
src/log-directory-setup.ts |
96.2% → 100.0% (+3.78%) | 96.3% → 100.0% (+3.71%) |
✨ New Files (10 files)
src/parsers/sealed-probe-parser.ts: 100.0% linessrc/sealed-probe/manager.ts: 100.0% linessrc/sealed-probe/paths.ts: 100.0% linessrc/sealed-probe/preflight.ts: 100.0% linessrc/sealed-probe/protocol.ts: 100.0% linessrc/sealed-probe/skill.ts: 100.0% linessrc/sealed-probe/staging.ts: 100.0% linessrc/sealed-probe/types.ts: 100.0% linessrc/services/sealed-probe-service.ts: 100.0% linessrc/types/sealed-probe-options.ts: 100.0% lines
Coverage comparison generated by scripts/ci/compare-coverage.ts
Smoke Test: Claude Engine Validation
Overall result: PASS
|
|
@lpcox — smoke test results for network isolation egress enforcement:
Overall: PASS Warning Firewall blocked 1 domainThe following domain was blocked by the firewall during workflow execution:
network:
allowed:
- defaults
- "example.com"See Network Configuration for more information.
|
|
Smoke Test: Copilot BYOK (Direct Mode) ✅ GitHub MCP: Available (read access confirmed) Overall: PASS — Direct BYOK mode (COPILOT_PROVIDER_API_KEY) is operational.
|
Smoke Test Results
Overall: FAIL —
|
🔥 Smoke Test Results
Overall: PASS
|
|
feat: add sealed probes for private repositories Warning Firewall blocked 1 domainThe following domain was blocked by the firewall during workflow execution:
network:
allowed:
- defaults
- "registry.npmjs.org"See Network Configuration for more information.
|
Chroot Version Comparison Results
Overall: ❌ FAILED — Node.js version mismatch (host
|
Smoke Test Results
Overall status: FAIL Warning Firewall blocked 1 domainThe following domain was blocked by the firewall during workflow execution:
network:
allowed:
- defaults
- "localhost"See Network Configuration for more information.
|
Smoke Test: API Proxy OpenTelemetry Tracing
Summary: All 5 scenarios pass. OTEL tracing integration is fully functional — spans are created per request with GenAI semantic conventions, parent context propagation via
|
Running in direct BYOK mode (AWF_AUTH_TYPE=github-oidc + AWF_AUTH_AZURE_* + COPILOT_PROVIDER_BASE_URL) via api-proxy → Azure OpenAI (Foundry, o4-mini-aw) authenticated via Microsoft Entra Overall: PASS
|
🏗️ Build Test Suite Results
Overall: 8/8 ecosystems passed — ✅ PASS
|
|
Smoke Test Results: PASS
|
🔍 Smoke Test: Docker Sbx Validation
Overall:
|
Summary
sealedProbesconfiguration with schema, stdin-config, defaults, validation, and fail-closed preflight supportsealed-probeCLI and generated skill with exactly three caller-declared outcomes plus reservedERRORSecurity model
The broker and probe have no network access. Private repository credentials are used only by trusted host staging and are excluded from the primary agent. Each probe receives only a fresh ephemeral repository copy and a read-only script, with a read-only root filesystem, non-root identity, dropped capabilities, seccomp, resource bounds, and no Docker socket.
The broker validates the request before launch, enforces the invocation budget, rejects non-zero exits and invalid output, and emits only canonical
{"result":"..."}JSON. All failure paths collapse to{"result":"ERROR"}with the same exit status and no diagnostics exposed to the agent.Closes #6661