@fitlab-ai/agent-infra 0.9.14 → 0.10.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/README.md +10 -0
- package/README.zh-CN.md +10 -0
- package/bin/internal-cli.sh +45 -0
- package/dist/bin/internal-cli.js +93 -30
- package/dist/lib/agent-clients/adapters/codex-lifecycle/capability-store.js +165 -27
- package/dist/lib/agent-clients/adapters/codex-lifecycle/sandbox-controller.js +9 -4
- package/dist/lib/agent-clients/adapters/codex-lifecycle/store.js +43 -3
- package/dist/lib/defaults.json +103 -103
- package/dist/lib/fs/durable-write.js +39 -0
- package/dist/lib/fs/file-lock.js +111 -0
- package/dist/lib/host-control/audit.js +19 -0
- package/dist/lib/host-control/client.js +142 -0
- package/dist/lib/host-control/command.js +49 -0
- package/dist/lib/host-control/path.js +160 -0
- package/dist/lib/host-control/secure-fs.js +140 -0
- package/dist/lib/host-control/server.js +159 -0
- package/dist/lib/host-control/service.js +112 -0
- package/dist/lib/init.js +11 -2
- package/dist/lib/internal/cli-route-inventory.js +4 -2
- package/dist/lib/internal/codex-lifecycle.js +6 -6
- package/dist/lib/internal/demo-promotion.js +322 -0
- package/dist/lib/internal/demo-transcript.js +454 -0
- package/dist/lib/internal/host-control.js +28 -0
- package/dist/lib/internal/manual-validation.js +331 -0
- package/dist/lib/internal/platform-pr.js +18 -4
- package/dist/lib/internal/release-workflow.js +63 -84
- package/dist/lib/internal/sandbox-control.js +149 -2
- package/dist/lib/internal/task-artifact.js +16 -263
- package/dist/lib/internal/task-create.js +6 -5
- package/dist/lib/internal/task-event.js +37 -37
- package/dist/lib/internal/task-lifecycle.js +2 -2
- package/dist/lib/internal/task-operation-registry.js +101 -4
- package/dist/lib/internal/task-review.js +11 -56
- package/dist/lib/internal/task-validate.js +30 -10
- package/dist/lib/owned-path.js +33 -0
- package/dist/lib/platform/check-status.js +11 -0
- package/dist/lib/platform/comment-safety.js +4 -1
- package/dist/lib/platform/completion-backfill.js +1 -1
- package/dist/lib/platform/github-data.js +241 -0
- package/dist/lib/platform/github-provider.js +15 -20
- package/dist/lib/platform/issue-comments.js +18 -12
- package/dist/lib/platform/issues.js +2 -180
- package/dist/lib/platform/pr-change-report.js +5 -4
- package/dist/lib/platform/pr-checks.js +12 -65
- package/dist/lib/platform/pr-summary.js +117 -33
- package/dist/lib/platform/pull-requests.js +5 -108
- package/dist/lib/platform/snapshots.js +2 -0
- package/dist/lib/platform/task-identities.js +2 -9
- package/dist/lib/platform/verification-sync.js +132 -143
- package/dist/lib/pr-review/evidence-grading.js +4 -8
- package/dist/lib/release/workflow.js +1 -1
- package/dist/lib/sandbox/commands/create.js +7 -2
- package/dist/lib/sandbox/commands/rm.js +19 -1511
- package/dist/lib/sandbox/control/audit.js +203 -0
- package/dist/lib/sandbox/control/client.js +93 -54
- package/dist/lib/sandbox/control/executor.js +129 -65
- package/dist/lib/sandbox/control/finalization-response.js +27 -0
- package/dist/lib/sandbox/control/identity-sentinel.js +107 -0
- package/dist/lib/sandbox/control/lifecycle.js +36 -2
- package/dist/lib/sandbox/control/native-file-lock.js +6 -98
- package/dist/lib/sandbox/control/protocol.js +55 -4
- package/dist/lib/sandbox/control/server.js +518 -127
- package/dist/lib/sandbox/control/state.js +64 -0
- package/dist/lib/sandbox/control/task-workflow.js +74 -0
- package/dist/lib/sandbox/control/workflow-executor.js +89 -0
- package/dist/lib/sandbox/index.js +1 -2
- package/dist/lib/sandbox/recovery.js +28 -4
- package/dist/lib/sandbox/removal.js +822 -0
- package/dist/lib/sandbox/task-cleanup.js +217 -0
- package/dist/lib/sandbox/workspace-identity.js +17 -1
- package/dist/lib/sandbox/workspace-view.js +13 -14
- package/dist/lib/task/activity-intent.js +2 -1
- package/dist/lib/task/activity-log.js +30 -24
- package/dist/lib/task/artifact-command.js +79 -0
- package/dist/lib/task/artifact-lifecycle.js +30 -28
- package/dist/lib/task/artifact-name.js +36 -0
- package/dist/lib/task/artifact-operations.js +29 -289
- package/dist/lib/task/artifact-receipts.js +3 -15
- package/dist/lib/task/artifact-recovery.js +430 -0
- package/dist/lib/task/artifact-repair-intent.js +134 -29
- package/dist/lib/task/artifact-schema.js +6 -14
- package/dist/lib/task/capabilities.js +12 -19
- package/dist/lib/task/codex-orchestration.js +71 -25
- package/dist/lib/task/commit-identity.js +28 -0
- package/dist/lib/task/commit-operation.js +33 -20
- package/dist/lib/task/control-authority.js +403 -6
- package/dist/lib/task/control-recovery.js +140 -0
- package/dist/lib/task/create-service.js +1 -8
- package/dist/lib/task/create.js +62 -9
- package/dist/lib/task/decision-details.js +2 -46
- package/dist/lib/task/delegation-receipts.js +64 -3
- package/dist/lib/task/events.js +275 -22
- package/dist/lib/task/finalization-state.js +9 -0
- package/dist/lib/task/human-override.js +8 -14
- package/dist/lib/task/implementation-inputs.js +3 -3
- package/dist/lib/task/intermediate-cleanup.js +441 -0
- package/dist/lib/task/invalidation.js +18 -65
- package/dist/lib/task/ledger-intents.js +7 -22
- package/dist/lib/task/ledger.js +1 -3
- package/dist/lib/task/lifecycle-recovery.js +549 -0
- package/dist/lib/task/lifecycle.js +31 -4
- package/dist/lib/task/local-artifact-finalization.js +197 -197
- package/dist/lib/task/manual-validation-completion.js +26 -0
- package/dist/lib/task/manual-validation-evidence.js +130 -0
- package/dist/lib/task/manual-validation-receipt.js +105 -0
- package/dist/lib/task/manual-validation-shared.js +40 -0
- package/dist/lib/task/manual-validation-transaction.js +243 -0
- package/dist/lib/task/markdown.js +47 -0
- package/dist/lib/task/orchestration.js +66 -19
- package/dist/lib/task/pr-delivery-fact.js +12 -56
- package/dist/lib/task/qualification-audit.js +20 -34
- package/dist/lib/task/recovery-warning.js +19 -0
- package/dist/lib/task/review-artifacts.js +2 -18
- package/dist/lib/task/review-command.js +26 -0
- package/dist/lib/task/review-finalization.js +175 -216
- package/dist/lib/task/review-fingerprint.js +2 -2
- package/dist/lib/task/sections.js +34 -56
- package/dist/lib/task/short-id.js +15 -7
- package/dist/lib/task/task-execution-lock.js +1 -1
- package/dist/lib/task/verification-engine.js +119 -337
- package/dist/lib/task/verification.js +1 -1
- package/dist/lib/task/workflow-command.js +16 -0
- package/dist/lib/task/workflow-warning-intents.js +0 -16
- package/dist/lib/task/workflow-warnings.js +28 -2
- package/dist/lib/update.js +2 -0
- package/dist/lib/version.js +1 -11
- package/dist/lifecycle-build-manifest.json +3 -3
- package/lib/agent-clients/adapters/codex-lifecycle/capability-store.ts +223 -33
- package/lib/agent-clients/adapters/codex-lifecycle/sandbox-controller.ts +10 -4
- package/lib/agent-clients/adapters/codex-lifecycle/store.ts +55 -3
- package/lib/fs/durable-write.ts +30 -0
- package/lib/fs/file-lock.ts +113 -0
- package/lib/host-control/audit.ts +22 -0
- package/lib/host-control/client.ts +172 -0
- package/lib/host-control/command.ts +60 -0
- package/lib/host-control/path.ts +167 -0
- package/lib/host-control/secure-fs.ts +135 -0
- package/lib/host-control/server.ts +180 -0
- package/lib/host-control/service.ts +133 -0
- package/lib/init.ts +15 -2
- package/lib/internal/cli-route-inventory.ts +4 -2
- package/lib/internal/codex-lifecycle.ts +6 -6
- package/lib/internal/demo-promotion.ts +354 -0
- package/lib/internal/demo-transcript.ts +419 -0
- package/lib/internal/host-control.ts +28 -0
- package/lib/internal/manual-validation.ts +315 -0
- package/lib/internal/platform-pr.ts +15 -4
- package/lib/internal/release-workflow.ts +74 -82
- package/lib/internal/sandbox-control.ts +162 -1
- package/lib/internal/task-artifact.ts +14 -217
- package/lib/internal/task-create.ts +5 -5
- package/lib/internal/task-event.ts +20 -11
- package/lib/internal/task-lifecycle.ts +4 -3
- package/lib/internal/task-operation-registry.ts +111 -4
- package/lib/internal/task-review.ts +9 -54
- package/lib/internal/task-validate.ts +26 -10
- package/lib/owned-path.ts +26 -0
- package/lib/platform/check-status.ts +9 -0
- package/lib/platform/comment-safety.ts +5 -0
- package/lib/platform/completion-backfill.ts +1 -1
- package/lib/platform/github-data.ts +322 -0
- package/lib/platform/github-provider.ts +15 -20
- package/lib/platform/issue-comments.ts +21 -14
- package/lib/platform/issues.ts +5 -246
- package/lib/platform/pr-change-report.ts +7 -5
- package/lib/platform/pr-checks.ts +13 -77
- package/lib/platform/pr-summary.ts +123 -35
- package/lib/platform/pull-requests.ts +6 -173
- package/lib/platform/snapshots.ts +53 -0
- package/lib/platform/task-identities.ts +3 -14
- package/lib/platform/verification-sync.ts +150 -156
- package/lib/pr-review/evidence-grading.ts +4 -9
- package/lib/release/workflow.ts +3 -3
- package/lib/sandbox/commands/create.ts +7 -6
- package/lib/sandbox/commands/rm.ts +21 -1895
- package/lib/sandbox/control/audit.ts +253 -0
- package/lib/sandbox/control/client.ts +109 -66
- package/lib/sandbox/control/executor.ts +134 -74
- package/lib/sandbox/control/finalization-response.ts +29 -0
- package/lib/sandbox/control/identity-sentinel.ts +137 -0
- package/lib/sandbox/control/lifecycle.ts +45 -3
- package/lib/sandbox/control/native-file-lock.ts +6 -107
- package/lib/sandbox/control/protocol.ts +80 -6
- package/lib/sandbox/control/server.ts +567 -132
- package/lib/sandbox/control/state.ts +86 -0
- package/lib/sandbox/control/task-workflow.ts +95 -0
- package/lib/sandbox/control/workflow-executor.ts +92 -0
- package/lib/sandbox/index.ts +1 -2
- package/lib/sandbox/recovery.ts +28 -5
- package/lib/sandbox/removal.ts +1142 -0
- package/lib/sandbox/task-cleanup.ts +209 -0
- package/lib/sandbox/workspace-identity.ts +19 -3
- package/lib/sandbox/workspace-view.ts +17 -15
- package/lib/task/activity-intent.ts +2 -2
- package/lib/task/activity-log.ts +27 -19
- package/lib/task/artifact-command.ts +85 -0
- package/lib/task/artifact-lifecycle.ts +31 -26
- package/lib/task/artifact-name.ts +55 -0
- package/lib/task/artifact-operations.ts +34 -310
- package/lib/task/artifact-receipts.ts +3 -14
- package/lib/task/artifact-recovery.ts +519 -0
- package/lib/task/artifact-repair-intent.ts +162 -33
- package/lib/task/artifact-schema.ts +5 -34
- package/lib/task/capabilities.ts +13 -22
- package/lib/task/codex-orchestration.ts +85 -24
- package/lib/task/commit-identity.ts +31 -0
- package/lib/task/commit-operation.ts +37 -20
- package/lib/task/control-authority.ts +540 -10
- package/lib/task/control-recovery.ts +186 -0
- package/lib/task/create-service.ts +1 -10
- package/lib/task/create.ts +63 -8
- package/lib/task/decision-details.ts +3 -71
- package/lib/task/delegation-receipts.ts +73 -2
- package/lib/task/events.ts +309 -24
- package/lib/task/finalization-state.ts +11 -0
- package/lib/task/human-override.ts +8 -16
- package/lib/task/implementation-inputs.ts +3 -3
- package/lib/task/intermediate-cleanup.ts +493 -0
- package/lib/task/invalidation.ts +18 -62
- package/lib/task/ledger-intents.ts +7 -24
- package/lib/task/ledger.ts +1 -3
- package/lib/task/lifecycle-recovery.ts +691 -0
- package/lib/task/lifecycle.ts +30 -5
- package/lib/task/local-artifact-finalization.ts +244 -234
- package/lib/task/manual-validation-completion.ts +40 -0
- package/lib/task/manual-validation-evidence.ts +209 -0
- package/lib/task/manual-validation-receipt.ts +156 -0
- package/lib/task/manual-validation-shared.ts +50 -0
- package/lib/task/manual-validation-transaction.ts +304 -0
- package/lib/task/markdown.ts +70 -0
- package/lib/task/orchestration.ts +84 -19
- package/lib/task/pr-delivery-fact.ts +15 -62
- package/lib/task/qualification-audit.ts +22 -33
- package/lib/task/recovery-warning.ts +21 -0
- package/lib/task/review-artifacts.ts +1 -20
- package/lib/task/review-command.ts +24 -0
- package/lib/task/review-finalization.ts +183 -292
- package/lib/task/review-fingerprint.ts +2 -2
- package/lib/task/sections.ts +33 -54
- package/lib/task/short-id.ts +27 -5
- package/lib/task/task-execution-lock.ts +1 -1
- package/lib/task/verification-engine.ts +113 -383
- package/lib/task/verification-types.ts +15 -0
- package/lib/task/verification.ts +1 -1
- package/lib/task/workflow-command.ts +17 -0
- package/lib/task/workflow-warning-intents.ts +0 -13
- package/lib/task/workflow-warnings.ts +21 -2
- package/lib/update.ts +6 -0
- package/lib/version.ts +1 -15
- package/package.json +6 -6
- package/templates/.agents/hooks/lifecycle-delegation.js +6 -6
- package/templates/.agents/rules/create-issue.en.md +1 -1
- package/templates/.agents/rules/create-issue.zh-CN.md +1 -1
- package/templates/.agents/rules/issue-sync.en.md +4 -2
- package/templates/.agents/rules/issue-sync.zh-CN.md +4 -3
- package/templates/.agents/rules/local-artifact-repair.en.md +46 -39
- package/templates/.agents/rules/local-artifact-repair.zh-CN.md +43 -36
- package/templates/.agents/rules/testing-discipline.en.md +2 -0
- package/templates/.agents/rules/testing-discipline.zh-CN.md +2 -0
- package/templates/.agents/scripts/package.json +3 -0
- package/templates/.agents/skills/analyze-task/SKILL.en.md +6 -6
- package/templates/.agents/skills/analyze-task/SKILL.zh-CN.md +6 -6
- package/templates/.agents/skills/analyze-task/config/verify.en.json +1 -1
- package/templates/.agents/skills/analyze-task/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/block-task/SKILL.en.md +2 -2
- package/templates/.agents/skills/block-task/SKILL.zh-CN.md +2 -2
- package/templates/.agents/skills/block-task/config/verify.json +1 -1
- package/templates/.agents/skills/cancel-task/SKILL.en.md +3 -3
- package/templates/.agents/skills/cancel-task/SKILL.zh-CN.md +3 -3
- package/templates/.agents/skills/cancel-task/config/verify.json +1 -1
- package/templates/.agents/skills/code-task/SKILL.en.md +7 -7
- package/templates/.agents/skills/code-task/SKILL.zh-CN.md +7 -7
- package/templates/.agents/skills/code-task/config/verify.en.json +1 -1
- package/templates/.agents/skills/code-task/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/commit/reference/issue-metadata-sync.en.md +1 -1
- package/templates/.agents/skills/commit/reference/issue-metadata-sync.zh-CN.md +1 -1
- package/templates/.agents/skills/complete-manual-validation/SKILL.en.md +33 -21
- package/templates/.agents/skills/complete-manual-validation/SKILL.zh-CN.md +33 -21
- package/templates/.agents/skills/complete-manual-validation/config/verify.en.json +1 -1
- package/templates/.agents/skills/complete-manual-validation/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/complete-manual-validation/reference/report-template.en.md +2 -0
- package/templates/.agents/skills/complete-manual-validation/reference/report-template.zh-CN.md +2 -0
- package/templates/.agents/skills/complete-manual-validation/reference/summary-update.en.md +16 -7
- package/templates/.agents/skills/complete-manual-validation/reference/summary-update.zh-CN.md +16 -7
- package/templates/.agents/skills/complete-task/SKILL.en.md +3 -3
- package/templates/.agents/skills/complete-task/SKILL.zh-CN.md +3 -3
- package/templates/.agents/skills/complete-task/config/verify.en.json +2 -2
- package/templates/.agents/skills/complete-task/config/verify.zh-CN.json +2 -2
- package/templates/.agents/skills/complete-task/reference/external-delivery.en.md +1 -1
- package/templates/.agents/skills/complete-task/reference/external-delivery.zh-CN.md +1 -1
- package/templates/.agents/skills/create-pr/SKILL.en.md +2 -2
- package/templates/.agents/skills/create-pr/SKILL.zh-CN.md +2 -2
- package/templates/.agents/skills/create-pr/config/verify.json +1 -1
- package/templates/.agents/skills/create-pr/reference/pr-body-template.en.md +2 -2
- package/templates/.agents/skills/create-pr/reference/pr-body-template.zh-CN.md +2 -2
- package/templates/.agents/skills/create-task/SKILL.en.md +5 -5
- package/templates/.agents/skills/create-task/SKILL.zh-CN.md +5 -5
- package/templates/.agents/skills/create-task/config/verify.json +1 -1
- package/templates/.agents/skills/import-issue/SKILL.en.md +8 -8
- package/templates/.agents/skills/import-issue/SKILL.zh-CN.md +8 -8
- package/templates/.agents/skills/import-issue/config/verify.json +2 -2
- package/templates/.agents/skills/plan-task/SKILL.en.md +4 -4
- package/templates/.agents/skills/plan-task/SKILL.zh-CN.md +4 -4
- package/templates/.agents/skills/plan-task/config/verify.en.json +1 -1
- package/templates/.agents/skills/plan-task/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/release/SKILL.en.md +7 -3
- package/templates/.agents/skills/release/SKILL.zh-CN.md +7 -3
- package/templates/.agents/skills/restore-task/SKILL.en.md +2 -2
- package/templates/.agents/skills/restore-task/SKILL.zh-CN.md +2 -2
- package/templates/.agents/skills/restore-task/config/verify.json +1 -1
- package/templates/.agents/skills/review-analysis/SKILL.en.md +2 -2
- package/templates/.agents/skills/review-analysis/SKILL.zh-CN.md +2 -2
- package/templates/.agents/skills/review-analysis/config/verify.en.json +1 -1
- package/templates/.agents/skills/review-analysis/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/review-analysis/reference/report-template.en.md +7 -7
- package/templates/.agents/skills/review-analysis/reference/report-template.zh-CN.md +6 -6
- package/templates/.agents/skills/review-code/SKILL.en.md +2 -2
- package/templates/.agents/skills/review-code/SKILL.zh-CN.md +2 -2
- package/templates/.agents/skills/review-code/config/verify.en.json +1 -1
- package/templates/.agents/skills/review-code/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/review-code/reference/report-template.en.md +12 -12
- package/templates/.agents/skills/review-code/reference/report-template.zh-CN.md +12 -12
- package/templates/.agents/skills/review-plan/SKILL.en.md +2 -2
- package/templates/.agents/skills/review-plan/SKILL.zh-CN.md +2 -2
- package/templates/.agents/skills/review-plan/config/verify.en.json +1 -1
- package/templates/.agents/skills/review-plan/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/review-plan/reference/report-template.en.md +7 -7
- package/templates/.agents/skills/review-plan/reference/report-template.zh-CN.md +7 -7
- package/templates/.agents/skills/review-pr/config/verify.en.json +1 -1
- package/templates/.agents/skills/review-pr/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/review-pr/reference/evidence-grading.en.md +3 -3
- package/templates/.agents/skills/review-pr/reference/evidence-grading.zh-CN.md +3 -3
- package/templates/.agents/skills/run-manual-validation/SKILL.en.md +20 -3
- package/templates/.agents/skills/run-manual-validation/SKILL.zh-CN.md +20 -3
- package/templates/.agents/skills/run-manual-validation/config/verify.en.json +1 -1
- package/templates/.agents/skills/run-manual-validation/config/verify.zh-CN.json +1 -1
- package/templates/.agents/skills/run-manual-validation/reference/discovery-and-execution.en.md +4 -1
- package/templates/.agents/skills/run-manual-validation/reference/discovery-and-execution.zh-CN.md +4 -1
- package/templates/.agents/skills/run-manual-validation/reference/report-template.en.md +2 -0
- package/templates/.agents/skills/run-manual-validation/reference/report-template.zh-CN.md +2 -0
- package/templates/.agents/skills/run-task/SKILL.en.md +1 -1
- package/templates/.agents/skills/run-task/SKILL.zh-CN.md +1 -1
- package/templates/.agents/skills/test/SKILL.en.md +17 -6
- package/templates/.agents/skills/test/SKILL.zh-CN.md +17 -6
- package/templates/.agents/templates/task.en.md +1 -1
- package/templates/.agents/templates/task.zh-CN.md +1 -1
- package/templates/.claude/commands/import-issue.en.md +1 -1
- package/templates/.claude/commands/import-issue.zh-CN.md +1 -1
- package/templates/.claude/commands/restore-task.en.md +1 -1
- package/templates/.claude/commands/restore-task.zh-CN.md +1 -1
- package/templates/.claude/commands/run-manual-validation.en.md +1 -1
- package/templates/.claude/commands/run-manual-validation.zh-CN.md +1 -1
- package/dist/lib/platform/adapters.js +0 -56
- package/lib/platform/adapters.ts +0 -197
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
import { createHash } from 'node:crypto';
|
|
2
|
+
import fs from 'node:fs';
|
|
3
|
+
import path from 'node:path';
|
|
4
|
+
import { identityDigest as digestIdentity } from './identity-sentinel.js';
|
|
5
|
+
import { acquireSandboxResourceLock } from './native-file-lock.js';
|
|
6
|
+
import { fsyncDirectory, writeDurableFile } from '../../fs/durable-write.js';
|
|
7
|
+
export const SANDBOX_CONTROL_AUDIT_PHASES = Object.freeze([
|
|
8
|
+
'validated', 'gated', 'reserved', 'prepared', 'accepted-authorized', 'accepted-committed',
|
|
9
|
+
'start-authorized', 'started-committed', 'completed', 'evidence-written',
|
|
10
|
+
'publish-authorized', 'published-committed', 'rejected', 'recovered'
|
|
11
|
+
]);
|
|
12
|
+
const REQUEST_ID = /^[a-f0-9-]{16,64}$/u;
|
|
13
|
+
const SAFE_OPERATION = /^[a-z][a-z0-9.-]{0,96}$/u;
|
|
14
|
+
const AUDIT_MAX_BYTES = 1024 * 1024;
|
|
15
|
+
export function requestAuditFields(manifest, request) {
|
|
16
|
+
return {
|
|
17
|
+
requestId: request.id, requestFamily: request.family, sandboxTaskId: manifest.taskId,
|
|
18
|
+
requestGeneration: request.generation, requestIssuedAt: request.issuedAt, requestExpiresAt: request.expiresAt
|
|
19
|
+
};
|
|
20
|
+
}
|
|
21
|
+
export function resultAuditFields(result) {
|
|
22
|
+
return {
|
|
23
|
+
exitCode: result.exitCode,
|
|
24
|
+
outputBytes: Buffer.byteLength(result.stdout, 'utf8'), errorBytes: Buffer.byteLength(result.stderr, 'utf8'),
|
|
25
|
+
outputDigest: createHash('sha256').update(result.stdout, 'utf8').digest('hex'),
|
|
26
|
+
errorDigest: createHash('sha256').update(result.stderr, 'utf8').digest('hex')
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
function auditRoot(manifest) {
|
|
30
|
+
return path.dirname(path.resolve(manifest.publicStatusDir));
|
|
31
|
+
}
|
|
32
|
+
function auditPath(manifest) {
|
|
33
|
+
return path.join(auditRoot(manifest), 'audit.ndjson');
|
|
34
|
+
}
|
|
35
|
+
function manifestIdentityDigest(manifest) {
|
|
36
|
+
return digestIdentity({
|
|
37
|
+
version: 1,
|
|
38
|
+
mode: manifest.mode,
|
|
39
|
+
taskId: manifest.taskId,
|
|
40
|
+
generation: manifest.generation,
|
|
41
|
+
controlRootId: manifest.controlRootId
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
export function createSandboxControlAuditContext(manifest, params) {
|
|
45
|
+
if (!REQUEST_ID.test(params.requestId))
|
|
46
|
+
throw new Error('SANDBOX_CONTROL_AUDIT_REQUEST_INVALID');
|
|
47
|
+
if (params.operation !== null && params.operation !== undefined && !SAFE_OPERATION.test(params.operation)) {
|
|
48
|
+
throw new Error('SANDBOX_CONTROL_AUDIT_OPERATION_INVALID');
|
|
49
|
+
}
|
|
50
|
+
if (!SANDBOX_CONTROL_AUDIT_PHASES.includes(params.phase))
|
|
51
|
+
throw new Error('SANDBOX_CONTROL_AUDIT_PHASE_INVALID');
|
|
52
|
+
return {
|
|
53
|
+
requestId: params.requestId,
|
|
54
|
+
taskId: manifest.taskId,
|
|
55
|
+
family: params.family,
|
|
56
|
+
operation: params.operation ?? null,
|
|
57
|
+
phase: params.phase,
|
|
58
|
+
outcome: params.outcome,
|
|
59
|
+
generation: manifest.generation,
|
|
60
|
+
identityDigest: manifestIdentityDigest(manifest)
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
function safeFields(fields) {
|
|
64
|
+
const result = {};
|
|
65
|
+
for (const [key, value] of Object.entries(fields)) {
|
|
66
|
+
if (!/^[a-z][a-zA-Z0-9]{0,63}$/u.test(key))
|
|
67
|
+
continue;
|
|
68
|
+
if (/(token|secret|credential|proof|password|path|root|cwd|stdout|stderr|args|command|taskref)/iu.test(key))
|
|
69
|
+
continue;
|
|
70
|
+
if (typeof value === 'string' && value.length > 256)
|
|
71
|
+
continue;
|
|
72
|
+
result[key] = value;
|
|
73
|
+
}
|
|
74
|
+
return result;
|
|
75
|
+
}
|
|
76
|
+
function requestHasTerminalTransition(directory) {
|
|
77
|
+
const transitions = path.join(directory, 'transitions');
|
|
78
|
+
if (!fs.existsSync(transitions))
|
|
79
|
+
return false;
|
|
80
|
+
return ['published-committed', 'recovered'].some((phase) => fs.existsSync(path.join(transitions, `${phase}.json`)));
|
|
81
|
+
}
|
|
82
|
+
function hasActiveRequest(manifest) {
|
|
83
|
+
if (!fs.existsSync(manifest.processingDir))
|
|
84
|
+
return false;
|
|
85
|
+
return fs.readdirSync(manifest.processingDir, { withFileTypes: true })
|
|
86
|
+
.some((entry) => entry.isDirectory() && REQUEST_ID.test(entry.name)
|
|
87
|
+
&& !requestHasTerminalTransition(path.join(manifest.processingDir, entry.name)));
|
|
88
|
+
}
|
|
89
|
+
function rotateAuditUnderLock(manifest, filePath) {
|
|
90
|
+
if (!fs.existsSync(filePath) || fs.statSync(filePath).size < AUDIT_MAX_BYTES)
|
|
91
|
+
return;
|
|
92
|
+
if (hasActiveRequest(manifest))
|
|
93
|
+
return;
|
|
94
|
+
fs.rmSync(`${filePath}.1`, { force: true });
|
|
95
|
+
fs.renameSync(filePath, `${filePath}.1`);
|
|
96
|
+
fsyncDirectory(auditRoot(manifest));
|
|
97
|
+
const descriptor = fs.openSync(filePath, 'a', 0o600);
|
|
98
|
+
try {
|
|
99
|
+
fs.fsyncSync(descriptor);
|
|
100
|
+
}
|
|
101
|
+
finally {
|
|
102
|
+
fs.closeSync(descriptor);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
function appendAuditRecord(manifest, record, critical) {
|
|
106
|
+
const root = auditRoot(manifest);
|
|
107
|
+
fs.mkdirSync(root, { recursive: true, mode: 0o700 });
|
|
108
|
+
const lock = acquireSandboxResourceLock(`sandbox-control-audit:${root}`);
|
|
109
|
+
try {
|
|
110
|
+
const filePath = auditPath(manifest);
|
|
111
|
+
rotateAuditUnderLock(manifest, filePath);
|
|
112
|
+
const descriptor = fs.openSync(filePath, 'a', 0o600);
|
|
113
|
+
try {
|
|
114
|
+
fs.writeSync(descriptor, `${JSON.stringify(record)}\n`, undefined, 'utf8');
|
|
115
|
+
if (critical)
|
|
116
|
+
fs.fsyncSync(descriptor);
|
|
117
|
+
}
|
|
118
|
+
finally {
|
|
119
|
+
fs.closeSync(descriptor);
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
catch (error) {
|
|
123
|
+
if (critical)
|
|
124
|
+
throw new Error(`SANDBOX_CONTROL_AUDIT_UNAVAILABLE: ${error instanceof Error ? error.message : String(error)}`);
|
|
125
|
+
}
|
|
126
|
+
finally {
|
|
127
|
+
lock.release();
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
export function appendCriticalAudit(manifest, context, fields = {}, now = Date.now()) {
|
|
131
|
+
appendAuditRecord(manifest, {
|
|
132
|
+
version: 2,
|
|
133
|
+
at: now,
|
|
134
|
+
event: context.phase,
|
|
135
|
+
...context,
|
|
136
|
+
...safeFields(fields)
|
|
137
|
+
}, true);
|
|
138
|
+
}
|
|
139
|
+
export function appendDiagnosticAudit(manifest, event, fields = {}, now = Date.now()) {
|
|
140
|
+
try {
|
|
141
|
+
appendAuditRecord(manifest, {
|
|
142
|
+
version: 2,
|
|
143
|
+
at: now,
|
|
144
|
+
event,
|
|
145
|
+
generation: manifest.generation,
|
|
146
|
+
identityDigest: manifestIdentityDigest(manifest),
|
|
147
|
+
...safeFields(fields)
|
|
148
|
+
}, false);
|
|
149
|
+
}
|
|
150
|
+
catch {
|
|
151
|
+
// Diagnostics are deliberately best effort.
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
function transitionPath(manifest, requestId, phase) {
|
|
155
|
+
if (!REQUEST_ID.test(requestId))
|
|
156
|
+
throw new Error('SANDBOX_CONTROL_TRANSITION_REQUEST_INVALID');
|
|
157
|
+
return path.join(manifest.processingDir, requestId, 'transitions', `${phase}.json`);
|
|
158
|
+
}
|
|
159
|
+
export function writeSandboxControlTransition(manifest, params) {
|
|
160
|
+
const transition = {
|
|
161
|
+
version: 1,
|
|
162
|
+
requestId: params.requestId,
|
|
163
|
+
generation: manifest.generation,
|
|
164
|
+
phase: params.phase,
|
|
165
|
+
at: params.now ?? Date.now(),
|
|
166
|
+
identityDigest: manifestIdentityDigest(manifest),
|
|
167
|
+
reference: params.reference ?? null
|
|
168
|
+
};
|
|
169
|
+
const target = transitionPath(manifest, params.requestId, params.phase);
|
|
170
|
+
fs.mkdirSync(path.dirname(target), { recursive: true, mode: 0o700 });
|
|
171
|
+
try {
|
|
172
|
+
writeDurableFile(target, `${JSON.stringify(transition)}\n`, { mode: 0o600, replace: false });
|
|
173
|
+
}
|
|
174
|
+
catch (error) {
|
|
175
|
+
if (error.code !== 'EEXIST')
|
|
176
|
+
throw error;
|
|
177
|
+
const existing = readSandboxControlTransition(manifest, params.requestId, params.phase);
|
|
178
|
+
if (JSON.stringify(existing) !== JSON.stringify(transition))
|
|
179
|
+
throw new Error('SANDBOX_CONTROL_TRANSITION_CONFLICT');
|
|
180
|
+
}
|
|
181
|
+
return transition;
|
|
182
|
+
}
|
|
183
|
+
export function readSandboxControlTransition(manifest, requestId, phase) {
|
|
184
|
+
const filePath = transitionPath(manifest, requestId, phase);
|
|
185
|
+
if (!fs.existsSync(filePath))
|
|
186
|
+
throw new Error('SANDBOX_CONTROL_TRANSITION_MISSING');
|
|
187
|
+
let value;
|
|
188
|
+
try {
|
|
189
|
+
value = JSON.parse(fs.readFileSync(filePath, 'utf8'));
|
|
190
|
+
}
|
|
191
|
+
catch {
|
|
192
|
+
throw new Error('SANDBOX_CONTROL_TRANSITION_INVALID');
|
|
193
|
+
}
|
|
194
|
+
const candidate = value;
|
|
195
|
+
if (!candidate || candidate.version !== 1 || candidate.requestId !== requestId
|
|
196
|
+
|| candidate.generation !== manifest.generation || candidate.phase !== phase
|
|
197
|
+
|| !Number.isSafeInteger(candidate.at) || typeof candidate.identityDigest !== 'string'
|
|
198
|
+
|| (candidate.reference !== null && typeof candidate.reference !== 'string')) {
|
|
199
|
+
throw new Error('SANDBOX_CONTROL_TRANSITION_INVALID');
|
|
200
|
+
}
|
|
201
|
+
return candidate;
|
|
202
|
+
}
|
|
203
|
+
//# sourceMappingURL=audit.js.map
|
|
@@ -1,57 +1,14 @@
|
|
|
1
1
|
import fs from 'node:fs';
|
|
2
|
+
import { hasTaskBoundMarker } from '../../internal/task-operation-registry.js';
|
|
2
3
|
import path from 'node:path';
|
|
3
4
|
import { randomUUID } from 'node:crypto';
|
|
4
5
|
import { SANDBOX_CONTROL_ADMISSION_WINDOW_MS, SANDBOX_CONTROL_MAX_BYTES, SANDBOX_CONTROL_STATUS_STALE_MS, isSandboxControlFamily } from './protocol.js';
|
|
5
6
|
import { normalizeAgentToken } from '../../agent-clients/tokens.js';
|
|
6
7
|
import { readSandboxControlPayload, readSandboxControlStatus } from './state.js';
|
|
7
8
|
import { accessSandboxTaskView, taskViewFromStatus } from './task-view.js';
|
|
9
|
+
import { readSandboxControlIdentitySentinel } from './identity-sentinel.js';
|
|
10
|
+
import { configuredShortIdLength, resolveShortIdReadOnly } from '../../task/short-id.js';
|
|
8
11
|
const SANDBOX_CONTROL_RESPONSE_SETTLE_MS = 250;
|
|
9
|
-
export function classifySandboxControlEnvironment(env = process.env) {
|
|
10
|
-
const controlKeys = [
|
|
11
|
-
'AGENT_INFRA_CONTROL_TOKEN',
|
|
12
|
-
'AGENT_INFRA_CONTROL_GENERATION',
|
|
13
|
-
'AGENT_INFRA_CONTROL_DIR',
|
|
14
|
-
'AGENT_INFRA_CONTROL_STATUS_DIR'
|
|
15
|
-
];
|
|
16
|
-
const hasControlMarker = controlKeys.some((key) => Boolean(env[key]));
|
|
17
|
-
const hasTaskIdentity = Boolean(env.AGENT_INFRA_TASK_ID);
|
|
18
|
-
const hasRuntime = Boolean(env.AGENT_INFRA_RUNTIME_DIR);
|
|
19
|
-
const hasExecutorMarker = Boolean(env.AGENT_INFRA_EXECUTOR_MANIFEST);
|
|
20
|
-
const hasControllerBinding = Boolean(env.AGENT_INFRA_CONTROL_CONTROLLER_BINDING);
|
|
21
|
-
const hasAnyMarker = hasControlMarker || hasTaskIdentity || hasRuntime || hasExecutorMarker || hasControllerBinding;
|
|
22
|
-
const hasCompleteControl = controlKeys.every((key) => Boolean(env[key]));
|
|
23
|
-
if (!hasAnyMarker)
|
|
24
|
-
return { kind: 'direct' };
|
|
25
|
-
if (hasExecutorMarker) {
|
|
26
|
-
return {
|
|
27
|
-
kind: 'invalid',
|
|
28
|
-
code: 'TASK_CONTROL_TRANSPORT_INVALID',
|
|
29
|
-
message: 'executor context is only valid for sandbox-control execute'
|
|
30
|
-
};
|
|
31
|
-
}
|
|
32
|
-
if (hasControllerBinding) {
|
|
33
|
-
return {
|
|
34
|
-
kind: 'invalid',
|
|
35
|
-
code: 'TASK_CONTROL_TRANSPORT_INVALID',
|
|
36
|
-
message: 'sandbox client control configuration is incomplete or conflicting'
|
|
37
|
-
};
|
|
38
|
-
}
|
|
39
|
-
if (!hasCompleteControl) {
|
|
40
|
-
return {
|
|
41
|
-
kind: 'invalid',
|
|
42
|
-
code: 'TASK_CONTROL_TRANSPORT_INVALID',
|
|
43
|
-
message: 'sandbox client control configuration is incomplete or conflicting'
|
|
44
|
-
};
|
|
45
|
-
}
|
|
46
|
-
if (hasTaskIdentity !== hasRuntime) {
|
|
47
|
-
return {
|
|
48
|
-
kind: 'invalid',
|
|
49
|
-
code: 'TASK_CONTROL_TRANSPORT_INVALID',
|
|
50
|
-
message: 'sandbox task identity and runtime binding must be provided together'
|
|
51
|
-
};
|
|
52
|
-
}
|
|
53
|
-
return { kind: 'controlled', mode: hasTaskIdentity ? 'task-bound' : 'branch-only' };
|
|
54
|
-
}
|
|
55
12
|
export class SandboxControlClientError extends Error {
|
|
56
13
|
detail;
|
|
57
14
|
accepted;
|
|
@@ -70,12 +27,25 @@ function sleep(milliseconds) {
|
|
|
70
27
|
function clientError(code, message, retryable, accepted = false, requestId = null) {
|
|
71
28
|
throw new SandboxControlClientError({ code, message: `${code}: ${message}`, retryable }, accepted, requestId);
|
|
72
29
|
}
|
|
73
|
-
function hasTaskBoundMarker(env = process.env) {
|
|
74
|
-
return Boolean(env.AGENT_INFRA_TASK_ID)
|
|
75
|
-
&& Boolean(env.AGENT_INFRA_CONTROL_TOKEN || env.AGENT_INFRA_CONTROL_GENERATION
|
|
76
|
-
|| env.AGENT_INFRA_CONTROL_STATUS_DIR || env.AGENT_INFRA_RUNTIME_DIR || env.AGENT_INFRA_CONTROL_DIR);
|
|
77
|
-
}
|
|
78
30
|
function preflight(statusDir, generation, taskViewEffect = null, now = Date.now(), env = process.env) {
|
|
31
|
+
if (fs.existsSync(statusDir)) {
|
|
32
|
+
let identity;
|
|
33
|
+
try {
|
|
34
|
+
identity = readSandboxControlIdentitySentinel(statusDir);
|
|
35
|
+
}
|
|
36
|
+
catch (error) {
|
|
37
|
+
const code = error instanceof Error && error.message.endsWith('MISSING')
|
|
38
|
+
? 'SANDBOX_CONTROL_IDENTITY_MISSING'
|
|
39
|
+
: 'SANDBOX_CONTROL_IDENTITY_MALFORMED';
|
|
40
|
+
clientError(code, 'sandbox control identity is missing or invalid', false);
|
|
41
|
+
}
|
|
42
|
+
if (identity.generation !== generation) {
|
|
43
|
+
clientError('SANDBOX_CONTROL_IDENTITY_GENERATION_MISMATCH', 'sandbox control identity generation does not match the request', false);
|
|
44
|
+
}
|
|
45
|
+
if (env.AGENT_INFRA_CONTROL_ROOT_ID && identity.controlRootId !== env.AGENT_INFRA_CONTROL_ROOT_ID) {
|
|
46
|
+
clientError('SANDBOX_CONTROL_IDENTITY_ROOT_ID_MISMATCH', 'sandbox control identity root does not match the client configuration', false);
|
|
47
|
+
}
|
|
48
|
+
}
|
|
79
49
|
let status;
|
|
80
50
|
try {
|
|
81
51
|
status = readSandboxControlStatus(statusDir);
|
|
@@ -113,6 +83,8 @@ function taskViewEffectForRequest(request) {
|
|
|
113
83
|
return 'progress';
|
|
114
84
|
if (request.family === 'task-orchestration')
|
|
115
85
|
return request.args[1] === 'status' ? 'diagnostic' : 'progress';
|
|
86
|
+
if (request.family === 'task-workflow')
|
|
87
|
+
return request.workflow.operation === 'artifact-inspect' || request.workflow.operation === 'decision-next-id' ? 'diagnostic' : 'progress';
|
|
116
88
|
return null;
|
|
117
89
|
}
|
|
118
90
|
function parseResponse(raw, id, accepted = false) {
|
|
@@ -158,11 +130,59 @@ function cancelPendingRequest(requestPath) {
|
|
|
158
130
|
throw error;
|
|
159
131
|
}
|
|
160
132
|
}
|
|
133
|
+
const CONTROL_TASK_ID_RE = /^TASK-\d{8}-\d{6}$/;
|
|
134
|
+
const CONTROL_SHORT_ID_RE = /^\d+$/;
|
|
135
|
+
// Use the current short-id contract for the first visible active registry.
|
|
136
|
+
export function resolveVisibleActiveShortId(ref) {
|
|
137
|
+
let dir = process.cwd();
|
|
138
|
+
for (let depth = 0; depth < 64; depth += 1) {
|
|
139
|
+
const registryPath = path.join(dir, '.agents', 'workspace', 'active', '.short-ids.json');
|
|
140
|
+
if (fs.existsSync(registryPath)) {
|
|
141
|
+
const resolved = resolveShortIdReadOnly(ref, dir, { shortIdLength: configuredShortIdLength(dir) });
|
|
142
|
+
return resolved.ok ? resolved.taskId : null;
|
|
143
|
+
}
|
|
144
|
+
const parent = path.dirname(dir);
|
|
145
|
+
if (parent === dir)
|
|
146
|
+
break;
|
|
147
|
+
dir = parent;
|
|
148
|
+
}
|
|
149
|
+
return null;
|
|
150
|
+
}
|
|
151
|
+
// A request's leading argument is only a task reference for some families and
|
|
152
|
+
// may be a documented short id. Compare canonical ids so a bound sandbox keeps
|
|
153
|
+
// refusing other tasks without rejecting its own task's short id.
|
|
154
|
+
function canonicalRequestTask(request) {
|
|
155
|
+
const ref = request.family === 'task-workflow'
|
|
156
|
+
? request.workflow.taskId
|
|
157
|
+
: 'args' in request ? request.args[0] ?? null : null;
|
|
158
|
+
if (!ref)
|
|
159
|
+
return { kind: 'none' };
|
|
160
|
+
if (CONTROL_TASK_ID_RE.test(ref))
|
|
161
|
+
return { kind: 'task', taskId: ref };
|
|
162
|
+
if (!CONTROL_SHORT_ID_RE.test(ref))
|
|
163
|
+
return { kind: 'none' };
|
|
164
|
+
const resolved = resolveVisibleActiveShortId(ref);
|
|
165
|
+
return resolved ? { kind: 'task', taskId: resolved } : { kind: 'unresolved' };
|
|
166
|
+
}
|
|
161
167
|
function exchangeSandboxControl(request, params) {
|
|
162
168
|
const channelDir = params.channelDir ?? process.env.AGENT_INFRA_CONTROL_DIR ?? '/run/agent-infra/control';
|
|
163
169
|
const statusDir = params.statusDir ?? process.env.AGENT_INFRA_CONTROL_STATUS_DIR ?? '/run/agent-infra/control-status';
|
|
164
170
|
const taskViewEffect = taskViewEffectForRequest(request);
|
|
165
171
|
preflight(statusDir, request.generation, taskViewEffect);
|
|
172
|
+
const identityPath = path.join(statusDir, 'identity.json');
|
|
173
|
+
if (fs.existsSync(statusDir)) {
|
|
174
|
+
const identity = readSandboxControlIdentitySentinel(statusDir);
|
|
175
|
+
const requestTask = canonicalRequestTask(request);
|
|
176
|
+
if (identity.mode === 'task-bound'
|
|
177
|
+
&& ((process.env.AGENT_INFRA_TASK_ID && process.env.AGENT_INFRA_TASK_ID !== identity.taskId)
|
|
178
|
+
|| requestTask.kind === 'unresolved'
|
|
179
|
+
|| (requestTask.kind === 'task' && requestTask.taskId !== identity.taskId))) {
|
|
180
|
+
clientError('SANDBOX_CONTROL_IDENTITY_TOPOLOGY_MISMATCH', 'request task does not match the sandbox identity', false);
|
|
181
|
+
}
|
|
182
|
+
if (identity.mode === 'branch-only' && (request.family === 'task-finalization' || request.family === 'task-workflow')) {
|
|
183
|
+
clientError('SANDBOX_CONTROL_BRANCH_ONLY', 'branch-only sandboxes cannot finalize tasks', false);
|
|
184
|
+
}
|
|
185
|
+
}
|
|
166
186
|
const encoded = `${JSON.stringify(request)}\n`;
|
|
167
187
|
if (Buffer.byteLength(encoded, 'utf8') > SANDBOX_CONTROL_MAX_BYTES) {
|
|
168
188
|
clientError('SANDBOX_CONTROL_REQUEST_TOO_LARGE', 'request exceeds the control limit', false, false, request.id);
|
|
@@ -306,7 +326,7 @@ function authority(params) {
|
|
|
306
326
|
export function requestSandboxControl(params) {
|
|
307
327
|
if (!isSandboxControlFamily(params.family))
|
|
308
328
|
clientError('SANDBOX_CONTROL_COMMAND_DENIED', `'${params.family}' is not allowed`, false);
|
|
309
|
-
if (params.family === 'task-create' || params.family === 'codex-controller' || params.family === 'task-finalization') {
|
|
329
|
+
if (params.family === 'task-create' || params.family === 'codex-controller' || params.family === 'task-finalization' || params.family === 'task-workflow') {
|
|
310
330
|
clientError('SANDBOX_CONTROL_COMMAND_DENIED', `'${params.family}' requires a typed request`, false);
|
|
311
331
|
}
|
|
312
332
|
const auth = authority(params);
|
|
@@ -325,14 +345,15 @@ export function requestSandboxTaskControl(params) {
|
|
|
325
345
|
const issuedAt = Date.now();
|
|
326
346
|
const request = {
|
|
327
347
|
version: 3,
|
|
328
|
-
id: randomUUID(),
|
|
348
|
+
id: params.authority?.requestId ?? randomUUID(),
|
|
329
349
|
...auth,
|
|
330
350
|
issuedAt,
|
|
331
351
|
expiresAt: issuedAt + SANDBOX_CONTROL_ADMISSION_WINDOW_MS,
|
|
332
352
|
family: params.family,
|
|
333
353
|
args: params.args,
|
|
334
354
|
controllerProcess: null,
|
|
335
|
-
controllerProof: params.controllerProof
|
|
355
|
+
controllerProof: params.authority ? null : params.controllerProof,
|
|
356
|
+
...(params.authority ? { authority: params.authority } : {})
|
|
336
357
|
};
|
|
337
358
|
return exchangeSandboxControl(request, params);
|
|
338
359
|
}
|
|
@@ -357,6 +378,24 @@ export function requestSandboxTaskFinalization(params) {
|
|
|
357
378
|
};
|
|
358
379
|
return exchangeSandboxControl(request, params);
|
|
359
380
|
}
|
|
381
|
+
export function requestSandboxTaskWorkflow(params) {
|
|
382
|
+
const auth = authority(params);
|
|
383
|
+
const issuedAt = Date.now();
|
|
384
|
+
const request = {
|
|
385
|
+
version: 3,
|
|
386
|
+
id: params.workflow.id,
|
|
387
|
+
...auth,
|
|
388
|
+
issuedAt,
|
|
389
|
+
expiresAt: issuedAt + SANDBOX_CONTROL_ADMISSION_WINDOW_MS,
|
|
390
|
+
family: 'task-workflow',
|
|
391
|
+
args: [],
|
|
392
|
+
controllerProcess: null,
|
|
393
|
+
controllerProof: null,
|
|
394
|
+
workflow: params.workflow,
|
|
395
|
+
...(params.authority ? { authority: params.authority } : {})
|
|
396
|
+
};
|
|
397
|
+
return exchangeSandboxControl(request, params);
|
|
398
|
+
}
|
|
360
399
|
function exactKeys(value, keys) {
|
|
361
400
|
return Object.keys(value).sort().join(',') === [...keys].sort().join(',');
|
|
362
401
|
}
|