@elie-laloum/outpost 5.0.0 → 7.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +54 -0
- package/README.md +11 -11
- package/SECURITY.md +10 -0
- package/dist/adapters/agents/antigravity-adapter.d.ts +3 -0
- package/dist/adapters/agents/antigravity-adapter.js +41 -0
- package/dist/adapters/agents/antigravity-adapter.js.map +1 -0
- package/dist/adapters/agents/antigravity-authentication.d.ts +2 -0
- package/dist/adapters/agents/antigravity-authentication.js +27 -0
- package/dist/adapters/agents/antigravity-authentication.js.map +1 -0
- package/dist/adapters/agents/antigravity-diagnostics.d.ts +1 -0
- package/dist/adapters/agents/antigravity-diagnostics.js +6 -0
- package/dist/adapters/agents/antigravity-diagnostics.js.map +1 -0
- package/dist/adapters/agents/antigravity-events.d.ts +2 -0
- package/dist/adapters/agents/antigravity-events.js +75 -0
- package/dist/adapters/agents/antigravity-events.js.map +1 -0
- package/dist/adapters/agents/antigravity-request.d.ts +5 -0
- package/dist/adapters/agents/antigravity-request.js +37 -0
- package/dist/adapters/agents/antigravity-request.js.map +1 -0
- package/dist/adapters/agents/antigravity.constants.d.ts +3 -0
- package/dist/adapters/agents/antigravity.constants.js +4 -0
- package/dist/adapters/agents/antigravity.constants.js.map +1 -0
- package/dist/adapters/agents/{gemini.types.d.ts → antigravity.types.d.ts} +2 -2
- package/dist/adapters/agents/antigravity.types.js +2 -0
- package/dist/adapters/agents/antigravity.types.js.map +1 -0
- package/dist/adapters/agents/authentication.constants.d.ts +19 -9
- package/dist/adapters/agents/authentication.constants.js +12 -9
- package/dist/adapters/agents/authentication.constants.js.map +1 -1
- package/dist/adapters/agents/authentication.d.ts +11 -2
- package/dist/adapters/agents/authentication.js +70 -47
- package/dist/adapters/agents/authentication.js.map +1 -1
- package/dist/adapters/agents/authentication.types.d.ts +20 -0
- package/dist/adapters/agents/authentication.types.js +2 -0
- package/dist/adapters/agents/authentication.types.js.map +1 -0
- package/dist/adapters/agents/claude-adapter.js +4 -2
- package/dist/adapters/agents/claude-adapter.js.map +1 -1
- package/dist/adapters/agents/claude-authentication.d.ts +2 -0
- package/dist/adapters/agents/claude-authentication.js +34 -0
- package/dist/adapters/agents/claude-authentication.js.map +1 -0
- package/dist/adapters/agents/claude-events.js +52 -9
- package/dist/adapters/agents/claude-events.js.map +1 -1
- package/dist/adapters/agents/claude-request.js +2 -0
- package/dist/adapters/agents/claude-request.js.map +1 -1
- package/dist/adapters/agents/cli-diagnostics.constants.d.ts +6 -6
- package/dist/adapters/agents/cli-diagnostics.constants.js +6 -6
- package/dist/adapters/agents/cli-diagnostics.constants.js.map +1 -1
- package/dist/adapters/agents/cli-diagnostics.d.ts +1 -0
- package/dist/adapters/agents/cli-diagnostics.js +18 -0
- package/dist/adapters/agents/cli-diagnostics.js.map +1 -1
- package/dist/adapters/agents/codex-adapter.js +4 -2
- package/dist/adapters/agents/codex-adapter.js.map +1 -1
- package/dist/adapters/agents/codex-authentication.d.ts +3 -0
- package/dist/adapters/agents/codex-authentication.js +47 -0
- package/dist/adapters/agents/codex-authentication.js.map +1 -0
- package/dist/adapters/agents/codex-events.js +28 -2
- package/dist/adapters/agents/codex-events.js.map +1 -1
- package/dist/adapters/agents/copilot-adapter.d.ts +3 -0
- package/dist/adapters/agents/copilot-adapter.js +45 -0
- package/dist/adapters/agents/copilot-adapter.js.map +1 -0
- package/dist/adapters/agents/copilot-authentication.d.ts +2 -0
- package/dist/adapters/agents/copilot-authentication.js +46 -0
- package/dist/adapters/agents/copilot-authentication.js.map +1 -0
- package/dist/adapters/agents/copilot-diagnostics.d.ts +1 -0
- package/dist/adapters/agents/copilot-diagnostics.js +6 -0
- package/dist/adapters/agents/copilot-diagnostics.js.map +1 -0
- package/dist/adapters/agents/copilot-events.d.ts +2 -0
- package/dist/adapters/agents/copilot-events.js +66 -0
- package/dist/adapters/agents/copilot-events.js.map +1 -0
- package/dist/adapters/agents/copilot-request.d.ts +5 -0
- package/dist/adapters/agents/copilot-request.js +24 -0
- package/dist/adapters/agents/copilot-request.js.map +1 -0
- package/dist/adapters/agents/copilot-usage.d.ts +3 -0
- package/dist/adapters/agents/copilot-usage.js +19 -0
- package/dist/adapters/agents/copilot-usage.js.map +1 -0
- package/dist/adapters/agents/copilot.types.d.ts +6 -0
- package/dist/adapters/agents/copilot.types.js +2 -0
- package/dist/adapters/agents/copilot.types.js.map +1 -0
- package/dist/adapters/agents/event-decoder.d.ts +2 -2
- package/dist/adapters/agents/event-decoder.js +6 -5
- package/dist/adapters/agents/event-decoder.js.map +1 -1
- package/dist/adapters/agents/kimi-adapter.d.ts +3 -0
- package/dist/adapters/agents/kimi-adapter.js +51 -0
- package/dist/adapters/agents/kimi-adapter.js.map +1 -0
- package/dist/adapters/agents/kimi-authentication.d.ts +3 -0
- package/dist/adapters/agents/kimi-authentication.js +63 -0
- package/dist/adapters/agents/kimi-authentication.js.map +1 -0
- package/dist/adapters/agents/kimi-diagnostics.d.ts +2 -0
- package/dist/adapters/agents/kimi-diagnostics.js +14 -0
- package/dist/adapters/agents/kimi-diagnostics.js.map +1 -0
- package/dist/adapters/agents/kimi-events.d.ts +2 -0
- package/dist/adapters/agents/kimi-events.js +55 -0
- package/dist/adapters/agents/kimi-events.js.map +1 -0
- package/dist/adapters/agents/kimi-fork.d.ts +2 -0
- package/dist/adapters/agents/kimi-fork.js +11 -0
- package/dist/adapters/agents/kimi-fork.js.map +1 -0
- package/dist/adapters/agents/{gemini-request.d.ts → kimi-request.d.ts} +2 -2
- package/dist/adapters/agents/kimi-request.js +33 -0
- package/dist/adapters/agents/kimi-request.js.map +1 -0
- package/dist/adapters/agents/kimi-usage.d.ts +2 -0
- package/dist/adapters/agents/kimi-usage.js +7 -0
- package/dist/adapters/agents/kimi-usage.js.map +1 -0
- package/dist/adapters/agents/kimi.constants.d.ts +13 -0
- package/dist/adapters/agents/kimi.constants.js +14 -0
- package/dist/adapters/agents/kimi.constants.js.map +1 -0
- package/dist/adapters/agents/kimi.types.d.ts +7 -0
- package/dist/adapters/agents/kimi.types.js +2 -0
- package/dist/adapters/agents/kimi.types.js.map +1 -0
- package/dist/adapters/agents/model-support.constants.d.ts +3 -1
- package/dist/adapters/agents/model-support.constants.js +12 -2
- package/dist/adapters/agents/model-support.constants.js.map +1 -1
- package/dist/adapters/agents/protocol-fixtures.constants.d.ts +2 -2
- package/dist/adapters/agents/protocol-fixtures.constants.js +131 -9
- package/dist/adapters/agents/protocol-fixtures.constants.js.map +1 -1
- package/dist/adapters/agents/protocol-fixtures.types.d.ts +1 -0
- package/dist/adapters/agents/protocol-fixtures.types.js.map +1 -1
- package/dist/adapters/agents/protocol.d.ts +1 -0
- package/dist/adapters/agents/protocol.js +9 -0
- package/dist/adapters/agents/protocol.js.map +1 -1
- package/dist/adapters/agents/session-usage.constants.d.ts +10 -0
- package/dist/adapters/agents/session-usage.constants.js +110 -0
- package/dist/adapters/agents/session-usage.constants.js.map +1 -0
- package/dist/adapters/agents/session-usage.d.ts +5 -0
- package/dist/adapters/agents/session-usage.js +45 -0
- package/dist/adapters/agents/session-usage.js.map +1 -0
- package/dist/adapters/agents/settings.types.d.ts +1 -0
- package/dist/adapters/agents/settings.types.js.map +1 -1
- package/dist/adapters/agents/tool-result.d.ts +2 -0
- package/dist/adapters/agents/tool-result.js +17 -0
- package/dist/adapters/agents/tool-result.js.map +1 -0
- package/dist/adapters/models/anthropic-response.js +3 -0
- package/dist/adapters/models/anthropic-response.js.map +1 -1
- package/dist/adapters/models/http-provider.js +6 -1
- package/dist/adapters/models/http-provider.js.map +1 -1
- package/dist/adapters/models/openai-responses.js +10 -0
- package/dist/adapters/models/openai-responses.js.map +1 -1
- package/dist/adapters/models/retry-after.d.ts +1 -0
- package/dist/adapters/models/retry-after.js +16 -0
- package/dist/adapters/models/retry-after.js.map +1 -0
- package/dist/application/activity-watchdog.js +1 -2
- package/dist/application/activity-watchdog.js.map +1 -1
- package/dist/application/agent-authentication.d.ts +4 -0
- package/dist/application/agent-authentication.js +32 -0
- package/dist/application/agent-authentication.js.map +1 -0
- package/dist/application/agent-bootstrap.constants.d.ts +2 -5
- package/dist/application/agent-bootstrap.constants.js +27 -4
- package/dist/application/agent-bootstrap.constants.js.map +1 -1
- package/dist/application/agent-bootstrap.js +39 -12
- package/dist/application/agent-bootstrap.js.map +1 -1
- package/dist/application/agent-bootstrap.types.d.ts +19 -0
- package/dist/application/agent-bootstrap.types.js +2 -0
- package/dist/application/agent-bootstrap.types.js.map +1 -0
- package/dist/application/agent-output.js +74 -8
- package/dist/application/agent-output.js.map +1 -1
- package/dist/application/agent-request.d.ts +3 -0
- package/dist/application/agent-request.js +11 -0
- package/dist/application/agent-request.js.map +1 -0
- package/dist/application/agent-turn.js +74 -6
- package/dist/application/agent-turn.js.map +1 -1
- package/dist/application/agent-usage.d.ts +6 -0
- package/dist/application/agent-usage.js +57 -0
- package/dist/application/agent-usage.js.map +1 -0
- package/dist/application/attach.js +2 -0
- package/dist/application/attach.js.map +1 -1
- package/dist/application/credential-installer.constants.d.ts +1 -0
- package/dist/application/credential-installer.constants.js +22 -0
- package/dist/application/credential-installer.constants.js.map +1 -0
- package/dist/application/custom-turn.js +44 -49
- package/dist/application/custom-turn.js.map +1 -1
- package/dist/application/dispatch-observation.d.ts +1 -1
- package/dist/application/dispatch-observation.js +141 -21
- package/dist/application/dispatch-observation.js.map +1 -1
- package/dist/application/dispatch-observation.types.d.ts +2 -0
- package/dist/application/dispatch-observation.types.js.map +1 -1
- package/dist/application/dispatch-validation.js +2 -0
- package/dist/application/dispatch-validation.js.map +1 -1
- package/dist/application/dispatch.js +1 -1
- package/dist/application/dispatch.js.map +1 -1
- package/dist/application/doctor-agent.constants.d.ts +2 -8
- package/dist/application/doctor-agent.constants.js +43 -6
- package/dist/application/doctor-agent.constants.js.map +1 -1
- package/dist/application/doctor-agent.d.ts +2 -1
- package/dist/application/doctor-agent.js +15 -3
- package/dist/application/doctor-agent.js.map +1 -1
- package/dist/application/doctor-image.js +4 -6
- package/dist/application/doctor-image.js.map +1 -1
- package/dist/application/doctor-protocol.js +6 -11
- package/dist/application/doctor-protocol.js.map +1 -1
- package/dist/application/doctor-protocol.types.d.ts +1 -1
- package/dist/application/doctor-protocol.types.js.map +1 -1
- package/dist/application/doctor-sandbox.js +2 -5
- package/dist/application/doctor-sandbox.js.map +1 -1
- package/dist/application/doctor.js +28 -10
- package/dist/application/doctor.js.map +1 -1
- package/dist/application/doctor.types.d.ts +10 -1
- package/dist/application/doctor.types.js.map +1 -1
- package/dist/application/execution.constants.d.ts +2 -0
- package/dist/application/execution.constants.js +2 -0
- package/dist/application/execution.constants.js.map +1 -1
- package/dist/application/execution.types.d.ts +8 -0
- package/dist/application/execution.types.js.map +1 -1
- package/dist/application/harness-budget.d.ts +3 -0
- package/dist/application/harness-budget.js +42 -0
- package/dist/application/harness-budget.js.map +1 -0
- package/dist/application/harness-budget.types.d.ts +5 -0
- package/dist/application/harness-budget.types.js +2 -0
- package/dist/application/harness-budget.types.js.map +1 -0
- package/dist/application/harness-hooks.js +34 -3
- package/dist/application/harness-hooks.js.map +1 -1
- package/dist/application/harness-loop.js +52 -24
- package/dist/application/harness-loop.js.map +1 -1
- package/dist/application/harness-model-provider.d.ts +3 -0
- package/dist/application/harness-model-provider.js +49 -0
- package/dist/application/harness-model-provider.js.map +1 -0
- package/dist/application/harness-model-provider.types.d.ts +10 -0
- package/dist/application/harness-model-provider.types.js +2 -0
- package/dist/application/harness-model-provider.types.js.map +1 -0
- package/dist/application/harness-subagent.d.ts +4 -0
- package/dist/application/harness-subagent.js +110 -0
- package/dist/application/harness-subagent.js.map +1 -0
- package/dist/application/harness.types.d.ts +11 -0
- package/dist/application/harness.types.js.map +1 -1
- package/dist/application/lifecycle-hooks.d.ts +1 -1
- package/dist/application/lifecycle-hooks.js +5 -4
- package/dist/application/lifecycle-hooks.js.map +1 -1
- package/dist/application/observed-lease.d.ts +3 -0
- package/dist/application/observed-lease.js +26 -0
- package/dist/application/observed-lease.js.map +1 -0
- package/dist/application/outpost.types.d.ts +3 -1
- package/dist/application/outpost.types.js.map +1 -1
- package/dist/application/output-lines.d.ts +4 -0
- package/dist/application/output-lines.js +28 -0
- package/dist/application/output-lines.js.map +1 -0
- package/dist/application/queue-worker.js +1 -1
- package/dist/application/queue-worker.js.map +1 -1
- package/dist/application/queue-worker.types.d.ts +1 -0
- package/dist/application/queue-worker.types.js.map +1 -1
- package/dist/application/queued-task.js +24 -5
- package/dist/application/queued-task.js.map +1 -1
- package/dist/application/recovery-archive.d.ts +3 -2
- package/dist/application/recovery-archive.js +9 -2
- package/dist/application/recovery-archive.js.map +1 -1
- package/dist/application/recovery-restore.d.ts +3 -2
- package/dist/application/recovery-restore.js +9 -2
- package/dist/application/recovery-restore.js.map +1 -1
- package/dist/application/recovery-retention.d.ts +3 -2
- package/dist/application/recovery-retention.js +74 -26
- package/dist/application/recovery-retention.js.map +1 -1
- package/dist/application/remote-workspace.js +5 -4
- package/dist/application/remote-workspace.js.map +1 -1
- package/dist/application/remote-workspace.types.d.ts +1 -0
- package/dist/application/remote-workspace.types.js.map +1 -1
- package/dist/application/sandbox-agents.js +19 -19
- package/dist/application/sandbox-agents.js.map +1 -1
- package/dist/application/sandbox-attach.js +12 -3
- package/dist/application/sandbox-attach.js.map +1 -1
- package/dist/application/sandbox-dispatch.js +13 -27
- package/dist/application/sandbox-dispatch.js.map +1 -1
- package/dist/application/sandbox-provision.js +15 -9
- package/dist/application/sandbox-provision.js.map +1 -1
- package/dist/application/sandbox-session.types.d.ts +7 -2
- package/dist/application/sandbox-session.types.js.map +1 -1
- package/dist/application/sandbox.js +13 -6
- package/dist/application/sandbox.js.map +1 -1
- package/dist/application/speculation-checkpoint.d.ts +6 -0
- package/dist/application/speculation-checkpoint.js +206 -0
- package/dist/application/speculation-checkpoint.js.map +1 -0
- package/dist/application/speculation-checkpoint.types.d.ts +24 -0
- package/dist/application/speculation-checkpoint.types.js +2 -0
- package/dist/application/speculation-checkpoint.types.js.map +1 -0
- package/dist/application/speculation-integration.constants.d.ts +4 -0
- package/dist/application/speculation-integration.constants.js +5 -0
- package/dist/application/speculation-integration.constants.js.map +1 -0
- package/dist/application/speculation-integration.d.ts +2 -0
- package/dist/application/speculation-integration.js +67 -0
- package/dist/application/speculation-integration.js.map +1 -0
- package/dist/application/speculation-resume.d.ts +4 -0
- package/dist/application/speculation-resume.js +71 -0
- package/dist/application/speculation-resume.js.map +1 -0
- package/dist/application/speculation-run.d.ts +4 -0
- package/dist/application/speculation-run.js +320 -0
- package/dist/application/speculation-run.js.map +1 -0
- package/dist/application/speculation-timeout.d.ts +1 -0
- package/dist/application/speculation-timeout.js +15 -0
- package/dist/application/speculation-timeout.js.map +1 -0
- package/dist/application/speculation.constants.d.ts +1 -0
- package/dist/application/speculation.constants.js +5 -1
- package/dist/application/speculation.constants.js.map +1 -1
- package/dist/application/speculation.js +41 -149
- package/dist/application/speculation.js.map +1 -1
- package/dist/application/speculation.types.d.ts +23 -0
- package/dist/application/speculation.types.js.map +1 -1
- package/dist/application/startup-recovery.js +14 -1
- package/dist/application/startup-recovery.js.map +1 -1
- package/dist/application/startup-recovery.types.d.ts +1 -0
- package/dist/application/startup-recovery.types.js.map +1 -1
- package/dist/application/stop-reason.d.ts +2 -0
- package/dist/application/stop-reason.js +21 -0
- package/dist/application/stop-reason.js.map +1 -0
- package/dist/application/stop-reason.types.d.ts +4 -0
- package/dist/application/stop-reason.types.js +2 -0
- package/dist/application/stop-reason.types.js.map +1 -0
- package/dist/application/storage-reservation.js +9 -2
- package/dist/application/storage-reservation.js.map +1 -1
- package/dist/application/task-observation.d.ts +3 -0
- package/dist/application/task-observation.js +22 -0
- package/dist/application/task-observation.js.map +1 -0
- package/dist/application/task-usage.js +5 -12
- package/dist/application/task-usage.js.map +1 -1
- package/dist/application/tasks.js +41 -16
- package/dist/application/tasks.js.map +1 -1
- package/dist/application/tool-execution.js +42 -19
- package/dist/application/tool-execution.js.map +1 -1
- package/dist/application/workspace.js +6 -4
- package/dist/application/workspace.js.map +1 -1
- package/dist/cli/doctor-command.js +6 -2
- package/dist/cli/doctor-command.js.map +1 -1
- package/dist/cli/init-authentication.d.ts +4 -1
- package/dist/cli/init-authentication.js +28 -33
- package/dist/cli/init-authentication.js.map +1 -1
- package/dist/cli/init-command.js +3 -3
- package/dist/cli/init-command.js.map +1 -1
- package/dist/cli/main.constants.d.ts +50 -13
- package/dist/cli/main.constants.js +70 -8
- package/dist/cli/main.constants.js.map +1 -1
- package/dist/cli/main.js +2 -1
- package/dist/cli/main.js.map +1 -1
- package/dist/cli/scaffold-files.js +1 -1
- package/dist/cli/scaffold-files.js.map +1 -1
- package/dist/cli/scaffold-validation.js +29 -22
- package/dist/cli/scaffold-validation.js.map +1 -1
- package/dist/cli/scaffold.constants.d.ts +0 -1
- package/dist/cli/scaffold.constants.js +6 -2
- package/dist/cli/scaffold.constants.js.map +1 -1
- package/dist/cli/scaffold.types.d.ts +8 -2
- package/dist/cli/scaffold.types.js.map +1 -1
- package/dist/cli/starters.js +1 -3
- package/dist/cli/starters.js.map +1 -1
- package/dist/domain/agent-observation.d.ts +4 -0
- package/dist/domain/agent-observation.js +27 -0
- package/dist/domain/agent-observation.js.map +1 -0
- package/dist/domain/agent.types.d.ts +122 -14
- package/dist/domain/agent.types.js.map +1 -1
- package/dist/domain/authentication.constants.d.ts +3 -0
- package/dist/domain/authentication.constants.js +11 -0
- package/dist/domain/authentication.constants.js.map +1 -0
- package/dist/domain/authentication.d.ts +3 -0
- package/dist/domain/authentication.js +22 -0
- package/dist/domain/authentication.js.map +1 -0
- package/dist/domain/authentication.types.d.ts +5 -0
- package/dist/domain/authentication.types.js +2 -0
- package/dist/domain/authentication.types.js.map +1 -0
- package/dist/domain/harness.d.ts +2 -2
- package/dist/domain/harness.js +6 -0
- package/dist/domain/harness.js.map +1 -1
- package/dist/domain/harness.types.d.ts +4 -3
- package/dist/domain/harness.types.js.map +1 -1
- package/dist/domain/model.types.d.ts +8 -0
- package/dist/domain/model.types.js.map +1 -1
- package/dist/domain/observation.constants.d.ts +8 -0
- package/dist/domain/observation.constants.js +9 -0
- package/dist/domain/observation.constants.js.map +1 -0
- package/dist/domain/observation.d.ts +2 -0
- package/dist/domain/observation.js +190 -0
- package/dist/domain/observation.js.map +1 -0
- package/dist/domain/observation.types.d.ts +84 -0
- package/dist/domain/observation.types.js +2 -0
- package/dist/domain/observation.types.js.map +1 -0
- package/dist/domain/observed-operation.d.ts +2 -0
- package/dist/domain/observed-operation.js +30 -0
- package/dist/domain/observed-operation.js.map +1 -0
- package/dist/domain/sandbox.types.d.ts +2 -0
- package/dist/domain/sandbox.types.js.map +1 -1
- package/dist/domain/subagent.constants.d.ts +13 -0
- package/dist/domain/subagent.constants.js +9 -0
- package/dist/domain/subagent.constants.js.map +1 -0
- package/dist/domain/subagent.d.ts +4 -0
- package/dist/domain/subagent.js +28 -0
- package/dist/domain/subagent.js.map +1 -0
- package/dist/domain/subagent.types.d.ts +13 -0
- package/dist/domain/subagent.types.js +2 -0
- package/dist/domain/subagent.types.js.map +1 -0
- package/dist/domain/transcript.types.d.ts +2 -0
- package/dist/domain/transcript.types.js.map +1 -1
- package/dist/domain/usage.d.ts +1 -0
- package/dist/domain/usage.js +16 -0
- package/dist/domain/usage.js.map +1 -1
- package/dist/domain/workflow/budget.d.ts +7 -3
- package/dist/domain/workflow/budget.js +26 -0
- package/dist/domain/workflow/budget.js.map +1 -1
- package/dist/domain/workflow/budget.types.d.ts +1 -1
- package/dist/domain/workflow/budget.types.js.map +1 -1
- package/dist/domain/workflow/checkpoint-validation.js +7 -1
- package/dist/domain/workflow/checkpoint-validation.js.map +1 -1
- package/dist/domain/workflow/checkpoint.js +3 -0
- package/dist/domain/workflow/checkpoint.js.map +1 -1
- package/dist/domain/workflow/gate-validation.js +14 -1
- package/dist/domain/workflow/gate-validation.js.map +1 -1
- package/dist/domain/workflow/gates.d.ts +1 -1
- package/dist/domain/workflow/gates.js +52 -4
- package/dist/domain/workflow/gates.js.map +1 -1
- package/dist/domain/workflow/gates.types.d.ts +15 -1
- package/dist/domain/workflow/gates.types.js.map +1 -1
- package/dist/domain/workflow/idempotency.d.ts +1 -0
- package/dist/domain/workflow/idempotency.js +7 -0
- package/dist/domain/workflow/idempotency.js.map +1 -0
- package/dist/domain/workflow/retry.constants.d.ts +2 -0
- package/dist/domain/workflow/retry.constants.js +3 -0
- package/dist/domain/workflow/retry.constants.js.map +1 -0
- package/dist/domain/workflow/retry.d.ts +4 -0
- package/dist/domain/workflow/retry.js +49 -0
- package/dist/domain/workflow/retry.js.map +1 -0
- package/dist/domain/workflow/task-runner.js +9 -5
- package/dist/domain/workflow/task-runner.js.map +1 -1
- package/dist/domain/workflow/task.js +6 -6
- package/dist/domain/workflow/task.js.map +1 -1
- package/dist/domain/workflow/workflow-scheduler.js +110 -72
- package/dist/domain/workflow/workflow-scheduler.js.map +1 -1
- package/dist/domain/workflow/workflow-state.js +28 -12
- package/dist/domain/workflow/workflow-state.js.map +1 -1
- package/dist/domain/workflow.d.ts +1 -1
- package/dist/domain/workflow.js +1 -1
- package/dist/domain/workflow.js.map +1 -1
- package/dist/domain/workflow.types.d.ts +13 -2
- package/dist/domain/workflow.types.js.map +1 -1
- package/dist/index.d.ts +16 -11
- package/dist/index.js +7 -4
- package/dist/index.js.map +1 -1
- package/dist/infrastructure/conversations/capture.js +10 -0
- package/dist/infrastructure/conversations/capture.js.map +1 -1
- package/dist/infrastructure/conversations/harness-transcript.js +6 -0
- package/dist/infrastructure/conversations/harness-transcript.js.map +1 -1
- package/dist/infrastructure/conversations/harness-transcript.types.d.ts +2 -0
- package/dist/infrastructure/conversations/harness-transcript.types.js.map +1 -1
- package/dist/infrastructure/conversations/layout.js +2 -0
- package/dist/infrastructure/conversations/layout.js.map +1 -1
- package/dist/infrastructure/conversations/locate.js +7 -1
- package/dist/infrastructure/conversations/locate.js.map +1 -1
- package/dist/infrastructure/conversations/native-store.js +8 -1
- package/dist/infrastructure/conversations/native-store.js.map +1 -1
- package/dist/infrastructure/conversations/paths.js +3 -0
- package/dist/infrastructure/conversations/paths.js.map +1 -1
- package/dist/infrastructure/conversations/restore.js +7 -0
- package/dist/infrastructure/conversations/restore.js.map +1 -1
- package/dist/infrastructure/conversations/session-bundle.constants.d.ts +5 -0
- package/dist/infrastructure/conversations/session-bundle.constants.js +173 -0
- package/dist/infrastructure/conversations/session-bundle.constants.js.map +1 -0
- package/dist/infrastructure/conversations/session-bundle.d.ts +6 -0
- package/dist/infrastructure/conversations/session-bundle.js +98 -0
- package/dist/infrastructure/conversations/session-bundle.js.map +1 -0
- package/dist/infrastructure/conversations/session-bundle.types.d.ts +1 -0
- package/dist/infrastructure/conversations/session-bundle.types.js +2 -0
- package/dist/infrastructure/conversations/session-bundle.types.js.map +1 -0
- package/dist/infrastructure/conversations.js +4 -2
- package/dist/infrastructure/conversations.js.map +1 -1
- package/dist/infrastructure/conversations.types.d.ts +1 -1
- package/dist/infrastructure/conversations.types.js.map +1 -1
- package/dist/infrastructure/custom-reporter.js +32 -24
- package/dist/infrastructure/custom-reporter.js.map +1 -1
- package/dist/infrastructure/custom-reporter.types.d.ts +2 -0
- package/dist/infrastructure/custom-reporter.types.js.map +1 -1
- package/dist/infrastructure/git/git.constants.d.ts +1 -1
- package/dist/infrastructure/git/git.constants.js +1 -0
- package/dist/infrastructure/git/git.constants.js.map +1 -1
- package/dist/infrastructure/git/workspace-lease.js +4 -3
- package/dist/infrastructure/git/workspace-lease.js.map +1 -1
- package/dist/infrastructure/git/workspace.js +7 -6
- package/dist/infrastructure/git/workspace.js.map +1 -1
- package/dist/infrastructure/git/workspace.types.d.ts +1 -0
- package/dist/infrastructure/git/workspace.types.js.map +1 -1
- package/dist/infrastructure/host-credentials.constants.d.ts +1 -0
- package/dist/infrastructure/host-credentials.constants.js +2 -0
- package/dist/infrastructure/host-credentials.constants.js.map +1 -0
- package/dist/infrastructure/host-credentials.d.ts +4 -0
- package/dist/infrastructure/host-credentials.js +89 -0
- package/dist/infrastructure/host-credentials.js.map +1 -0
- package/dist/infrastructure/inspection-path.js +4 -3
- package/dist/infrastructure/inspection-path.js.map +1 -1
- package/dist/infrastructure/journal.constants.js +10 -1
- package/dist/infrastructure/journal.constants.js.map +1 -1
- package/dist/infrastructure/journal.d.ts +1 -1
- package/dist/infrastructure/journal.js +8 -75
- package/dist/infrastructure/journal.js.map +1 -1
- package/dist/infrastructure/journal.types.d.ts +2 -4
- package/dist/infrastructure/journal.types.js.map +1 -1
- package/dist/infrastructure/local-transport.js +9 -4
- package/dist/infrastructure/local-transport.js.map +1 -1
- package/dist/infrastructure/opentelemetry-dispatch.d.ts +3 -3
- package/dist/infrastructure/opentelemetry-dispatch.js +5 -4
- package/dist/infrastructure/opentelemetry-dispatch.js.map +1 -1
- package/dist/infrastructure/opentelemetry-observation.d.ts +5 -0
- package/dist/infrastructure/opentelemetry-observation.js +59 -0
- package/dist/infrastructure/opentelemetry-observation.js.map +1 -0
- package/dist/infrastructure/opentelemetry.js +15 -1
- package/dist/infrastructure/opentelemetry.js.map +1 -1
- package/dist/infrastructure/opentelemetry.types.d.ts +9 -1
- package/dist/infrastructure/opentelemetry.types.js.map +1 -1
- package/dist/infrastructure/reporter.d.ts +2 -2
- package/dist/infrastructure/reporter.js +5 -1
- package/dist/infrastructure/reporter.js.map +1 -1
- package/dist/infrastructure/repository-transport.constants.d.ts +1 -0
- package/dist/infrastructure/repository-transport.constants.js +2 -0
- package/dist/infrastructure/repository-transport.constants.js.map +1 -0
- package/dist/infrastructure/repository-transport.d.ts +2 -0
- package/dist/infrastructure/repository-transport.js +9 -0
- package/dist/infrastructure/repository-transport.js.map +1 -0
- package/dist/infrastructure/resource-activity-inspection.js +19 -24
- package/dist/infrastructure/resource-activity-inspection.js.map +1 -1
- package/dist/infrastructure/resource-activity.constants.d.ts +0 -1
- package/dist/infrastructure/resource-activity.constants.js +0 -1
- package/dist/infrastructure/resource-activity.constants.js.map +1 -1
- package/dist/infrastructure/resource-activity.js +20 -83
- package/dist/infrastructure/resource-activity.js.map +1 -1
- package/dist/infrastructure/s3-transport.constants.d.ts +2 -0
- package/dist/infrastructure/s3-transport.constants.js +3 -0
- package/dist/infrastructure/s3-transport.constants.js.map +1 -0
- package/dist/infrastructure/s3-transport.js +57 -3
- package/dist/infrastructure/s3-transport.js.map +1 -1
- package/dist/infrastructure/s3-transport.types.d.ts +1 -0
- package/dist/infrastructure/s3-transport.types.js.map +1 -1
- package/dist/infrastructure/speculation-store.constants.d.ts +3 -0
- package/dist/infrastructure/speculation-store.constants.js +2 -0
- package/dist/infrastructure/speculation-store.constants.js.map +1 -0
- package/dist/infrastructure/speculation-store.d.ts +4 -0
- package/dist/infrastructure/speculation-store.js +73 -0
- package/dist/infrastructure/speculation-store.js.map +1 -0
- package/dist/infrastructure/speculation-store.types.d.ts +12 -0
- package/dist/infrastructure/speculation-store.types.js +2 -0
- package/dist/infrastructure/speculation-store.types.js.map +1 -0
- package/dist/infrastructure/storage-inventory.constants.js +1 -0
- package/dist/infrastructure/storage-inventory.constants.js.map +1 -1
- package/dist/infrastructure/storage-inventory.types.d.ts +1 -1
- package/dist/infrastructure/storage-inventory.types.js.map +1 -1
- package/dist/infrastructure/storage-reservations.types.d.ts +0 -8
- package/dist/infrastructure/storage-reservations.types.js.map +1 -1
- package/dist/infrastructure/task-queue-bullmq-resources.js +3 -0
- package/dist/infrastructure/task-queue-bullmq-resources.js.map +1 -1
- package/dist/infrastructure/task-queue-http.js +29 -4
- package/dist/infrastructure/task-queue-http.js.map +1 -1
- package/dist/infrastructure/task-queue-http.types.d.ts +2 -2
- package/dist/infrastructure/task-queue-http.types.js.map +1 -1
- package/dist/infrastructure/transport-conversations.js +2 -0
- package/dist/infrastructure/transport-conversations.js.map +1 -1
- package/dist/infrastructure/transport-journal.d.ts +1 -1
- package/dist/infrastructure/transport-journal.js +8 -2
- package/dist/infrastructure/transport-journal.js.map +1 -1
- package/dist/infrastructure/transport-reservations.d.ts +1 -1
- package/dist/infrastructure/transport-reservations.js +14 -8
- package/dist/infrastructure/transport-reservations.js.map +1 -1
- package/dist/infrastructure/workflow-decision-signature.constants.d.ts +4 -0
- package/dist/infrastructure/workflow-decision-signature.constants.js +5 -0
- package/dist/infrastructure/workflow-decision-signature.constants.js.map +1 -0
- package/dist/infrastructure/workflow-decision-signature.d.ts +4 -0
- package/dist/infrastructure/workflow-decision-signature.js +83 -0
- package/dist/infrastructure/workflow-decision-signature.js.map +1 -0
- package/dist/infrastructure/workflow-decision-signature.types.d.ts +16 -0
- package/dist/infrastructure/workflow-decision-signature.types.js +2 -0
- package/dist/infrastructure/workflow-decision-signature.types.js.map +1 -0
- package/dist/providers/agents.d.ts +7 -2
- package/dist/providers/agents.js +4 -1
- package/dist/providers/agents.js.map +1 -1
- package/dist/providers/antigravity-install.constants.d.ts +2 -0
- package/dist/providers/antigravity-install.constants.js +28 -0
- package/dist/providers/antigravity-install.constants.js.map +1 -0
- package/dist/providers/antigravity-install.d.ts +2 -0
- package/dist/providers/antigravity-install.js +29 -0
- package/dist/providers/antigravity-install.js.map +1 -0
- package/dist/providers/antigravity-install.types.d.ts +4 -0
- package/dist/providers/antigravity-install.types.js +2 -0
- package/dist/providers/antigravity-install.types.js.map +1 -0
- package/dist/providers/container-recovery.d.ts +4 -0
- package/dist/providers/container-recovery.js +28 -0
- package/dist/providers/container-recovery.js.map +1 -0
- package/dist/providers/container.js +8 -0
- package/dist/providers/container.js.map +1 -1
- package/dist/providers/daytona-network.constants.d.ts +5 -0
- package/dist/providers/daytona-network.constants.js +8 -0
- package/dist/providers/daytona-network.constants.js.map +1 -0
- package/dist/providers/daytona-network.d.ts +4 -0
- package/dist/providers/daytona-network.js +33 -0
- package/dist/providers/daytona-network.js.map +1 -0
- package/dist/providers/daytona.d.ts +1 -0
- package/dist/providers/daytona.js +9 -3
- package/dist/providers/daytona.js.map +1 -1
- package/dist/providers/daytona.types.d.ts +2 -0
- package/dist/providers/daytona.types.js.map +1 -1
- package/dist/providers/firecracker-command.js +1 -1
- package/dist/providers/firecracker-command.js.map +1 -1
- package/dist/providers/firecracker-jailer.constants.d.ts +9 -0
- package/dist/providers/firecracker-jailer.constants.js +10 -0
- package/dist/providers/firecracker-jailer.constants.js.map +1 -0
- package/dist/providers/firecracker-jailer.d.ts +4 -0
- package/dist/providers/firecracker-jailer.js +171 -0
- package/dist/providers/firecracker-jailer.js.map +1 -0
- package/dist/providers/firecracker-machine.js +30 -8
- package/dist/providers/firecracker-machine.js.map +1 -1
- package/dist/providers/firecracker.types.d.ts +16 -0
- package/dist/providers/firecracker.types.js.map +1 -1
- package/dist/providers/vercel-network.js +1 -1
- package/dist/providers/vercel-network.js.map +1 -1
- package/dist/providers/vercel.js +6 -3
- package/dist/providers/vercel.js.map +1 -1
- package/dist/providers/versions.constants.d.ts +3 -1
- package/dist/providers/versions.constants.js +3 -1
- package/dist/providers/versions.constants.js.map +1 -1
- package/package.json +3 -3
- package/dist/adapters/agents/gemini-adapter.d.ts +0 -3
- package/dist/adapters/agents/gemini-adapter.js +0 -34
- package/dist/adapters/agents/gemini-adapter.js.map +0 -1
- package/dist/adapters/agents/gemini-diagnostics.d.ts +0 -2
- package/dist/adapters/agents/gemini-diagnostics.js +0 -15
- package/dist/adapters/agents/gemini-diagnostics.js.map +0 -1
- package/dist/adapters/agents/gemini-events.d.ts +0 -2
- package/dist/adapters/agents/gemini-events.js +0 -50
- package/dist/adapters/agents/gemini-events.js.map +0 -1
- package/dist/adapters/agents/gemini-request.js +0 -23
- package/dist/adapters/agents/gemini-request.js.map +0 -1
- package/dist/adapters/agents/gemini.types.js +0 -2
- package/dist/adapters/agents/gemini.types.js.map +0 -1
- package/dist/infrastructure/artifact-store.d.ts +0 -3
- package/dist/infrastructure/artifact-store.js +0 -110
- package/dist/infrastructure/artifact-store.js.map +0 -1
- package/dist/infrastructure/artifact-store.types.d.ts +0 -6
- package/dist/infrastructure/artifact-store.types.js +0 -2
- package/dist/infrastructure/artifact-store.types.js.map +0 -1
- package/dist/infrastructure/journal-retention.constants.d.ts +0 -4
- package/dist/infrastructure/journal-retention.constants.js +0 -5
- package/dist/infrastructure/journal-retention.constants.js.map +0 -1
- package/dist/infrastructure/journal-retention.d.ts +0 -2
- package/dist/infrastructure/journal-retention.js +0 -51
- package/dist/infrastructure/journal-retention.js.map +0 -1
- package/dist/infrastructure/storage-mutation-lock.constants.d.ts +0 -5
- package/dist/infrastructure/storage-mutation-lock.constants.js +0 -6
- package/dist/infrastructure/storage-mutation-lock.constants.js.map +0 -1
- package/dist/infrastructure/storage-mutation-lock.d.ts +0 -1
- package/dist/infrastructure/storage-mutation-lock.js +0 -21
- package/dist/infrastructure/storage-mutation-lock.js.map +0 -1
- package/dist/infrastructure/storage-reservations.constants.d.ts +0 -4
- package/dist/infrastructure/storage-reservations.constants.js +0 -5
- package/dist/infrastructure/storage-reservations.constants.js.map +0 -1
- package/dist/infrastructure/storage-reservations.d.ts +0 -2
- package/dist/infrastructure/storage-reservations.js +0 -150
- package/dist/infrastructure/storage-reservations.js.map +0 -1
- package/dist/infrastructure/workflow-checkpoint.d.ts +0 -3
- package/dist/infrastructure/workflow-checkpoint.js +0 -84
- package/dist/infrastructure/workflow-checkpoint.js.map +0 -1
- package/dist/infrastructure/workflow-checkpoint.types.d.ts +0 -6
- package/dist/infrastructure/workflow-checkpoint.types.js +0 -2
- package/dist/infrastructure/workflow-checkpoint.types.js.map +0 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"antigravity-install.types.js","sourceRoot":"","sources":["../../src/providers/antigravity-install.types.ts"],"names":[],"mappings":"","sourcesContent":["export interface AntigravityRelease {\n readonly url: string;\n readonly sha512: string;\n}\n"]}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { TransferOptions } from "../domain/sandbox.types.ts";
|
|
2
|
+
import type { Executor } from "../infrastructure/process.types.ts";
|
|
3
|
+
import type { ContainerEngine } from "./container.types.ts";
|
|
4
|
+
export declare function recoverContainer(engine: ContainerEngine, executor: Executor, resourceId: string, options?: TransferOptions): Promise<void>;
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { invariant } from "../domain/errors.js";
|
|
2
|
+
import { requireSuccess } from "../infrastructure/process.js";
|
|
3
|
+
import { containerDefaults } from "./container.constants.js";
|
|
4
|
+
export async function recoverContainer(engine, executor, resourceId, options = {}) {
|
|
5
|
+
invariant(/^outpost-[a-f0-9-]{36}$/.test(resourceId), "Invalid recoverable container identity");
|
|
6
|
+
const limits = {
|
|
7
|
+
deadlineMs: options.deadlineMs ?? containerDefaults.cleanupMs,
|
|
8
|
+
...(options.signal ? { signal: options.signal } : {}),
|
|
9
|
+
};
|
|
10
|
+
const result = await requireSuccess({
|
|
11
|
+
executable: engine,
|
|
12
|
+
arguments: [
|
|
13
|
+
"container",
|
|
14
|
+
"ls",
|
|
15
|
+
"--all",
|
|
16
|
+
"--filter",
|
|
17
|
+
`name=^${resourceId}$`,
|
|
18
|
+
"--format",
|
|
19
|
+
"{{.Names}}",
|
|
20
|
+
],
|
|
21
|
+
...limits,
|
|
22
|
+
}, executor);
|
|
23
|
+
if (!result.stdout.trim())
|
|
24
|
+
return;
|
|
25
|
+
invariant(result.stdout.trim() === resourceId, "Recoverable container identity mismatch");
|
|
26
|
+
await requireSuccess({ executable: engine, arguments: ["rm", "--force", resourceId], ...limits }, executor);
|
|
27
|
+
}
|
|
28
|
+
//# sourceMappingURL=container-recovery.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"container-recovery.js","sourceRoot":"","sources":["../../src/providers/container-recovery.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,qBAAqB,CAAC;AAEhD,OAAO,EAAE,cAAc,EAAE,MAAM,8BAA8B,CAAC;AAE9D,OAAO,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAG7D,MAAM,CAAC,KAAK,UAAU,gBAAgB,CACpC,MAAuB,EACvB,QAAkB,EAClB,UAAkB,EAClB,UAA2B,EAAE;IAE7B,SAAS,CACP,yBAAyB,CAAC,IAAI,CAAC,UAAU,CAAC,EAC1C,wCAAwC,CACzC,CAAC;IACF,MAAM,MAAM,GAAG;QACb,UAAU,EAAE,OAAO,CAAC,UAAU,IAAI,iBAAiB,CAAC,SAAS;QAC7D,GAAG,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KACtD,CAAC;IACF,MAAM,MAAM,GAAG,MAAM,cAAc,CACjC;QACE,UAAU,EAAE,MAAM;QAClB,SAAS,EAAE;YACT,WAAW;YACX,IAAI;YACJ,OAAO;YACP,UAAU;YACV,SAAS,UAAU,GAAG;YACtB,UAAU;YACV,YAAY;SACb;QACD,GAAG,MAAM;KACV,EACD,QAAQ,CACT,CAAC;IACF,IAAI,CAAC,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE;QAAE,OAAO;IAClC,SAAS,CACP,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,KAAK,UAAU,EACnC,yCAAyC,CAC1C,CAAC;IACF,MAAM,cAAc,CAClB,EAAE,UAAU,EAAE,MAAM,EAAE,SAAS,EAAE,CAAC,IAAI,EAAE,SAAS,EAAE,UAAU,CAAC,EAAE,GAAG,MAAM,EAAE,EAC3E,QAAQ,CACT,CAAC;AACJ,CAAC","sourcesContent":["import { invariant } from \"../domain/errors.ts\";\nimport type { TransferOptions } from \"../domain/sandbox.types.ts\";\nimport { requireSuccess } from \"../infrastructure/process.ts\";\nimport type { Executor } from \"../infrastructure/process.types.ts\";\nimport { containerDefaults } from \"./container.constants.ts\";\nimport type { ContainerEngine } from \"./container.types.ts\";\n\nexport async function recoverContainer(\n engine: ContainerEngine,\n executor: Executor,\n resourceId: string,\n options: TransferOptions = {},\n): Promise<void> {\n invariant(\n /^outpost-[a-f0-9-]{36}$/.test(resourceId),\n \"Invalid recoverable container identity\",\n );\n const limits = {\n deadlineMs: options.deadlineMs ?? containerDefaults.cleanupMs,\n ...(options.signal ? { signal: options.signal } : {}),\n };\n const result = await requireSuccess(\n {\n executable: engine,\n arguments: [\n \"container\",\n \"ls\",\n \"--all\",\n \"--filter\",\n `name=^${resourceId}$`,\n \"--format\",\n \"{{.Names}}\",\n ],\n ...limits,\n },\n executor,\n );\n if (!result.stdout.trim()) return;\n invariant(\n result.stdout.trim() === resourceId,\n \"Recoverable container identity mismatch\",\n );\n await requireSuccess(\n { executable: engine, arguments: [\"rm\", \"--force\", resourceId], ...limits },\n executor,\n );\n}\n"]}
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { recoverContainer } from "./container-recovery.js";
|
|
1
2
|
import { execFileSync } from "node:child_process";
|
|
2
3
|
import { randomUUID } from "node:crypto";
|
|
3
4
|
import { basename } from "node:path";
|
|
@@ -37,6 +38,11 @@ export function containerProvider(engine, options = {}, executor = executeProces
|
|
|
37
38
|
name: engine,
|
|
38
39
|
placement: config.repositoryMode === "isolated" ? "remote" : "mounted",
|
|
39
40
|
variables: { ...config.variables },
|
|
41
|
+
...(config.repositoryMode !== "isolated"
|
|
42
|
+
? {
|
|
43
|
+
recover: (resourceId, recoveryOptions) => recoverContainer(engine, executor, resourceId, recoveryOptions),
|
|
44
|
+
}
|
|
45
|
+
: {}),
|
|
40
46
|
async acquire(context) {
|
|
41
47
|
context.signal?.throwIfAborted();
|
|
42
48
|
const name = `outpost-${randomUUID()}`;
|
|
@@ -97,6 +103,8 @@ export function containerProvider(engine, options = {}, executor = executeProces
|
|
|
97
103
|
`${cacheDefaults.label}=true`,
|
|
98
104
|
cache.volume,
|
|
99
105
|
], context.signal ? { signal: context.signal } : {});
|
|
106
|
+
await context.registerRecovery?.(name);
|
|
107
|
+
context.signal?.throwIfAborted();
|
|
100
108
|
await call(args, {
|
|
101
109
|
...(context.signal ? { signal: context.signal } : {}),
|
|
102
110
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"container.js","sourceRoot":"","sources":["../../src/providers/container.ts"],"names":[],"mappings":"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","sourcesContent":["import { execFileSync } from \"node:child_process\";\nimport { randomUUID } from \"node:crypto\";\nimport { basename } from \"node:path\";\nimport type { Command } from \"../domain/command.types.ts\";\nimport { containerNetworks } from \"./container-network.ts\";\nimport { invariant } from \"../domain/errors.ts\";\nimport type { SandboxProvider } from \"../domain/sandbox.types.ts\";\nimport {\n executeProcess,\n quote,\n requireSuccess,\n} from \"../infrastructure/process.ts\";\nimport type { Executor } from \"../infrastructure/process.types.ts\";\nimport { registerCleanup } from \"../infrastructure/shutdown.ts\";\nimport { cacheMounts, validateCaches } from \"./container-cache.ts\";\nimport {\n cacheCreateOptions,\n cacheDefaults,\n} from \"./container-cache.constants.ts\";\nimport { containerCommand } from \"./container-command.ts\";\nimport { containerFiles } from \"./container-files.ts\";\nimport { containerMounts } from \"./container-mounts.ts\";\nimport { containerPlan } from \"./container-plan.ts\";\nimport { containerPreflight } from \"./container-preflight.ts\";\nimport { containerDefaults } from \"./container.constants.ts\";\nimport type { ContainerEngine, ContainerOptions } from \"./container.types.ts\";\n\nexport type { ContainerOptions } from \"./container.types.ts\";\n\nexport function imageName(repository: string): string {\n return `outpost:${\n basename(repository)\n .toLowerCase()\n .replace(/[^a-z0-9_.-]/g, \"-\") || \"workspace\"\n }`;\n}\n\nexport function containerProvider(\n engine: ContainerEngine,\n options: ContainerOptions = {},\n executor: Executor = executeProcess,\n platform: NodeJS.Platform = process.platform,\n): SandboxProvider {\n const config = {\n ...options,\n networks: containerNetworks(options),\n caches: (options.caches ?? []).map((cache) => ({ ...cache })),\n };\n invariant(\n config.repositoryMode === undefined ||\n config.repositoryMode === \"mounted\" ||\n config.repositoryMode === \"isolated\",\n \"repositoryMode must be mounted or isolated\",\n );\n validateCaches(config);\n if (config.cpus !== undefined)\n invariant(\n Number.isFinite(config.cpus) && config.cpus > 0,\n \"cpus must be positive\",\n );\n if (config.memoryMb !== undefined)\n invariant(\n Number.isSafeInteger(config.memoryMb) &&\n config.memoryMb >= containerDefaults.minimumMemoryMb,\n \"memoryMb must be at least 64\",\n );\n return {\n name: engine,\n placement: config.repositoryMode === \"isolated\" ? \"remote\" : \"mounted\",\n variables: { ...config.variables },\n async acquire(context) {\n context.signal?.throwIfAborted();\n const name = `outpost-${randomUUID()}`;\n const image = config.image ?? imageName(context.repository);\n const user = config.user ?? {\n uid: process.getuid?.() ?? containerDefaults.uid,\n gid: process.getgid?.() ?? containerDefaults.gid,\n };\n invariant(\n Number.isInteger(user.uid) &&\n user.uid >= 0 &&\n Number.isInteger(user.gid) &&\n user.gid >= 0,\n \"Invalid container user\",\n );\n const call = (args: readonly string[], extra: Partial<Command> = {}) =>\n requireSuccess(\n {\n executable: engine,\n arguments: args,\n deadlineMs: containerDefaults.deadlineMs,\n ...extra,\n },\n executor,\n );\n await containerPreflight(engine, platform, call, config, image, user);\n const root =\n config.repositoryMode === \"isolated\"\n ? containerDefaults.isolatedRoot\n : containerDefaults.root,\n home = containerDefaults.home;\n const { env, volumes, fileParents } = await containerMounts(\n context,\n config,\n platform,\n root,\n home,\n );\n const caches = await cacheMounts(\n config.caches ?? [],\n context.repository,\n image,\n user,\n );\n for (const cache of caches)\n volumes.push(\"--volume\", `${cache.volume}:${cache.target}:nocopy`);\n const args = containerPlan({\n config,\n engine,\n user,\n root,\n name,\n image,\n volumes,\n fileParents,\n });\n let closed = false,\n releasing: Promise<void> | undefined;\n let unregister = () => {};\n const release = (): Promise<void> => {\n closed = true;\n releasing ??= call([\"rm\", \"--force\", name])\n .then(() => {\n unregister();\n })\n .catch((error) => {\n releasing = undefined;\n throw error;\n });\n return releasing;\n };\n try {\n for (const cache of caches)\n await call(\n [\n \"volume\",\n \"create\",\n ...cacheCreateOptions[engine],\n \"--label\",\n `${cacheDefaults.label}=true`,\n cache.volume,\n ],\n context.signal ? { signal: context.signal } : {},\n );\n await call(args, {\n ...(context.signal ? { signal: context.signal } : {}),\n });\n await call(\n [\"start\", name],\n context.signal ? { signal: context.signal } : {},\n );\n for (const cache of caches) {\n await call(\n [\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"chown\",\n `${user.uid}:${user.gid}`,\n cache.target,\n ],\n context.signal ? { signal: context.signal } : {},\n );\n await call(\n [\"exec\", name, \"chmod\", \"700\", cache.target],\n context.signal ? { signal: context.signal } : {},\n );\n }\n for (const parent of fileParents)\n await call([\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"sh\",\n \"-c\",\n `mkdir -p ${quote(parent)} && chown ${user.uid}:${user.gid} ${quote(parent)}`,\n ]);\n if (fileParents.size)\n await call([\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"chown\",\n `${user.uid}:${user.gid}`,\n home,\n ]);\n if (config.repositoryMode === \"isolated\")\n await call(\n [\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"sh\",\n \"-c\",\n `mkdir -p ${quote(root)} && chmod 700 ${quote(root)} /tmp/outpost && chown ${user.uid}:${user.gid} ${quote(root)} /tmp/outpost`,\n ],\n context.signal ? { signal: context.signal } : {},\n );\n await call([\n \"exec\",\n name,\n \"sh\",\n \"-c\",\n \"command -v setsid >/dev/null && command -v kill >/dev/null && command -v tar >/dev/null && command -v cp >/dev/null\",\n ]);\n } catch (cause) {\n try {\n await release();\n } catch (cleanup) {\n throw new AggregateError(\n [cause, cleanup],\n \"Sandbox provisioning and cleanup failed\",\n );\n }\n throw cause;\n }\n unregister = registerCleanup(release, () => {\n if (!closed)\n execFileSync(engine, [\"rm\", \"--force\", name], {\n timeout: containerDefaults.cleanupMs,\n stdio: \"ignore\",\n windowsHide: true,\n });\n });\n return {\n root,\n home,\n invoke: containerCommand({\n engine,\n config,\n executor,\n root,\n name,\n env,\n call,\n isClosed: () => closed,\n }),\n ...containerFiles({\n engine,\n config,\n executor,\n root,\n name,\n env,\n call,\n isClosed: () => closed,\n }),\n release,\n };\n },\n };\n}\n"]}
|
|
1
|
+
{"version":3,"file":"container.js","sourceRoot":"","sources":["../../src/providers/container.ts"],"names":[],"mappings":"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","sourcesContent":["import { recoverContainer } from \"./container-recovery.ts\";\nimport { execFileSync } from \"node:child_process\";\nimport { randomUUID } from \"node:crypto\";\nimport { basename } from \"node:path\";\nimport type { Command } from \"../domain/command.types.ts\";\nimport { containerNetworks } from \"./container-network.ts\";\nimport { invariant } from \"../domain/errors.ts\";\nimport type { SandboxProvider } from \"../domain/sandbox.types.ts\";\nimport {\n executeProcess,\n quote,\n requireSuccess,\n} from \"../infrastructure/process.ts\";\nimport type { Executor } from \"../infrastructure/process.types.ts\";\nimport { registerCleanup } from \"../infrastructure/shutdown.ts\";\nimport { cacheMounts, validateCaches } from \"./container-cache.ts\";\nimport {\n cacheCreateOptions,\n cacheDefaults,\n} from \"./container-cache.constants.ts\";\nimport { containerCommand } from \"./container-command.ts\";\nimport { containerFiles } from \"./container-files.ts\";\nimport { containerMounts } from \"./container-mounts.ts\";\nimport { containerPlan } from \"./container-plan.ts\";\nimport { containerPreflight } from \"./container-preflight.ts\";\nimport { containerDefaults } from \"./container.constants.ts\";\nimport type { ContainerEngine, ContainerOptions } from \"./container.types.ts\";\n\nexport type { ContainerOptions } from \"./container.types.ts\";\n\nexport function imageName(repository: string): string {\n return `outpost:${\n basename(repository)\n .toLowerCase()\n .replace(/[^a-z0-9_.-]/g, \"-\") || \"workspace\"\n }`;\n}\n\nexport function containerProvider(\n engine: ContainerEngine,\n options: ContainerOptions = {},\n executor: Executor = executeProcess,\n platform: NodeJS.Platform = process.platform,\n): SandboxProvider {\n const config = {\n ...options,\n networks: containerNetworks(options),\n caches: (options.caches ?? []).map((cache) => ({ ...cache })),\n };\n invariant(\n config.repositoryMode === undefined ||\n config.repositoryMode === \"mounted\" ||\n config.repositoryMode === \"isolated\",\n \"repositoryMode must be mounted or isolated\",\n );\n validateCaches(config);\n if (config.cpus !== undefined)\n invariant(\n Number.isFinite(config.cpus) && config.cpus > 0,\n \"cpus must be positive\",\n );\n if (config.memoryMb !== undefined)\n invariant(\n Number.isSafeInteger(config.memoryMb) &&\n config.memoryMb >= containerDefaults.minimumMemoryMb,\n \"memoryMb must be at least 64\",\n );\n return {\n name: engine,\n placement: config.repositoryMode === \"isolated\" ? \"remote\" : \"mounted\",\n variables: { ...config.variables },\n ...(config.repositoryMode !== \"isolated\"\n ? {\n recover: (resourceId, recoveryOptions) =>\n recoverContainer(engine, executor, resourceId, recoveryOptions),\n }\n : {}),\n async acquire(context) {\n context.signal?.throwIfAborted();\n const name = `outpost-${randomUUID()}`;\n const image = config.image ?? imageName(context.repository);\n const user = config.user ?? {\n uid: process.getuid?.() ?? containerDefaults.uid,\n gid: process.getgid?.() ?? containerDefaults.gid,\n };\n invariant(\n Number.isInteger(user.uid) &&\n user.uid >= 0 &&\n Number.isInteger(user.gid) &&\n user.gid >= 0,\n \"Invalid container user\",\n );\n const call = (args: readonly string[], extra: Partial<Command> = {}) =>\n requireSuccess(\n {\n executable: engine,\n arguments: args,\n deadlineMs: containerDefaults.deadlineMs,\n ...extra,\n },\n executor,\n );\n await containerPreflight(engine, platform, call, config, image, user);\n const root =\n config.repositoryMode === \"isolated\"\n ? containerDefaults.isolatedRoot\n : containerDefaults.root,\n home = containerDefaults.home;\n const { env, volumes, fileParents } = await containerMounts(\n context,\n config,\n platform,\n root,\n home,\n );\n const caches = await cacheMounts(\n config.caches ?? [],\n context.repository,\n image,\n user,\n );\n for (const cache of caches)\n volumes.push(\"--volume\", `${cache.volume}:${cache.target}:nocopy`);\n const args = containerPlan({\n config,\n engine,\n user,\n root,\n name,\n image,\n volumes,\n fileParents,\n });\n let closed = false,\n releasing: Promise<void> | undefined;\n let unregister = () => {};\n const release = (): Promise<void> => {\n closed = true;\n releasing ??= call([\"rm\", \"--force\", name])\n .then(() => {\n unregister();\n })\n .catch((error) => {\n releasing = undefined;\n throw error;\n });\n return releasing;\n };\n try {\n for (const cache of caches)\n await call(\n [\n \"volume\",\n \"create\",\n ...cacheCreateOptions[engine],\n \"--label\",\n `${cacheDefaults.label}=true`,\n cache.volume,\n ],\n context.signal ? { signal: context.signal } : {},\n );\n await context.registerRecovery?.(name);\n context.signal?.throwIfAborted();\n await call(args, {\n ...(context.signal ? { signal: context.signal } : {}),\n });\n await call(\n [\"start\", name],\n context.signal ? { signal: context.signal } : {},\n );\n for (const cache of caches) {\n await call(\n [\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"chown\",\n `${user.uid}:${user.gid}`,\n cache.target,\n ],\n context.signal ? { signal: context.signal } : {},\n );\n await call(\n [\"exec\", name, \"chmod\", \"700\", cache.target],\n context.signal ? { signal: context.signal } : {},\n );\n }\n for (const parent of fileParents)\n await call([\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"sh\",\n \"-c\",\n `mkdir -p ${quote(parent)} && chown ${user.uid}:${user.gid} ${quote(parent)}`,\n ]);\n if (fileParents.size)\n await call([\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"chown\",\n `${user.uid}:${user.gid}`,\n home,\n ]);\n if (config.repositoryMode === \"isolated\")\n await call(\n [\n \"exec\",\n \"--user\",\n \"0:0\",\n name,\n \"sh\",\n \"-c\",\n `mkdir -p ${quote(root)} && chmod 700 ${quote(root)} /tmp/outpost && chown ${user.uid}:${user.gid} ${quote(root)} /tmp/outpost`,\n ],\n context.signal ? { signal: context.signal } : {},\n );\n await call([\n \"exec\",\n name,\n \"sh\",\n \"-c\",\n \"command -v setsid >/dev/null && command -v kill >/dev/null && command -v tar >/dev/null && command -v cp >/dev/null\",\n ]);\n } catch (cause) {\n try {\n await release();\n } catch (cleanup) {\n throw new AggregateError(\n [cause, cleanup],\n \"Sandbox provisioning and cleanup failed\",\n );\n }\n throw cause;\n }\n unregister = registerCleanup(release, () => {\n if (!closed)\n execFileSync(engine, [\"rm\", \"--force\", name], {\n timeout: containerDefaults.cleanupMs,\n stdio: \"ignore\",\n windowsHide: true,\n });\n });\n return {\n root,\n home,\n invoke: containerCommand({\n engine,\n config,\n executor,\n root,\n name,\n env,\n call,\n isClosed: () => closed,\n }),\n ...containerFiles({\n engine,\n config,\n executor,\n root,\n name,\n env,\n call,\n isClosed: () => closed,\n }),\n release,\n };\n },\n };\n}\n"]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"daytona-network.constants.js","sourceRoot":"","sources":["../../src/providers/daytona-network.constants.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,oBAAoB,GAAG;IAClC,iBAAiB;IACjB,kBAAkB;IAClB,iBAAiB;IACjB,kBAAkB;CACV,CAAC;AAEX,MAAM,CAAC,MAAM,oBAAoB,GAAG,EAAE,OAAO,EAAE,GAAG,EAAE,KAAK,EAAE,EAAE,EAAW,CAAC","sourcesContent":["export const daytonaNetworkFields = [\n \"networkBlockAll\",\n \"networkAllowList\",\n \"domainAllowList\",\n \"outboundProxyUrl\",\n] as const;\n\nexport const daytonaNetworkLimits = { domains: 100, cidrs: 10 } as const;\n"]}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { Sandbox } from "@daytona/sdk";
|
|
2
|
+
import type { DaytonaOptions } from "./daytona.types.ts";
|
|
3
|
+
export declare function daytonaNetworkPolicy(options: DaytonaOptions): Parameters<Sandbox["updateNetworkSettings"]>[0] | undefined;
|
|
4
|
+
export declare function confirmDaytonaNetworkPolicy(sandbox: Pick<Sandbox, "updateNetworkSettings">, policy: Parameters<Sandbox["updateNetworkSettings"]>[0]): Promise<void>;
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { isIP } from "node:net";
|
|
2
|
+
import { validateEgress } from "../domain/egress.js";
|
|
3
|
+
import { invariant, OutpostError } from "../domain/errors.js";
|
|
4
|
+
import { daytonaNetworkFields, daytonaNetworkLimits, } from "./daytona-network.constants.js";
|
|
5
|
+
export function daytonaNetworkPolicy(options) {
|
|
6
|
+
const policy = validateEgress(options.egress);
|
|
7
|
+
if (!policy)
|
|
8
|
+
return undefined;
|
|
9
|
+
invariant(daytonaNetworkFields.every((field) => options.create?.[field] === undefined), "Use egress or Daytona create network settings, not both");
|
|
10
|
+
if (policy.mode === "deny-all")
|
|
11
|
+
return { networkBlockAll: true };
|
|
12
|
+
const domains = policy.domains ?? [];
|
|
13
|
+
const cidrs = policy.allowCidrs ?? [];
|
|
14
|
+
invariant(!policy.denyCidrs?.length, "Daytona cannot enforce egress denyCidrs");
|
|
15
|
+
invariant(!domains.length || !cidrs.length, "Daytona cannot combine egress domains and allowCidrs");
|
|
16
|
+
invariant(cidrs.every((entry) => isIP(entry.split("/")[0]) === 4), "Daytona egress allowCidrs supports IPv4 only");
|
|
17
|
+
invariant(cidrs.length <= daytonaNetworkLimits.cidrs &&
|
|
18
|
+
domains.length <= daytonaNetworkLimits.domains, "Daytona egress supports at most 10 CIDRs or 100 domains");
|
|
19
|
+
const names = new Set(domains.map((name) => name.toLowerCase()));
|
|
20
|
+
invariant(domains.every((name) => !name.startsWith("*.") || names.has(name.slice(2).toLowerCase())), "Daytona wildcard domains also allow the apex; list the apex domain explicitly");
|
|
21
|
+
if (domains.length)
|
|
22
|
+
return { domainAllowList: domains.join(",") };
|
|
23
|
+
return { networkAllowList: cidrs.join(",") };
|
|
24
|
+
}
|
|
25
|
+
export async function confirmDaytonaNetworkPolicy(sandbox, policy) {
|
|
26
|
+
try {
|
|
27
|
+
await sandbox.updateNetworkSettings({ ...policy });
|
|
28
|
+
}
|
|
29
|
+
catch (cause) {
|
|
30
|
+
throw new OutpostError("provider", "Daytona could not confirm egress enforcement; sandbox-level network controls require Tier 3/4 and WRITE_SANDBOXES permission", { stage: "egress-confirmation" }, cause);
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
//# sourceMappingURL=daytona-network.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"daytona-network.js","sourceRoot":"","sources":["../../src/providers/daytona-network.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAEhC,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AACrD,OAAO,EAAE,SAAS,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,EACL,oBAAoB,EACpB,oBAAoB,GACrB,MAAM,gCAAgC,CAAC;AAGxC,MAAM,UAAU,oBAAoB,CAClC,OAAuB;IAEvB,MAAM,MAAM,GAAG,cAAc,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC;IAC9C,IAAI,CAAC,MAAM;QAAE,OAAO,SAAS,CAAC;IAC9B,SAAS,CACP,oBAAoB,CAAC,KAAK,CACxB,CAAC,KAAK,EAAE,EAAE,CAAC,OAAO,CAAC,MAAM,EAAE,CAAC,KAAK,CAAC,KAAK,SAAS,CACjD,EACD,yDAAyD,CAC1D,CAAC;IACF,IAAI,MAAM,CAAC,IAAI,KAAK,UAAU;QAAE,OAAO,EAAE,eAAe,EAAE,IAAI,EAAE,CAAC;IACjE,MAAM,OAAO,GAAG,MAAM,CAAC,OAAO,IAAI,EAAE,CAAC;IACrC,MAAM,KAAK,GAAG,MAAM,CAAC,UAAU,IAAI,EAAE,CAAC;IACtC,SAAS,CACP,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,EACzB,yCAAyC,CAC1C,CAAC;IACF,SAAS,CACP,CAAC,OAAO,CAAC,MAAM,IAAI,CAAC,KAAK,CAAC,MAAM,EAChC,sDAAsD,CACvD,CAAC;IACF,SAAS,CACP,KAAK,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAE,CAAC,KAAK,CAAC,CAAC,EACxD,8CAA8C,CAC/C,CAAC;IACF,SAAS,CACP,KAAK,CAAC,MAAM,IAAI,oBAAoB,CAAC,KAAK;QACxC,OAAO,CAAC,MAAM,IAAI,oBAAoB,CAAC,OAAO,EAChD,yDAAyD,CAC1D,CAAC;IACF,MAAM,KAAK,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC;IACjE,SAAS,CACP,OAAO,CAAC,KAAK,CACX,CAAC,IAAI,EAAE,EAAE,CACP,CAAC,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC,CACnE,EACD,+EAA+E,CAChF,CAAC;IACF,IAAI,OAAO,CAAC,MAAM;QAAE,OAAO,EAAE,eAAe,EAAE,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;IAClE,OAAO,EAAE,gBAAgB,EAAE,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;AAC/C,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,2BAA2B,CAC/C,OAA+C,EAC/C,MAAuD;IAEvD,IAAI,CAAC;QACH,MAAM,OAAO,CAAC,qBAAqB,CAAC,EAAE,GAAG,MAAM,EAAE,CAAC,CAAC;IACrD,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,MAAM,IAAI,YAAY,CACpB,UAAU,EACV,8HAA8H,EAC9H,EAAE,KAAK,EAAE,qBAAqB,EAAE,EAChC,KAAK,CACN,CAAC;IACJ,CAAC;AACH,CAAC","sourcesContent":["import { isIP } from \"node:net\";\nimport type { Sandbox } from \"@daytona/sdk\";\nimport { validateEgress } from \"../domain/egress.ts\";\nimport { invariant, OutpostError } from \"../domain/errors.ts\";\nimport {\n daytonaNetworkFields,\n daytonaNetworkLimits,\n} from \"./daytona-network.constants.ts\";\nimport type { DaytonaOptions } from \"./daytona.types.ts\";\n\nexport function daytonaNetworkPolicy(\n options: DaytonaOptions,\n): Parameters<Sandbox[\"updateNetworkSettings\"]>[0] | undefined {\n const policy = validateEgress(options.egress);\n if (!policy) return undefined;\n invariant(\n daytonaNetworkFields.every(\n (field) => options.create?.[field] === undefined,\n ),\n \"Use egress or Daytona create network settings, not both\",\n );\n if (policy.mode === \"deny-all\") return { networkBlockAll: true };\n const domains = policy.domains ?? [];\n const cidrs = policy.allowCidrs ?? [];\n invariant(\n !policy.denyCidrs?.length,\n \"Daytona cannot enforce egress denyCidrs\",\n );\n invariant(\n !domains.length || !cidrs.length,\n \"Daytona cannot combine egress domains and allowCidrs\",\n );\n invariant(\n cidrs.every((entry) => isIP(entry.split(\"/\")[0]!) === 4),\n \"Daytona egress allowCidrs supports IPv4 only\",\n );\n invariant(\n cidrs.length <= daytonaNetworkLimits.cidrs &&\n domains.length <= daytonaNetworkLimits.domains,\n \"Daytona egress supports at most 10 CIDRs or 100 domains\",\n );\n const names = new Set(domains.map((name) => name.toLowerCase()));\n invariant(\n domains.every(\n (name) =>\n !name.startsWith(\"*.\") || names.has(name.slice(2).toLowerCase()),\n ),\n \"Daytona wildcard domains also allow the apex; list the apex domain explicitly\",\n );\n if (domains.length) return { domainAllowList: domains.join(\",\") };\n return { networkAllowList: cidrs.join(\",\") };\n}\n\nexport async function confirmDaytonaNetworkPolicy(\n sandbox: Pick<Sandbox, \"updateNetworkSettings\">,\n policy: Parameters<Sandbox[\"updateNetworkSettings\"]>[0],\n): Promise<void> {\n try {\n await sandbox.updateNetworkSettings({ ...policy });\n } catch (cause) {\n throw new OutpostError(\n \"provider\",\n \"Daytona could not confirm egress enforcement; sandbox-level network controls require Tier 3/4 and WRITE_SANDBOXES permission\",\n { stage: \"egress-confirmation\" },\n cause,\n );\n }\n}\n"]}
|
|
@@ -3,3 +3,4 @@ import type { SandboxProvider } from "../domain/sandbox.types.ts";
|
|
|
3
3
|
import type { DaytonaOptions } from "./daytona.types.ts";
|
|
4
4
|
export type { DaytonaOptions } from "./daytona.types.ts";
|
|
5
5
|
export declare function daytonaSandboxProvider(options?: DaytonaOptions, connect?: (config?: DaytonaConfig) => Promise<Pick<Daytona, "create" | "delete">>): SandboxProvider;
|
|
6
|
+
export type { EgressPolicy } from "../domain/egress.types.ts";
|
|
@@ -1,12 +1,13 @@
|
|
|
1
|
-
import { invariant } from "../domain/errors.js";
|
|
2
1
|
import { posix } from "node:path";
|
|
3
2
|
import { fileBatches } from "./file-batches.js";
|
|
4
3
|
import { registerCleanup } from "../infrastructure/shutdown.js";
|
|
5
4
|
import { cloudRoots } from "./cloud.constants.js";
|
|
5
|
+
import { daytonaNetworkPolicy, confirmDaytonaNetworkPolicy, } from "./daytona-network.js";
|
|
6
6
|
import { daytonaCommand } from "./daytona-command.js";
|
|
7
7
|
import { daytonaFiles } from "./daytona-files.js";
|
|
8
8
|
export function daytonaSandboxProvider(options = {}, connect = async (config) => new (await import("@daytona/sdk")).Daytona(config)) {
|
|
9
|
-
|
|
9
|
+
const networkPolicy = daytonaNetworkPolicy(options);
|
|
10
|
+
const create = { ...options.create, ...networkPolicy };
|
|
10
11
|
return {
|
|
11
12
|
name: "daytona",
|
|
12
13
|
placement: "remote",
|
|
@@ -14,7 +15,7 @@ export function daytonaSandboxProvider(options = {}, connect = async (config) =>
|
|
|
14
15
|
async acquire(context) {
|
|
15
16
|
context.signal?.throwIfAborted();
|
|
16
17
|
const client = await connect(options.connection);
|
|
17
|
-
const sandbox = await client.create(
|
|
18
|
+
const sandbox = await client.create({ ...create });
|
|
18
19
|
let closed = false, releasing;
|
|
19
20
|
let unregister = () => { };
|
|
20
21
|
const release = () => (releasing ??= client
|
|
@@ -31,6 +32,11 @@ export function daytonaSandboxProvider(options = {}, connect = async (config) =>
|
|
|
31
32
|
let home;
|
|
32
33
|
let root;
|
|
33
34
|
try {
|
|
35
|
+
context.signal?.throwIfAborted();
|
|
36
|
+
if (networkPolicy) {
|
|
37
|
+
await confirmDaytonaNetworkPolicy(sandbox, networkPolicy);
|
|
38
|
+
context.signal?.throwIfAborted();
|
|
39
|
+
}
|
|
34
40
|
home = (await sandbox.getUserHomeDir()) ?? cloudRoots.daytonaHome;
|
|
35
41
|
root = options.root ?? posix.join(home, "outpost");
|
|
36
42
|
await sandbox.fs.createFolder(root, "755");
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"daytona.js","sourceRoot":"","sources":["../../src/providers/daytona.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"daytona.js","sourceRoot":"","sources":["../../src/providers/daytona.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Daytona, DaytonaConfig } from \"@daytona/sdk\";\nimport { posix } from \"node:path\";\nimport type { SandboxProvider } from \"../domain/sandbox.types.ts\";\nimport { fileBatches } from \"./file-batches.ts\";\nimport { registerCleanup } from \"../infrastructure/shutdown.ts\";\nimport { cloudRoots } from \"./cloud.constants.ts\";\nimport {\n daytonaNetworkPolicy,\n confirmDaytonaNetworkPolicy,\n} from \"./daytona-network.ts\";\nimport { daytonaCommand } from \"./daytona-command.ts\";\nimport { daytonaFiles } from \"./daytona-files.ts\";\nimport type { DaytonaOptions } from \"./daytona.types.ts\";\n\nexport type { DaytonaOptions } from \"./daytona.types.ts\";\n\nexport function daytonaSandboxProvider(\n options: DaytonaOptions = {},\n connect: (\n config?: DaytonaConfig,\n ) => Promise<Pick<Daytona, \"create\" | \"delete\">> = async (config) =>\n new (await import(\"@daytona/sdk\")).Daytona(config),\n): SandboxProvider {\n const networkPolicy = daytonaNetworkPolicy(options);\n const create = { ...options.create, ...networkPolicy };\n return {\n name: \"daytona\",\n placement: \"remote\",\n variables: { ...options.variables },\n async acquire(context) {\n context.signal?.throwIfAborted();\n const client = await connect(options.connection);\n const sandbox = await client.create({ ...create });\n let closed = false,\n releasing: Promise<void> | undefined;\n let unregister = () => {};\n const release = () =>\n (releasing ??= client\n .delete(sandbox)\n .then(() => {\n closed = true;\n unregister();\n })\n .catch((error) => {\n releasing = undefined;\n throw error;\n }));\n unregister = registerCleanup(release);\n let home: string;\n let root: string;\n try {\n context.signal?.throwIfAborted();\n if (networkPolicy) {\n await confirmDaytonaNetworkPolicy(sandbox, networkPolicy);\n context.signal?.throwIfAborted();\n }\n home = (await sandbox.getUserHomeDir()) ?? cloudRoots.daytonaHome;\n root = options.root ?? posix.join(home, \"outpost\");\n await sandbox.fs.createFolder(root, \"755\");\n } catch (cause) {\n try {\n await release();\n } catch (cleanup) {\n throw new AggregateError(\n [cause, cleanup],\n \"Cloud setup and cleanup failed\",\n );\n }\n throw cause;\n }\n const lease = {\n root,\n home,\n invoke: daytonaCommand({\n sandbox,\n root,\n options,\n context,\n isClosed: () => closed,\n }),\n ...daytonaFiles(sandbox),\n release,\n };\n return { ...lease, fileTransfers: fileBatches(lease) };\n },\n };\n}\n\nexport type { EgressPolicy } from \"../domain/egress.types.ts\";\n"]}
|
|
@@ -1,7 +1,9 @@
|
|
|
1
|
+
import type { EgressPolicy } from "../domain/egress.types.ts";
|
|
1
2
|
import type { CreateSandboxFromImageParams, CreateSandboxFromSnapshotParams, DaytonaConfig, Sandbox as DaytonaSandbox } from "@daytona/sdk";
|
|
2
3
|
import type { Variables } from "../domain/command.types.ts";
|
|
3
4
|
import type { SandboxContext } from "../domain/sandbox.types.ts";
|
|
4
5
|
export interface DaytonaOptions {
|
|
6
|
+
readonly egress?: EgressPolicy;
|
|
5
7
|
readonly connection?: DaytonaConfig;
|
|
6
8
|
readonly create?: CreateSandboxFromImageParams | CreateSandboxFromSnapshotParams;
|
|
7
9
|
readonly variables?: Variables;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"daytona.types.js","sourceRoot":"","sources":["../../src/providers/daytona.types.ts"],"names":[],"mappings":"","sourcesContent":["import type {\n CreateSandboxFromImageParams,\n CreateSandboxFromSnapshotParams,\n DaytonaConfig,\n Sandbox as DaytonaSandbox,\n} from \"@daytona/sdk\";\nimport type { Variables } from \"../domain/command.types.ts\";\nimport type { SandboxContext } from \"../domain/sandbox.types.ts\";\n\nexport interface DaytonaOptions {\n readonly connection?: DaytonaConfig;\n readonly create?:\n CreateSandboxFromImageParams | CreateSandboxFromSnapshotParams;\n readonly variables?: Variables;\n readonly root?: string;\n readonly retain?: number;\n}\n\nexport interface DaytonaRuntime {\n readonly sandbox: DaytonaSandbox;\n readonly root: string;\n readonly options: DaytonaOptions;\n readonly context: SandboxContext;\n readonly isClosed: () => boolean;\n}\n"]}
|
|
1
|
+
{"version":3,"file":"daytona.types.js","sourceRoot":"","sources":["../../src/providers/daytona.types.ts"],"names":[],"mappings":"","sourcesContent":["import type { EgressPolicy } from \"../domain/egress.types.ts\";\nimport type {\n CreateSandboxFromImageParams,\n CreateSandboxFromSnapshotParams,\n DaytonaConfig,\n Sandbox as DaytonaSandbox,\n} from \"@daytona/sdk\";\nimport type { Variables } from \"../domain/command.types.ts\";\nimport type { SandboxContext } from \"../domain/sandbox.types.ts\";\n\nexport interface DaytonaOptions {\n readonly egress?: EgressPolicy;\n readonly connection?: DaytonaConfig;\n readonly create?:\n CreateSandboxFromImageParams | CreateSandboxFromSnapshotParams;\n readonly variables?: Variables;\n readonly root?: string;\n readonly retain?: number;\n}\n\nexport interface DaytonaRuntime {\n readonly sandbox: DaytonaSandbox;\n readonly root: string;\n readonly options: DaytonaOptions;\n readonly context: SandboxContext;\n readonly isClosed: () => boolean;\n}\n"]}
|
|
@@ -5,7 +5,7 @@ import { firecrackerDefaults } from "./firecracker.constants.js";
|
|
|
5
5
|
export function firecrackerSsh(options, script) {
|
|
6
6
|
const ssh = options.ssh;
|
|
7
7
|
return {
|
|
8
|
-
executable: ssh.binary ?? "ssh",
|
|
8
|
+
executable: ssh.binary ?? (options.jailer ? "/usr/bin/ssh" : "ssh"),
|
|
9
9
|
arguments: [
|
|
10
10
|
"-F",
|
|
11
11
|
"/dev/null",
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"firecracker-command.js","sourceRoot":"","sources":["../../src/providers/firecracker-command.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,SAAS,EAAE,YAAY,EAAE,QAAQ,EAAE,MAAM,qBAAqB,CAAC;AAGxE,OAAO,EACL,cAAc,EACd,KAAK,EACL,cAAc,GACf,MAAM,8BAA8B,CAAC;AACtC,OAAO,EAAE,mBAAmB,EAAE,MAAM,4BAA4B,CAAC;AAMjE,MAAM,UAAU,cAAc,CAC5B,OAA2B,EAC3B,MAAc;IAEd,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC;IACxB,OAAO;QACL,UAAU,EAAE,GAAG,CAAC,MAAM,IAAI,KAAK;
|
|
1
|
+
{"version":3,"file":"firecracker-command.js","sourceRoot":"","sources":["../../src/providers/firecracker-command.ts"],"names":[],"mappings":"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","sourcesContent":["import { randomUUID } from \"node:crypto\";\nimport { invariant, OutpostError, positive } from \"../domain/errors.ts\";\nimport type { Command } from \"../domain/command.types.ts\";\nimport type { SandboxLease } from \"../domain/sandbox.types.ts\";\nimport {\n executeProcess,\n quote,\n requireSuccess,\n} from \"../infrastructure/process.ts\";\nimport { firecrackerDefaults } from \"./firecracker.constants.ts\";\nimport type {\n FirecrackerOptions,\n FirecrackerRuntime,\n} from \"./firecracker.types.ts\";\n\nexport function firecrackerSsh(\n options: FirecrackerOptions,\n script: string,\n): Command {\n const ssh = options.ssh;\n return {\n executable: ssh.binary ?? (options.jailer ? \"/usr/bin/ssh\" : \"ssh\"),\n arguments: [\n \"-F\",\n \"/dev/null\",\n \"-T\",\n \"-o\",\n \"BatchMode=yes\",\n \"-o\",\n \"IdentitiesOnly=yes\",\n \"-o\",\n \"StrictHostKeyChecking=yes\",\n \"-o\",\n `UserKnownHostsFile=${ssh.knownHosts}`,\n \"-o\",\n \"GlobalKnownHostsFile=/dev/null\",\n \"-o\",\n \"ConnectTimeout=2\",\n \"-o\",\n \"ServerAliveInterval=2\",\n \"-o\",\n \"ServerAliveCountMax=2\",\n \"-i\",\n ssh.identity,\n \"-p\",\n String(ssh.port ?? 22),\n \"-l\",\n ssh.user,\n \"--\",\n ssh.host,\n script,\n ],\n };\n}\n\nexport function firecrackerCommand(\n runtime: FirecrackerRuntime,\n): SandboxLease[\"invoke\"] {\n return async (command) => {\n if (runtime.isClosed())\n throw new OutpostError(\"provider\", \"Firecracker sandbox is closed\");\n invariant(\n !command.interactive && !command.elevated,\n \"Firecracker research provider does not support interactive or elevated commands\",\n );\n command.signal?.throwIfAborted();\n const variables = { ...runtime.variables, ...command.variables };\n invariant(\n Object.keys(variables).every((key) =>\n /^[A-Za-z_][A-Za-z0-9_]*$/.test(key),\n ),\n \"Invalid environment key\",\n );\n const id = `/tmp/outpost-command-${randomUUID()}`;\n const wrapper = `umask 077; echo $$ > ${quote(id)}; test ! -e ${quote(id + \".cancel\")} || exit 130; cd ${quote(command.directory ?? runtime.root)} || exit; exec env ${Object.entries(\n variables,\n )\n .map(([key, value]) => quote(`${key}=${value}`))\n .join(\n \" \",\n )} ${[command.executable, ...(command.arguments ?? [])].map(quote).join(\" \")}`;\n const stop = new AbortController();\n const signal = command.signal\n ? AbortSignal.any([command.signal, stop.signal])\n : stop.signal;\n const deadlineMs = command.deadlineMs ?? firecrackerDefaults.commandMs;\n positive(deadlineMs, \"deadlineMs\");\n let cancellation: Promise<unknown> | undefined;\n const cancel = () => {\n cancellation ??= requireSuccess(\n {\n ...firecrackerSsh(\n runtime.options,\n `umask 077; touch ${quote(id + \".cancel\")}; if [ -f ${quote(id)} ]; then node -e ${quote(\"const fs=require('node:fs');const pid=Number(fs.readFileSync(process.argv[1],'utf8'));if(!Number.isSafeInteger(pid)||pid<2)process.exit(1);const kill=s=>{try{process.kill(-pid,s)}catch(e){if(e.code!=='ESRCH')throw e}};kill('SIGTERM');setTimeout(()=>kill('SIGKILL'),100)\")} ${quote(id)}; fi`,\n ),\n deadlineMs: firecrackerDefaults.cleanupMs,\n },\n executeProcess,\n );\n void cancellation.catch(() => undefined);\n };\n signal.addEventListener(\"abort\", cancel, { once: true });\n const timer = setTimeout(\n () =>\n stop.abort(\n new OutpostError(\"timeout\", `Command exceeded ${deadlineMs} ms`),\n ),\n deadlineMs,\n );\n let interrupted = false;\n try {\n const {\n directory: _directory,\n variables: _variables,\n ...invocation\n } = command;\n const result = await runtime.executor({\n ...invocation,\n ...(command.observe\n ? {\n observe: (channel, text) => {\n try {\n command.observe!(channel, text);\n } catch (cause) {\n stop.abort(cause);\n }\n },\n }\n : {}),\n signal,\n ...firecrackerSsh(\n runtime.options,\n `setsid --wait sh -c ${quote(wrapper)}`,\n ),\n });\n signal.throwIfAborted();\n return result;\n } catch (cause) {\n interrupted = true;\n try {\n cancel();\n await cancellation;\n } catch (cleanup) {\n throw new AggregateError(\n [cause, cleanup],\n \"Guest cancellation could not be confirmed; release the VM\",\n );\n }\n throw cause;\n } finally {\n clearTimeout(timer);\n signal.removeEventListener(\"abort\", cancel);\n if (!interrupted && !runtime.isClosed())\n await executeProcess({\n ...firecrackerSsh(runtime.options, `rm -f -- ${quote(id)}`),\n deadlineMs: firecrackerDefaults.cleanupMs,\n }).catch(() => undefined);\n }\n };\n}\n"]}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export declare const firecrackerJailerLimits: {
|
|
2
|
+
readonly cgroupRoot: "/sys/fs/cgroup";
|
|
3
|
+
readonly cgroupFilesystem: 1667723888;
|
|
4
|
+
readonly cpuPeriodUs: 100000;
|
|
5
|
+
readonly minimumCpuQuotaUs: 1000;
|
|
6
|
+
readonly minimumProcesses: 16;
|
|
7
|
+
readonly maximumIdentity: 4294967294;
|
|
8
|
+
readonly bytesPerMiB: number;
|
|
9
|
+
};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
export const firecrackerJailerLimits = {
|
|
2
|
+
cgroupRoot: "/sys/fs/cgroup",
|
|
3
|
+
cgroupFilesystem: 0x63677270,
|
|
4
|
+
cpuPeriodUs: 100_000,
|
|
5
|
+
minimumCpuQuotaUs: 1000,
|
|
6
|
+
minimumProcesses: 16,
|
|
7
|
+
maximumIdentity: 4_294_967_294,
|
|
8
|
+
bytesPerMiB: 1024 * 1024,
|
|
9
|
+
};
|
|
10
|
+
//# sourceMappingURL=firecracker-jailer.constants.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"firecracker-jailer.constants.js","sourceRoot":"","sources":["../../src/providers/firecracker-jailer.constants.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,uBAAuB,GAAG;IACrC,UAAU,EAAE,gBAAgB;IAC5B,gBAAgB,EAAE,UAAU;IAC5B,WAAW,EAAE,OAAO;IACpB,iBAAiB,EAAE,IAAI;IACvB,gBAAgB,EAAE,EAAE;IACpB,eAAe,EAAE,aAAa;IAC9B,WAAW,EAAE,IAAI,GAAG,IAAI;CAChB,CAAC","sourcesContent":["export const firecrackerJailerLimits = {\n cgroupRoot: \"/sys/fs/cgroup\",\n cgroupFilesystem: 0x63677270,\n cpuPeriodUs: 100_000,\n minimumCpuQuotaUs: 1000,\n minimumProcesses: 16,\n maximumIdentity: 4_294_967_294,\n bytesPerMiB: 1024 * 1024,\n} as const;\n"]}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { FirecrackerOptions, FirecrackerLaunch } from "./firecracker.types.ts";
|
|
2
|
+
export declare function validateJailer(options: FirecrackerOptions): void;
|
|
3
|
+
export declare function trustedJailerPath(path: string): Promise<void>;
|
|
4
|
+
export declare function prepareJailer(options: FirecrackerOptions, directory: string, signal?: AbortSignal): Promise<FirecrackerLaunch>;
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
import { randomUUID } from "node:crypto";
|
|
2
|
+
import { constants } from "node:fs";
|
|
3
|
+
import { access, chmod, chown, copyFile, lstat, mkdir, readFile, rm, rmdir, statfs, writeFile, } from "node:fs/promises";
|
|
4
|
+
import { basename, dirname, isAbsolute, join, normalize, relative, } from "node:path";
|
|
5
|
+
import { invariant, OutpostError } from "../domain/errors.js";
|
|
6
|
+
import { firecrackerJailerLimits as limits } from "./firecracker-jailer.constants.js";
|
|
7
|
+
import { firecrackerDefaults } from "./firecracker.constants.js";
|
|
8
|
+
export function validateJailer(options) {
|
|
9
|
+
const jailer = options.jailer;
|
|
10
|
+
if (!jailer)
|
|
11
|
+
return;
|
|
12
|
+
for (const path of [jailer.binary, jailer.directory, jailer.cgroup])
|
|
13
|
+
invariant(path.startsWith("/") &&
|
|
14
|
+
!path.includes("\0") &&
|
|
15
|
+
!path.split("/").includes(".."), "Jailer paths must be absolute without traversal");
|
|
16
|
+
invariant(jailer.cgroup.startsWith(`${limits.cgroupRoot}/`) &&
|
|
17
|
+
relative(limits.cgroupRoot, jailer.cgroup) !== "", "Jailer requires a dedicated cgroup v2 parent beneath /sys/fs/cgroup");
|
|
18
|
+
for (const value of [
|
|
19
|
+
jailer.uid,
|
|
20
|
+
jailer.gid,
|
|
21
|
+
jailer.cpuQuotaUs,
|
|
22
|
+
jailer.memoryMaxMb,
|
|
23
|
+
jailer.processes,
|
|
24
|
+
])
|
|
25
|
+
invariant(Number.isSafeInteger(value) && value > 0, "Jailer identities and resource limits must be positive integers");
|
|
26
|
+
invariant(jailer.cpuQuotaUs >= limits.minimumCpuQuotaUs, "Jailer CPU quota must be at least 1000 microseconds per 100000 microseconds");
|
|
27
|
+
invariant(jailer.memoryMaxMb > (options.memoryMb ?? firecrackerDefaults.memoryMb), "Jailer memory limit must exceed guest memory to allow VMM overhead");
|
|
28
|
+
invariant(Number.isSafeInteger(jailer.memoryMaxMb * limits.bytesPerMiB), "Jailer memory limit is too large");
|
|
29
|
+
invariant(jailer.uid <= limits.maximumIdentity &&
|
|
30
|
+
jailer.gid <= limits.maximumIdentity, "Jailer identities must fit Linux UID/GID limits");
|
|
31
|
+
invariant(jailer.processes >= limits.minimumProcesses, "Jailer process limit must allow at least 16 threads");
|
|
32
|
+
}
|
|
33
|
+
export async function trustedJailerPath(path) {
|
|
34
|
+
invariant(isAbsolute(path) && normalize(path) === path, "Jailer paths must be canonical absolute paths");
|
|
35
|
+
let current = path;
|
|
36
|
+
while (true) {
|
|
37
|
+
const entry = await lstat(current);
|
|
38
|
+
invariant(!entry.isSymbolicLink() && entry.uid === 0 && (entry.mode & 0o022) === 0, `Jailer path must be root-owned, without symlinks or group/world write access: ${current}`);
|
|
39
|
+
const parent = dirname(current);
|
|
40
|
+
if (parent === current)
|
|
41
|
+
return;
|
|
42
|
+
current = parent;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
export async function prepareJailer(options, directory, signal) {
|
|
46
|
+
const jailer = options.jailer;
|
|
47
|
+
invariant(jailer, "Jailer configuration is required");
|
|
48
|
+
invariant(process.getuid?.() === 0, "Jailer allocation requires a trusted root supervisor; Outpost never invokes sudo");
|
|
49
|
+
await Promise.all([
|
|
50
|
+
jailer.binary,
|
|
51
|
+
jailer.directory,
|
|
52
|
+
jailer.cgroup,
|
|
53
|
+
options.binary,
|
|
54
|
+
options.kernel,
|
|
55
|
+
options.rootfs,
|
|
56
|
+
options.ssh.identity,
|
|
57
|
+
options.ssh.knownHosts,
|
|
58
|
+
options.ssh.binary ?? "/usr/bin/ssh",
|
|
59
|
+
].map(trustedJailerPath));
|
|
60
|
+
await access(jailer.binary, constants.X_OK);
|
|
61
|
+
invariant((await statfs(jailer.cgroup)).type === limits.cgroupFilesystem, "Jailer parent must be on cgroup v2");
|
|
62
|
+
const controllers = (await readFile(join(jailer.cgroup, "cgroup.subtree_control"), "utf8")).split(/\s+/);
|
|
63
|
+
invariant(["cpu", "memory", "pids"].every((name) => controllers.includes(name)), "Enable cpu, memory and pids controllers in the dedicated jailer parent");
|
|
64
|
+
const parent = join(jailer.directory, basename(options.binary));
|
|
65
|
+
await mkdir(parent, { recursive: true, mode: 0o700 });
|
|
66
|
+
await trustedJailerPath(parent);
|
|
67
|
+
const id = randomUUID();
|
|
68
|
+
const jail = join(parent, id);
|
|
69
|
+
const root = join(jail, "root");
|
|
70
|
+
const cgroup = join(jailer.cgroup, id);
|
|
71
|
+
await mkdir(jail, { mode: 0o700 });
|
|
72
|
+
const cleanup = async () => {
|
|
73
|
+
try {
|
|
74
|
+
const events = await readFile(join(cgroup, "cgroup.events"), "utf8");
|
|
75
|
+
if (/^populated 1$/m.test(events))
|
|
76
|
+
throw new OutpostError("provider", `Jailer cgroup is still populated; recovery files retained at ${jail}`);
|
|
77
|
+
await rmdir(cgroup);
|
|
78
|
+
}
|
|
79
|
+
catch (cause) {
|
|
80
|
+
if (!(cause instanceof Error &&
|
|
81
|
+
"code" in cause &&
|
|
82
|
+
cause.code === "ENOENT"))
|
|
83
|
+
throw cause;
|
|
84
|
+
}
|
|
85
|
+
await rm(jail, { recursive: true, force: true });
|
|
86
|
+
};
|
|
87
|
+
try {
|
|
88
|
+
await mkdir(root, { mode: 0o700 });
|
|
89
|
+
await copyFile(options.kernel, join(root, "kernel"));
|
|
90
|
+
await copyFile(join(directory, "rootfs.ext4"), join(root, "rootfs.ext4"), constants.COPYFILE_FICLONE);
|
|
91
|
+
const config = JSON.parse(await readFile(join(directory, "config.json"), "utf8"));
|
|
92
|
+
invariant(config !== null &&
|
|
93
|
+
typeof config === "object" &&
|
|
94
|
+
"boot-source" in config &&
|
|
95
|
+
"drives" in config, "Invalid Firecracker boot configuration");
|
|
96
|
+
await writeFile(join(root, "config.json"), JSON.stringify({
|
|
97
|
+
...config,
|
|
98
|
+
"boot-source": {
|
|
99
|
+
kernel_image_path: "/kernel",
|
|
100
|
+
boot_args: options.bootArgs,
|
|
101
|
+
},
|
|
102
|
+
drives: [
|
|
103
|
+
{
|
|
104
|
+
drive_id: "rootfs",
|
|
105
|
+
path_on_host: "/rootfs.ext4",
|
|
106
|
+
is_root_device: true,
|
|
107
|
+
is_read_only: false,
|
|
108
|
+
},
|
|
109
|
+
],
|
|
110
|
+
}), { mode: 0o400 });
|
|
111
|
+
for (const name of ["kernel", "rootfs.ext4", "config.json"]) {
|
|
112
|
+
await chown(join(root, name), jailer.uid, jailer.gid);
|
|
113
|
+
await chmod(join(root, name), name === "rootfs.ext4" ? 0o600 : 0o400);
|
|
114
|
+
}
|
|
115
|
+
signal?.throwIfAborted();
|
|
116
|
+
}
|
|
117
|
+
catch (cause) {
|
|
118
|
+
try {
|
|
119
|
+
await cleanup();
|
|
120
|
+
}
|
|
121
|
+
catch (cleanupFailure) {
|
|
122
|
+
throw new AggregateError([cause, cleanupFailure], `Jailer preparation and cleanup failed; inspect ${jail}`);
|
|
123
|
+
}
|
|
124
|
+
throw cause;
|
|
125
|
+
}
|
|
126
|
+
return {
|
|
127
|
+
binary: jailer.binary,
|
|
128
|
+
arguments: [
|
|
129
|
+
"--id",
|
|
130
|
+
id,
|
|
131
|
+
"--exec-file",
|
|
132
|
+
options.binary,
|
|
133
|
+
"--uid",
|
|
134
|
+
String(jailer.uid),
|
|
135
|
+
"--gid",
|
|
136
|
+
String(jailer.gid),
|
|
137
|
+
"--chroot-base-dir",
|
|
138
|
+
jailer.directory,
|
|
139
|
+
"--cgroup-version",
|
|
140
|
+
"2",
|
|
141
|
+
"--parent-cgroup",
|
|
142
|
+
relative(limits.cgroupRoot, jailer.cgroup),
|
|
143
|
+
"--cgroup",
|
|
144
|
+
`cpu.max=${jailer.cpuQuotaUs} ${limits.cpuPeriodUs}`,
|
|
145
|
+
"--cgroup",
|
|
146
|
+
`memory.max=${jailer.memoryMaxMb * limits.bytesPerMiB}`,
|
|
147
|
+
"--cgroup",
|
|
148
|
+
"memory.swap.max=0",
|
|
149
|
+
"--cgroup",
|
|
150
|
+
`pids.max=${jailer.processes}`,
|
|
151
|
+
"--",
|
|
152
|
+
"--api-sock",
|
|
153
|
+
"/api.sock",
|
|
154
|
+
"--config-file",
|
|
155
|
+
"/config.json",
|
|
156
|
+
],
|
|
157
|
+
async stop() {
|
|
158
|
+
try {
|
|
159
|
+
await writeFile(join(cgroup, "cgroup.kill"), "1");
|
|
160
|
+
}
|
|
161
|
+
catch (cause) {
|
|
162
|
+
if (!(cause instanceof Error &&
|
|
163
|
+
"code" in cause &&
|
|
164
|
+
cause.code === "ENOENT"))
|
|
165
|
+
throw cause;
|
|
166
|
+
}
|
|
167
|
+
},
|
|
168
|
+
cleanup,
|
|
169
|
+
};
|
|
170
|
+
}
|
|
171
|
+
//# sourceMappingURL=firecracker-jailer.js.map
|