witnora 0.18.9 → 0.18.11
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/dist/cli.js +1 -1
- package/dist/gateway-service.js +15 -2
- package/dist/gateway.js +217 -24
- package/dist/internal/control-client/collector-gateway.d.ts +1 -1
- package/dist/internal/control-client/collector-gateway.d.ts.map +1 -1
- package/dist/internal/control-client/collector-gateway.js +2 -1
- package/dist/internal/control-client/durable-action-worker.d.ts +6 -0
- package/dist/internal/control-client/durable-action-worker.d.ts.map +1 -1
- package/dist/internal/control-client/durable-action-worker.js +13 -0
- package/dist/onboard.js +33 -8
- package/dist/real-path-activation.js +34 -13
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -255,7 +255,7 @@ else if (command === "gateway") {
|
|
|
255
255
|
throw new Error("Use witnora gateway service install|uninstall.");
|
|
256
256
|
}
|
|
257
257
|
else if (action === "supervise") {
|
|
258
|
-
await superviseManagedCustomerGateway({ repository: readFlag("--repo") ?? process.cwd(), dir: readFlag("--dir"), output: (message) => process.stdout.write(message) });
|
|
258
|
+
await superviseManagedCustomerGateway({ repository: readFlag("--repo") ?? process.cwd(), dir: readFlag("--dir"), configHome: readFlag("--config-home"), output: (message) => process.stdout.write(message) });
|
|
259
259
|
}
|
|
260
260
|
else if (action === "stop") {
|
|
261
261
|
const result = await stopManagedCustomerGateway({ repository: readFlag("--repo") ?? process.cwd(), dir: readFlag("--dir") });
|
package/dist/gateway-service.js
CHANGED
|
@@ -7,6 +7,11 @@ import { promisify } from "node:util";
|
|
|
7
7
|
const execFileAsync = promisify(execFile);
|
|
8
8
|
export async function installGatewayService(input) {
|
|
9
9
|
const plan = createGatewayServicePlan(input);
|
|
10
|
+
// A prior task can still be supervising an older generated Gateway. End it
|
|
11
|
+
// before replacing the definition so onboarding never leaves two owners
|
|
12
|
+
// racing for the same localhost port.
|
|
13
|
+
if (plan.kind === "WINDOWS_TASK")
|
|
14
|
+
await input.run(plan.stop.command, plan.stop.args).catch(() => undefined);
|
|
10
15
|
if (plan.launcher)
|
|
11
16
|
await input.writeDefinition(plan.launcher.path, plan.launcher.definition);
|
|
12
17
|
await input.writeDefinition(plan.definitionPath, plan.definition);
|
|
@@ -52,6 +57,8 @@ export function createGatewayServicePlan(input) {
|
|
|
52
57
|
const suffix = createHash("sha256").update(`${input.repository}\n${input.gatewayDirectory}`).digest("hex").slice(0, 12);
|
|
53
58
|
const id = `witnora-gateway-${suffix}`;
|
|
54
59
|
const superviseArgs = [input.cliEntry, "gateway", "supervise", "--repo", input.repository, "--dir", input.gatewayDirectory];
|
|
60
|
+
if (input.configHome)
|
|
61
|
+
superviseArgs.push("--config-home", input.configHome);
|
|
55
62
|
if (input.platform === "win32")
|
|
56
63
|
return windowsPlan(input, id, superviseArgs);
|
|
57
64
|
if (input.platform === "darwin")
|
|
@@ -92,13 +99,13 @@ function currentPlanInput(options) {
|
|
|
92
99
|
const env = options.env ?? process.env;
|
|
93
100
|
const serviceHome = platform === "win32" ? join(env.LOCALAPPDATA ?? join(homedir(), "AppData", "Local"), "Witnora", "services")
|
|
94
101
|
: platform === "darwin" ? join(homedir(), "Library", "LaunchAgents") : join(homedir(), ".config", "systemd", "user");
|
|
95
|
-
return { platform, repository, gatewayDirectory: resolve(repository, options.gatewayDirectory ?? ".witnora/gateway"), cliEntry: resolve(options.cliEntry), nodeExecutable: options.nodeExecutable ?? process.execPath, serviceHome, userId: platform === "win32" ? `${env.USERDOMAIN ? `${env.USERDOMAIN}\\` : ""}${env.USERNAME ?? userInfo().username}` : userInfo().username };
|
|
102
|
+
return { platform, repository, gatewayDirectory: resolve(repository, options.gatewayDirectory ?? ".witnora/gateway"), cliEntry: resolve(options.cliEntry), nodeExecutable: options.nodeExecutable ?? process.execPath, serviceHome, userId: platform === "win32" ? `${env.USERDOMAIN ? `${env.USERDOMAIN}\\` : ""}${env.USERNAME ?? userInfo().username}` : userInfo().username, configHome: options.configHome ?? env.WITNORA_CONFIG_HOME };
|
|
96
103
|
}
|
|
97
104
|
async function runCommand(command, args) { await execFileAsync(command, args, { windowsHide: true }); }
|
|
98
105
|
function systemdPlan(input, id, args) {
|
|
99
106
|
const unit = `${id}.service`;
|
|
100
107
|
const definitionPath = `${input.serviceHome}/${unit}`;
|
|
101
|
-
const definition = `[Unit]\nDescription=Witnora customer-owned Gateway\nAfter=network-online.target\nWants=network-online.target\n\n[Service]\nType=simple\nWorkingDirectory=${
|
|
108
|
+
const definition = `[Unit]\nDescription=Witnora customer-owned Gateway\nAfter=network-online.target\nWants=network-online.target\n\n[Service]\nType=simple\nWorkingDirectory=${systemdPath(input.repository)}\nExecStart=${[input.nodeExecutable, ...args].map(systemd).join(" ")}\nRestart=always\nRestartSec=5\n\n[Install]\nWantedBy=default.target\n`;
|
|
102
109
|
return { id, kind: "SYSTEMD_USER", definitionPath, definition,
|
|
103
110
|
install: { command: "systemctl", args: ["--user", "enable", "--now", unit] },
|
|
104
111
|
start: { command: "systemctl", args: ["--user", "start", unit] },
|
|
@@ -120,4 +127,10 @@ function launchdPlan(input, id, args) {
|
|
|
120
127
|
function windowsArgument(value) { return `"${value.replaceAll('"', '\\"')}"`; }
|
|
121
128
|
function vbScriptString(value) { return `"${value.replaceAll('"', '""')}"`; }
|
|
122
129
|
function systemd(value) { return `"${value.replaceAll("\\", "\\\\").replaceAll('"', '\\"')}"`; }
|
|
130
|
+
function systemdPath(value) {
|
|
131
|
+
return value
|
|
132
|
+
.replaceAll("\\", "\\\\")
|
|
133
|
+
.replaceAll("%", "%%")
|
|
134
|
+
.replace(/[\s#;]/g, (character) => `\\x${character.charCodeAt(0).toString(16).padStart(2, "0")}`);
|
|
135
|
+
}
|
|
123
136
|
function xml(value) { return value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'"); }
|
package/dist/gateway.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { createHash, createPrivateKey, createPublicKey, randomBytes } from "node:crypto";
|
|
1
|
+
import { createHash, createPrivateKey, createPublicKey, randomBytes, randomUUID } from "node:crypto";
|
|
2
2
|
import { spawn } from "node:child_process";
|
|
3
3
|
import { closeSync, openSync } from "node:fs";
|
|
4
4
|
import { access, chmod, mkdir, readFile, realpath, rename, rm, writeFile } from "node:fs/promises";
|
|
@@ -8,6 +8,7 @@ import { fileURLToPath, pathToFileURL } from "node:url";
|
|
|
8
8
|
import { loadConnection } from "./credentials.js";
|
|
9
9
|
import { authorizeProjectConnection } from "./device-authorization.js";
|
|
10
10
|
import { verifyHostedProbeCredential } from "./runtime-bootstrap.js";
|
|
11
|
+
import { activateRealPathIntegrations } from "./real-path-activation.js";
|
|
11
12
|
import { inspectIsolatedOutcomeProbe, observeInIsolatedOutcomeProbe } from "./probe-process.js";
|
|
12
13
|
import { findAvailableRuntimeSandboxOrigin, LOCAL_SANDBOX_FIXTURE_CONTRACT_SHA256, startRuntimeSandboxFixture, } from "./runtime-sandbox-fixture.js";
|
|
13
14
|
import { generateRuntimeSandboxKit, LOCAL_SANDBOX_ADAPTER_ID, LOCAL_SANDBOX_ADAPTER_VERSION, LOCAL_SANDBOX_PROBE_ID, } from "./runtime-sandbox-kit.js";
|
|
@@ -509,10 +510,6 @@ export async function runCustomerGateway(options) {
|
|
|
509
510
|
throw new Error("The saved Gateway credential does not match gateway.json. Run gateway init again.");
|
|
510
511
|
}
|
|
511
512
|
const dataDirectory = resolve(directory, config.storageDirectory);
|
|
512
|
-
const workflowHarnessConfigPath = join(directory, "workflow-harness.json");
|
|
513
|
-
const workflowHarnessConfig = await exists(workflowHarnessConfigPath)
|
|
514
|
-
? parseManagedWorkflowHarnessConfig(await readFile(workflowHarnessConfigPath, "utf8"))
|
|
515
|
-
: undefined;
|
|
516
513
|
const keyRingPath = join(dataDirectory, "source-keys.json");
|
|
517
514
|
const keyRing = await (await exists(keyRingPath)
|
|
518
515
|
? CustomerSourceKeyRing.open(keyRingPath)
|
|
@@ -534,16 +531,10 @@ export async function runCustomerGateway(options) {
|
|
|
534
531
|
FileActionCheckpointStore: (await durableWorker).FileActionCheckpointStore,
|
|
535
532
|
})
|
|
536
533
|
: undefined;
|
|
537
|
-
const
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
server: config.server,
|
|
542
|
-
apiKey: connection.apiKey,
|
|
543
|
-
config: workflowHarnessConfig,
|
|
544
|
-
managed: await configManagedWorkflowHarnessImport(),
|
|
545
|
-
})
|
|
546
|
-
: undefined;
|
|
534
|
+
const assuranceController = await createContinuousAssuranceController({
|
|
535
|
+
repository: resolve(directory, "..", ".."), directory, projectId: config.projectId, server: config.server,
|
|
536
|
+
apiKey: connection.apiKey, config, sourceSigner: () => keyRing.activeSigner(),
|
|
537
|
+
});
|
|
547
538
|
actionWorker?.start();
|
|
548
539
|
const gateway = await startCustomerOwnedCollectorGateway({
|
|
549
540
|
client: new RemoteCollectorClient({ baseUrl: connection.server, projectId: connection.projectId, apiKey: connection.apiKey }),
|
|
@@ -592,19 +583,17 @@ export async function runCustomerGateway(options) {
|
|
|
592
583
|
fixtureReady: false,
|
|
593
584
|
} } : {}),
|
|
594
585
|
} } : {}),
|
|
595
|
-
|
|
596
|
-
? { assuranceHarness: { status: () => workflowHarness.status() } }
|
|
597
|
-
: {}),
|
|
586
|
+
assuranceHarness: { status: () => assuranceController.status() },
|
|
598
587
|
});
|
|
599
|
-
|
|
588
|
+
assuranceController.start();
|
|
600
589
|
process.stdout.write(`Witnora customer-owned Gateway listening on ${gateway.baseUrl}\n`);
|
|
601
590
|
process.stdout.write(config.runtimeWorker
|
|
602
591
|
? "Runtime worker: READY. Approved exact configured actions execute automatically, then use the separate read-only probe and Hosted signed receipt.\n"
|
|
603
592
|
: "Evidence ceiling: RECORDED. No exact target adapter and separate outcome probe are configured, so runtime writes remain fail-closed.\n");
|
|
604
|
-
if (
|
|
605
|
-
process.stdout.write("Managed Workflow Harness:
|
|
593
|
+
if (await assuranceController.status())
|
|
594
|
+
process.stdout.write("Managed Workflow Harness: ACTIVE. Approved task changes are detected and revalidated automatically.\n");
|
|
606
595
|
for (const signal of ["SIGINT", "SIGTERM"]) {
|
|
607
|
-
process.once(signal, () => void Promise.allSettled([gateway.close(),
|
|
596
|
+
process.once(signal, () => void Promise.allSettled([gateway.close(), assuranceController.close(), ...(sandboxFixture ? [sandboxFixture.close()] : [])]).finally(() => process.exit(0)));
|
|
608
597
|
}
|
|
609
598
|
}
|
|
610
599
|
catch (error) {
|
|
@@ -727,6 +716,210 @@ export async function createConfiguredWorkflowHarness(input) {
|
|
|
727
716
|
tick,
|
|
728
717
|
};
|
|
729
718
|
}
|
|
719
|
+
function configSignedChangeManifestImport() {
|
|
720
|
+
return import(new URL("./vendor/onegent-runtime/signed-change-manifest.js", import.meta.url).href);
|
|
721
|
+
}
|
|
722
|
+
/**
|
|
723
|
+
* Reconciles the existing approved-task, Real Path, Manifest, and Autopilot
|
|
724
|
+
* contracts from inside the already-running Gateway. No new service or durable
|
|
725
|
+
* orchestration state is introduced; local config remains the recoverable cache.
|
|
726
|
+
*/
|
|
727
|
+
export async function createContinuousAssuranceController(input) {
|
|
728
|
+
const request = input.fetch ?? fetch;
|
|
729
|
+
const managed = input.managed ?? await configManagedWorkflowHarnessImport();
|
|
730
|
+
let harness;
|
|
731
|
+
let harnessFingerprint;
|
|
732
|
+
let timer;
|
|
733
|
+
let reconciling = false;
|
|
734
|
+
let closing = false;
|
|
735
|
+
let lastReportedError;
|
|
736
|
+
const replaceHarness = async (config) => {
|
|
737
|
+
const fingerprint = createHash("sha256").update(JSON.stringify(config)).digest("hex");
|
|
738
|
+
if (harness && fingerprint === harnessFingerprint)
|
|
739
|
+
return;
|
|
740
|
+
const next = await createConfiguredWorkflowHarness({
|
|
741
|
+
directory: input.directory,
|
|
742
|
+
projectId: input.projectId,
|
|
743
|
+
server: input.server,
|
|
744
|
+
apiKey: input.apiKey,
|
|
745
|
+
config,
|
|
746
|
+
managed,
|
|
747
|
+
evaluatorKit: input.evaluatorKit,
|
|
748
|
+
fetch: request,
|
|
749
|
+
});
|
|
750
|
+
next.start();
|
|
751
|
+
const previous = harness;
|
|
752
|
+
harness = next;
|
|
753
|
+
harnessFingerprint = fingerprint;
|
|
754
|
+
await previous?.close();
|
|
755
|
+
};
|
|
756
|
+
const workflowHarnessPath = join(input.directory, "workflow-harness.json");
|
|
757
|
+
if (await exists(workflowHarnessPath)) {
|
|
758
|
+
try {
|
|
759
|
+
await replaceHarness(parseManagedWorkflowHarnessConfig(await readFile(workflowHarnessPath, "utf8")));
|
|
760
|
+
}
|
|
761
|
+
catch (error) {
|
|
762
|
+
lastReportedError = message(error);
|
|
763
|
+
process.stderr.write(`Existing Assurance Harness will be repaired in the background: ${lastReportedError}\n`);
|
|
764
|
+
}
|
|
765
|
+
}
|
|
766
|
+
const reconcile = async () => {
|
|
767
|
+
if (closing || reconciling)
|
|
768
|
+
return;
|
|
769
|
+
reconciling = true;
|
|
770
|
+
try {
|
|
771
|
+
const activation = await activateRealPathIntegrations({
|
|
772
|
+
repository: input.repository,
|
|
773
|
+
server: input.server,
|
|
774
|
+
projectId: input.projectId,
|
|
775
|
+
apiKey: input.apiKey,
|
|
776
|
+
fetch: request,
|
|
777
|
+
});
|
|
778
|
+
if (activation.state === "READY_TO_START") {
|
|
779
|
+
const configured = await activateManagedWorkflowHarness({
|
|
780
|
+
repository: input.repository,
|
|
781
|
+
modulePath: activation.modulePath,
|
|
782
|
+
realPathActivations: activation.activations,
|
|
783
|
+
previousGeneratedModuleSha256: activation.previousGeneratedModuleSha256,
|
|
784
|
+
});
|
|
785
|
+
await replaceHarness(configured.config);
|
|
786
|
+
}
|
|
787
|
+
await publishCurrentChangeManifests({ ...input, fetch: request }, harness ? await harness.status() : undefined);
|
|
788
|
+
lastReportedError = undefined;
|
|
789
|
+
}
|
|
790
|
+
catch (error) {
|
|
791
|
+
const current = message(error).slice(0, 500);
|
|
792
|
+
if (current !== lastReportedError)
|
|
793
|
+
process.stderr.write(`Continuous Assurance reconciliation is waiting safely: ${current}\n`);
|
|
794
|
+
lastReportedError = current;
|
|
795
|
+
}
|
|
796
|
+
finally {
|
|
797
|
+
reconciling = false;
|
|
798
|
+
}
|
|
799
|
+
};
|
|
800
|
+
return {
|
|
801
|
+
start() {
|
|
802
|
+
if (timer || closing)
|
|
803
|
+
return;
|
|
804
|
+
void reconcile();
|
|
805
|
+
timer = setInterval(() => void reconcile(), input.intervalMs ?? 15_000);
|
|
806
|
+
timer.unref?.();
|
|
807
|
+
},
|
|
808
|
+
reconcile,
|
|
809
|
+
status: () => harness?.status() ?? Promise.resolve(undefined),
|
|
810
|
+
async close() {
|
|
811
|
+
closing = true;
|
|
812
|
+
if (timer)
|
|
813
|
+
clearInterval(timer);
|
|
814
|
+
timer = undefined;
|
|
815
|
+
await harness?.close();
|
|
816
|
+
harness = undefined;
|
|
817
|
+
},
|
|
818
|
+
};
|
|
819
|
+
}
|
|
820
|
+
async function publishCurrentChangeManifests(input, heartbeat) {
|
|
821
|
+
const base = input.server.replace(/\/$/, "");
|
|
822
|
+
const [activationResponse, manifestResponse] = await Promise.all([
|
|
823
|
+
input.fetch(`${base}/v1/projects/${encodeURIComponent(input.projectId)}/nora/activation-plan`, { headers: { authorization: `Bearer ${input.apiKey}` }, redirect: "error", signal: AbortSignal.timeout(10_000) }),
|
|
824
|
+
input.fetch(`${base}/v1/projects/${encodeURIComponent(input.projectId)}/change-manifests`, { headers: { authorization: `Bearer ${input.apiKey}` }, redirect: "error", signal: AbortSignal.timeout(10_000) }),
|
|
825
|
+
]);
|
|
826
|
+
if (!activationResponse.ok)
|
|
827
|
+
throw new Error(`Assurance activation plan returned HTTP ${activationResponse.status}.`);
|
|
828
|
+
if (!manifestResponse.ok)
|
|
829
|
+
throw new Error(`Signed Change Manifest collection returned HTTP ${manifestResponse.status}.`);
|
|
830
|
+
const activation = await boundedResponseJson(activationResponse, 512 * 1024);
|
|
831
|
+
const collection = await boundedResponseJson(manifestResponse, 512 * 1024);
|
|
832
|
+
const targets = Array.isArray(activation.targets) ? activation.targets.filter(validActivationTarget) : [];
|
|
833
|
+
const manifests = Array.isArray(collection.manifests) ? collection.manifests.filter(validChangeManifestRecord) : [];
|
|
834
|
+
if (!targets.length)
|
|
835
|
+
return;
|
|
836
|
+
const packageDigest = await optionalFileDigest(join(input.repository, "package.json"));
|
|
837
|
+
const discoveryDigest = await optionalFileDigest(join(input.repository, "witnora.discovery.json"));
|
|
838
|
+
const policyRevision = createHash("sha256").update(JSON.stringify({ privacyMode: input.config.privacyMode, coverage: input.config.coverage })).digest("hex");
|
|
839
|
+
const explicitModelDigest = process.env.WITNORA_MODEL_DIGEST?.trim();
|
|
840
|
+
const explicitPromptWorkflowDigest = process.env.WITNORA_PROMPT_WORKFLOW_DIGEST?.trim();
|
|
841
|
+
const runtime = input.config.runtimeWorker;
|
|
842
|
+
const components = {
|
|
843
|
+
...(explicitModelDigest && /^[a-f0-9]{64}$/.test(explicitModelDigest) ? { modelDigest: explicitModelDigest } : {}),
|
|
844
|
+
...(validSha256(explicitPromptWorkflowDigest) ? { promptWorkflowDigest: explicitPromptWorkflowDigest } : packageDigest ? { promptWorkflowDigest: packageDigest } : {}),
|
|
845
|
+
...(discoveryDigest ? { toolManifestDigest: discoveryDigest } : {}),
|
|
846
|
+
policyRevision,
|
|
847
|
+
...(heartbeat ? { evaluatorIdentity: { id: "witnora-managed-evaluator", version: "1", digestSha256: heartbeat.evaluatorContractSha256 } } : {}),
|
|
848
|
+
...(runtime ? { adapterIdentity: { id: runtime.adapterId, version: runtime.adapterVersion, digestSha256: runtime.adapterModuleSha256 } } : {}),
|
|
849
|
+
};
|
|
850
|
+
const signed = input.signedChangeManifest ?? await configSignedChangeManifestImport();
|
|
851
|
+
const unique = new Map();
|
|
852
|
+
const exactBindings = heartbeat?.realPathActivations ?? [];
|
|
853
|
+
for (const target of targets) {
|
|
854
|
+
for (const environment of target.environments) {
|
|
855
|
+
if (!exactBindings.some((binding) => binding.agentId === target.agentId && binding.environment === environment))
|
|
856
|
+
continue;
|
|
857
|
+
unique.set(`${target.agentId}:${environment}`, { agentId: target.agentId, agentVersion: target.currentAgentVersion, environment });
|
|
858
|
+
}
|
|
859
|
+
}
|
|
860
|
+
for (const target of unique.values()) {
|
|
861
|
+
const previous = manifests.find((manifest) => manifest.agentId === target.agentId && manifest.environment === target.environment);
|
|
862
|
+
if (previous && previous.agentVersion === target.agentVersion && sameManifestComponents(previous, components))
|
|
863
|
+
continue;
|
|
864
|
+
const observedAt = new Date().toISOString();
|
|
865
|
+
const payload = {
|
|
866
|
+
schemaVersion: "witnora.signed_change_manifest.v0.1",
|
|
867
|
+
manifestId: `gateway-${randomUUID()}`,
|
|
868
|
+
projectId: input.projectId,
|
|
869
|
+
agentId: target.agentId,
|
|
870
|
+
agentVersion: target.agentVersion,
|
|
871
|
+
environment: target.environment,
|
|
872
|
+
observedAt,
|
|
873
|
+
...components,
|
|
874
|
+
...(previous?.manifestDigestSha256 ? { previousManifestDigest: previous.manifestDigestSha256 } : {}),
|
|
875
|
+
};
|
|
876
|
+
const envelope = signed.createSignedChangeManifestEnvelope(payload, input.sourceSigner());
|
|
877
|
+
await signed.uploadSignedChangeManifest({ baseUrl: base, projectId: input.projectId, apiKey: input.apiKey, envelope, fetch: input.fetch });
|
|
878
|
+
}
|
|
879
|
+
}
|
|
880
|
+
function validActivationTarget(value) {
|
|
881
|
+
if (!value || typeof value !== "object" || Array.isArray(value))
|
|
882
|
+
return false;
|
|
883
|
+
const target = value;
|
|
884
|
+
return typeof target.agentId === "string" && typeof target.currentAgentVersion === "string"
|
|
885
|
+
&& Array.isArray(target.environments) && target.environments.every((environment) => environment === "sandbox" || environment === "staging" || environment === "production");
|
|
886
|
+
}
|
|
887
|
+
function validChangeManifestRecord(value) {
|
|
888
|
+
if (!value || typeof value !== "object" || Array.isArray(value))
|
|
889
|
+
return false;
|
|
890
|
+
const manifest = value;
|
|
891
|
+
return typeof manifest.agentId === "string" && typeof manifest.agentVersion === "string"
|
|
892
|
+
&& (manifest.environment === "sandbox" || manifest.environment === "staging" || manifest.environment === "production")
|
|
893
|
+
&& typeof manifest.manifestDigestSha256 === "string";
|
|
894
|
+
}
|
|
895
|
+
function sameManifestComponents(previous, next) {
|
|
896
|
+
return previous.modelDigest === next.modelDigest && previous.promptWorkflowDigest === next.promptWorkflowDigest
|
|
897
|
+
&& previous.toolManifestDigest === next.toolManifestDigest && previous.policyRevision === next.policyRevision
|
|
898
|
+
&& JSON.stringify(previous.evaluatorIdentity) === JSON.stringify(next.evaluatorIdentity)
|
|
899
|
+
&& JSON.stringify(previous.adapterIdentity) === JSON.stringify(next.adapterIdentity);
|
|
900
|
+
}
|
|
901
|
+
async function optionalFileDigest(path) {
|
|
902
|
+
try {
|
|
903
|
+
return createHash("sha256").update(await readFile(path)).digest("hex");
|
|
904
|
+
}
|
|
905
|
+
catch (error) {
|
|
906
|
+
if (error.code === "ENOENT")
|
|
907
|
+
return undefined;
|
|
908
|
+
throw error;
|
|
909
|
+
}
|
|
910
|
+
}
|
|
911
|
+
function validSha256(value) {
|
|
912
|
+
return Boolean(value && /^[a-f0-9]{64}$/.test(value));
|
|
913
|
+
}
|
|
914
|
+
async function boundedResponseJson(response, maxBytes) {
|
|
915
|
+
const text = await response.text();
|
|
916
|
+
if (Buffer.byteLength(text) > maxBytes)
|
|
917
|
+
throw new Error("Hosted Assurance response exceeded its size limit.");
|
|
918
|
+
const value = JSON.parse(text);
|
|
919
|
+
if (!value || typeof value !== "object" || Array.isArray(value))
|
|
920
|
+
throw new Error("Hosted Assurance response is invalid.");
|
|
921
|
+
return value;
|
|
922
|
+
}
|
|
730
923
|
async function startManagedLocalEvaluator(directory, config, evaluatorKit) {
|
|
731
924
|
const repository = resolve(directory, "..", "..");
|
|
732
925
|
const modulePath = resolve(repository, config.evaluatorModulePath);
|
|
@@ -1111,7 +1304,7 @@ export async function restartManagedCustomerGateway(options = {}) {
|
|
|
1111
1304
|
}
|
|
1112
1305
|
export async function superviseManagedCustomerGateway(options = {}) {
|
|
1113
1306
|
const inspect = options.inspect ?? (() => statusManagedCustomerGateway({ repository: options.repository, dir: options.dir }));
|
|
1114
|
-
const start = options.start ?? (() => startManagedCustomerGateway({ repository: options.repository, dir: options.dir }));
|
|
1307
|
+
const start = options.start ?? (() => startManagedCustomerGateway({ repository: options.repository, dir: options.dir, configHome: options.configHome }));
|
|
1115
1308
|
const sleep = options.sleep ?? wait;
|
|
1116
1309
|
const maxCycles = options.maxCycles ?? Number.POSITIVE_INFINITY;
|
|
1117
1310
|
let recoveries = 0;
|
|
@@ -1425,7 +1618,7 @@ function gatewayClient(config) {
|
|
|
1425
1618
|
const requestHelper = `async function actionRequest(path, init = {}) {\n const headers = new Headers(init.headers);\n headers.set("authorization", \`Bearer \${await token()}\`);\n if (init.body) headers.set("content-type", "application/json");\n const response = await fetch(\`\${baseUrl}\${path}\`, { ...init, headers });\n const result = await response.json().catch(() => ({}));\n if (!response.ok) throw new Error(result.error ?? \`Witnora Gateway returned HTTP \${response.status}.\`);\n return result;\n}\n`;
|
|
1426
1619
|
const actionMethods = ` proposeAction(proposal, idempotencyKey = proposal?.externalId) {\n if (typeof idempotencyKey !== "string" || !idempotencyKey) throw new Error("Witnora action proposal requires an idempotency key or externalId.");\n return actionRequest("/v1/actions", { method: "POST", body: JSON.stringify({ proposal, idempotencyKey }) });\n },\n getAction(actionId) {\n if (!/^[A-Za-z0-9._:-]+$/.test(actionId)) throw new Error("Witnora actionId contains unsupported characters.");\n return actionRequest(\`/v1/actions/\${encodeURIComponent(actionId)}\`);\n },\n issueExecutionGrant(actionId, grant, idempotencyKey = \`grant:\${actionId}\`) {\n if (!/^[A-Za-z0-9._:-]+$/.test(actionId)) throw new Error("Witnora actionId contains unsupported characters.");\n return actionRequest(\`/v1/actions/\${encodeURIComponent(actionId)}/execution-grant\`, { method: "POST", body: JSON.stringify({ grant, idempotencyKey }) });\n },\n`;
|
|
1427
1620
|
const localSandboxMethod = config.runtimeWorker?.adapterId === LOCAL_SANDBOX_ADAPTER_ID && config.runtimeWorker.mandateId && config.runtimeWorker.sandboxPrincipalId
|
|
1428
|
-
? ` async proposeLocalSandboxUpdate({ resourceId, status = "UPDATED", externalId = \`runtime-sandbox-\${crypto.randomUUID()}\`, agentBuildId = "witnora-local-sandbox-task@1.0.0" }) {\n if (!/^[A-Za-z0-9._:-]+$/.test(resourceId)) throw new Error("Local sandbox resourceId contains unsupported characters.");\n const approvedParameters = { resourceId, status };\n const digest = Buffer.from(await crypto.subtle.digest("SHA-256", new TextEncoder().encode(agentBuildId))).toString("hex");\n const proposal = {\n externalId, principal: { id: "${config.runtimeWorker.sandboxPrincipalId}", version: "sandbox-v1" },\n actionType: "UPDATE", targetSystem: "WitnoraLocalSandbox", requestedPermissions: [], sensitive: true, expectedState: approvedParameters,\n mandateId: "${config.runtimeWorker.mandateId}", requireMandate: true,\n executionIntent: { adapterId: "${LOCAL_SANDBOX_ADAPTER_ID}", adapterVersionConstraint: "^${LOCAL_SANDBOX_ADAPTER_VERSION}", allowedOrigins: ["${config.runtimeWorker.sandboxOrigin}"], approvedParameters, outcomePredicate: { type: "state_subset", expected: approvedParameters }, agentBuildId, agentBuildDigest: digest, allowedOperation: "UPDATE", allowedResource: \`mock-state/\${resourceId}\` },\n };\n return this.proposeAction(proposal, externalId);\n },\n`
|
|
1621
|
+
? ` async proposeLocalSandboxUpdate({ resourceId, status = "UPDATED", externalId = \`runtime-sandbox-\${crypto.randomUUID()}\`, agentBuildId = "witnora-local-sandbox-task@1.0.0" }) {\n if (!/^[A-Za-z0-9._:-]+$/.test(resourceId)) throw new Error("Local sandbox resourceId contains unsupported characters.");\n const approvedParameters = { resourceId, status };\n const digest = Buffer.from(await crypto.subtle.digest("SHA-256", new TextEncoder().encode(agentBuildId))).toString("hex");\n const proposal = {\n externalId, agentId: "${config.connectionName}", principal: { id: "${config.runtimeWorker.sandboxPrincipalId}", version: "sandbox-v1" },\n actionType: "UPDATE", targetSystem: "WitnoraLocalSandbox", requestedPermissions: [], sensitive: true, expectedState: approvedParameters,\n mandateId: "${config.runtimeWorker.mandateId}", requireMandate: true,\n executionIntent: { adapterId: "${LOCAL_SANDBOX_ADAPTER_ID}", adapterVersionConstraint: "^${LOCAL_SANDBOX_ADAPTER_VERSION}", allowedOrigins: ["${config.runtimeWorker.sandboxOrigin}"], approvedParameters, outcomePredicate: { type: "state_subset", expected: approvedParameters }, agentBuildId, agentBuildDigest: digest, allowedOperation: "UPDATE", allowedResource: \`mock-state/\${resourceId}\` },\n };\n return this.proposeAction(proposal, externalId);\n },\n`
|
|
1429
1622
|
: "";
|
|
1430
1623
|
const realPathSandboxMethod = config.runtimeWorker?.adapterId === LOCAL_SANDBOX_ADAPTER_ID && config.runtimeWorker.mandateId && config.runtimeWorker.sandboxPrincipalId
|
|
1431
1624
|
? ` async proposeRealPathSandboxSimulation({ integrationId, resourceId, status = "SUBMITTED", externalId = \`real-path-sandbox-\${crypto.randomUUID()}\`, agentBuildId = "witnora-real-path-sandbox@1.0.0" }) {\n if (!/^[A-Za-z0-9._:-]+$/.test(integrationId) || !/^[A-Za-z0-9._:-]+$/.test(resourceId)) throw new Error("Real-path integrationId and resourceId must be identifiers.");\n const harness = JSON.parse(await readFile(new URL("./workflow-harness.json", import.meta.url), "utf8"));\n const matches = Array.isArray(harness.realPathActivations) ? harness.realPathActivations.filter((item) => item?.integrationId === integrationId) : [];\n if (matches.length !== 1) throw new Error("Real-path sandbox simulation requires one exact active Harness integration.");\n const activation = matches[0];\n if (activation.environment !== "sandbox" || !Array.isArray(activation.actionPathIds) || activation.actionPathIds.length !== 1) throw new Error("Real-path sandbox simulation requires one exact sandbox action path.");\n const approvedParameters = { resourceId, status };\n const digest = Buffer.from(await crypto.subtle.digest("SHA-256", new TextEncoder().encode(agentBuildId))).toString("hex");\n const proposal = {\n externalId, agentId: activation.agentId, principal: { id: "${config.runtimeWorker.sandboxPrincipalId}", version: "sandbox-v1" },\n actionType: "UPDATE", targetSystem: "WitnoraLocalSandbox", requestedPermissions: [], sensitive: true, expectedState: approvedParameters,\n businessTaskBinding: { taskContractId: activation.taskContractId, taskContractDigestSha256: activation.taskContractDigestSha256, actionPathId: activation.actionPathIds[0], environment: "sandbox", realPathIntegrationId: activation.integrationId, realPathIntegrationDigestSha256: activation.integrationDigestSha256 },\n mandateId: "${config.runtimeWorker.mandateId}", requireMandate: true,\n executionIntent: { adapterId: "${LOCAL_SANDBOX_ADAPTER_ID}", adapterVersionConstraint: "^${LOCAL_SANDBOX_ADAPTER_VERSION}", allowedOrigins: ["${config.runtimeWorker.sandboxOrigin}"], approvedParameters, outcomePredicate: { type: "state_subset", expected: approvedParameters }, agentBuildId, agentBuildDigest: digest, allowedOperation: "UPDATE", allowedResource: \`mock-state/\${resourceId}\` },\n };\n return this.proposeAction(proposal, externalId);\n },\n`
|
|
@@ -48,7 +48,7 @@ export interface CustomerOwnedCollectorGatewayOptions {
|
|
|
48
48
|
};
|
|
49
49
|
};
|
|
50
50
|
assuranceHarness?: {
|
|
51
|
-
status(): Promise<AssuranceHarnessHeartbeat>;
|
|
51
|
+
status(): Promise<AssuranceHarnessHeartbeat | undefined>;
|
|
52
52
|
};
|
|
53
53
|
runtimeBinding?: RuntimeReadinessBinding;
|
|
54
54
|
onRepairRequested?: (request: {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"collector-gateway.d.ts","sourceRoot":"","sources":["../../../../agentcert-sdk/src/collector-gateway.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"collector-gateway.d.ts","sourceRoot":"","sources":["../../../../agentcert-sdk/src/collector-gateway.ts"],"names":[],"mappings":"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"}
|
|
@@ -76,6 +76,7 @@ export async function startCustomerOwnedCollectorGateway(options) {
|
|
|
76
76
|
return { delivered, reconciled, pending };
|
|
77
77
|
};
|
|
78
78
|
const status = async () => {
|
|
79
|
+
const assuranceHarness = options.assuranceHarness ? await options.assuranceHarness.status() : undefined;
|
|
79
80
|
let pendingRecordCount = 0;
|
|
80
81
|
let lastAckSequence;
|
|
81
82
|
for (const journal of journals.values()) {
|
|
@@ -94,7 +95,7 @@ export async function startCustomerOwnedCollectorGateway(options) {
|
|
|
94
95
|
lastRemoteSuccessAt,
|
|
95
96
|
lastRemoteError,
|
|
96
97
|
...(options.actionWorker ? { actionWorker: await options.actionWorker.status() } : {}),
|
|
97
|
-
...(
|
|
98
|
+
...(assuranceHarness ? { assuranceHarness } : {}),
|
|
98
99
|
...(monitoringControlFor() ? { monitoring: monitoringControlFor() } : {}),
|
|
99
100
|
};
|
|
100
101
|
};
|
|
@@ -28,6 +28,12 @@ export interface DurableWorkerAction {
|
|
|
28
28
|
verificationSuccess?: boolean;
|
|
29
29
|
receiptId?: string;
|
|
30
30
|
receiptSignatureCount?: number;
|
|
31
|
+
supersededByActionId?: string;
|
|
32
|
+
businessTaskBinding?: {
|
|
33
|
+
taskContractId?: string;
|
|
34
|
+
actionPathId?: string;
|
|
35
|
+
[key: string]: unknown;
|
|
36
|
+
};
|
|
31
37
|
assuranceContext?: {
|
|
32
38
|
executionIntent?: {
|
|
33
39
|
adapterId: string;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"durable-action-worker.d.ts","sourceRoot":"","sources":["../../../../agentcert-sdk/src/durable-action-worker.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"durable-action-worker.d.ts","sourceRoot":"","sources":["../../../../agentcert-sdk/src/durable-action-worker.ts"],"names":[],"mappings":"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"}
|
|
@@ -157,6 +157,19 @@ export class DurableApprovedActionWorker {
|
|
|
157
157
|
if (terminal(checkpoint.phase))
|
|
158
158
|
return checkpoint;
|
|
159
159
|
const action = await this.options.hosted.getAction(actionId);
|
|
160
|
+
if (action.supersededByActionId) {
|
|
161
|
+
if (action.status !== "REJECTED" && action.status !== "DENIED") {
|
|
162
|
+
return this.persist(checkpoint, "BLOCKED", { limitation: "Hosted action named a successor before the original request was denied." });
|
|
163
|
+
}
|
|
164
|
+
const successor = await this.options.hosted.getAction(action.supersededByActionId);
|
|
165
|
+
const successorProposal = { ...checkpoint.proposal, externalId: successor.externalId };
|
|
166
|
+
if (!successor.businessTaskBinding?.taskContractId || !successor.businessTaskBinding.actionPathId
|
|
167
|
+
|| !exactActionMatches(successor, successor.id, successorProposal, this.options.config.adapterId, this.options.config.adapterVersion)) {
|
|
168
|
+
return this.persist(checkpoint, "BLOCKED", { limitation: "The replacement action does not match the original local intent and exact confirmed Business Task path." });
|
|
169
|
+
}
|
|
170
|
+
await this.track({ actionId: successor.id, proposal: successorProposal });
|
|
171
|
+
return this.persist(checkpoint, "DENIED", { limitation: `Replaced by exact task-bound action ${successor.id}.` });
|
|
172
|
+
}
|
|
160
173
|
if (!exactActionMatches(action, actionId, checkpoint.proposal, this.options.config.adapterId, this.options.config.adapterVersion)) {
|
|
161
174
|
return this.persist(checkpoint, "BLOCKED", { limitation: "Hosted action no longer matches the exact locally configured action, adapter, or build binding." });
|
|
162
175
|
}
|
package/dist/onboard.js
CHANGED
|
@@ -8,7 +8,7 @@ import { verifyControlPlaneConnection } from "./control-plane.js";
|
|
|
8
8
|
import { inferPrivateCapabilities, runPrivateCapabilityDiscovery } from "./private-discovery.js";
|
|
9
9
|
import { parseAgentTemplate, starterAdapter, starterProfile, starterTripwireConfig } from "./onboarding-templates.js";
|
|
10
10
|
import { writeTryEvidence } from "./try.js";
|
|
11
|
-
import { doctorCustomerGateway, activateManagedWorkflowHarness, ensureCustomerGatewayPortAvailable, initializeCustomerGateway, inspectLocalRuntimeBinding, inspectCustomerGatewayFiles, startManagedCustomerGateway, stopManagedCustomerGateway, upgradeCustomerGatewayRuntime, RuntimeSetupNotReadyError, } from "./gateway.js";
|
|
11
|
+
import { doctorCustomerGateway, activateManagedWorkflowHarness, ensureCustomerGatewayPortAvailable, initializeCustomerGateway, inspectLocalRuntimeBinding, inspectCustomerGatewayFiles, startManagedCustomerGateway, statusManagedCustomerGateway, stopManagedCustomerGateway, upgradeCustomerGatewayRuntime, RuntimeSetupNotReadyError, } from "./gateway.js";
|
|
12
12
|
import { discoverRuntimeReferences, planRuntimeSandboxModules } from "./runtime-sandbox-kit.js";
|
|
13
13
|
import { automaticRuntimeReferencesUsable, bootstrapLocalRuntime, verifyAutomaticRuntimeProbe } from "./runtime-bootstrap.js";
|
|
14
14
|
import { activateRealPathIntegrations } from "./real-path-activation.js";
|
|
@@ -218,18 +218,29 @@ export async function runOnboard(options) {
|
|
|
218
218
|
throw new Error("The prior managed Gateway process did not stop before Assurance Harness activation.");
|
|
219
219
|
}
|
|
220
220
|
if (!options.gatewayLifecycle) {
|
|
221
|
+
// Stop any detached Gateway left by an earlier CLI before the OS-owned
|
|
222
|
+
// supervisor is installed. The service becomes the single process owner.
|
|
223
|
+
await gatewayLifecycle.stop({ repository: repositoryPath, configHome: options.configHome, fetch: requestFetch }).catch(() => undefined);
|
|
221
224
|
const port = await ensureCustomerGatewayPortAvailable({ repository: repositoryPath });
|
|
222
225
|
if (port.changed)
|
|
223
226
|
output(`Rebound this repository's generated Gateway to available localhost port ${port.port}; another project remains untouched.\n`);
|
|
224
|
-
const installed = await installCurrentGatewayService({ repository: repositoryPath, cliEntry: fileURLToPath(new URL("./cli.js", import.meta.url)) });
|
|
227
|
+
const installed = await installCurrentGatewayService({ repository: repositoryPath, cliEntry: fileURLToPath(new URL("./cli.js", import.meta.url)), configHome: options.configHome });
|
|
225
228
|
continuousService = { state: "INSTALLED", kind: installed.plan.kind, id: installed.plan.id };
|
|
229
|
+
managedGateway = await waitForInstalledGatewayService({
|
|
230
|
+
repository: repositoryPath,
|
|
231
|
+
fetch: requestFetch,
|
|
232
|
+
sleep: options.sleep,
|
|
233
|
+
timeoutMs: options.timeoutMs,
|
|
234
|
+
});
|
|
235
|
+
}
|
|
236
|
+
else {
|
|
237
|
+
managedGateway = await gatewayLifecycle.start({
|
|
238
|
+
repository: repositoryPath,
|
|
239
|
+
configHome: options.configHome,
|
|
240
|
+
fetch: requestFetch,
|
|
241
|
+
output,
|
|
242
|
+
});
|
|
226
243
|
}
|
|
227
|
-
managedGateway = await gatewayLifecycle.start({
|
|
228
|
-
repository: repositoryPath,
|
|
229
|
-
configHome: options.configHome,
|
|
230
|
-
fetch: requestFetch,
|
|
231
|
-
output,
|
|
232
|
-
});
|
|
233
244
|
if (!managedGateway.healthy)
|
|
234
245
|
throw new Error(managedGateway.detail);
|
|
235
246
|
const doctor = await doctorCustomerGateway({ repository: repositoryPath, configHome: options.configHome, fetch: requestFetch });
|
|
@@ -280,6 +291,20 @@ export async function runOnboard(options) {
|
|
|
280
291
|
throw new Error(`Witnora Setup Autopilot rolled back this install attempt: ${diagnosis}`);
|
|
281
292
|
}
|
|
282
293
|
}
|
|
294
|
+
async function waitForInstalledGatewayService(options) {
|
|
295
|
+
const pause = options.sleep ?? ((milliseconds) => new Promise((resolve) => setTimeout(resolve, milliseconds)));
|
|
296
|
+
const deadline = Date.now() + (options.timeoutMs ?? 12_000);
|
|
297
|
+
let last = await statusManagedCustomerGateway({ repository: options.repository, fetch: options.fetch });
|
|
298
|
+
while (Date.now() < deadline) {
|
|
299
|
+
if (last.state === "RUNNING_MANAGED" && last.healthy)
|
|
300
|
+
return { ...last, started: true };
|
|
301
|
+
if (last.state === "CONFLICT")
|
|
302
|
+
throw new Error(last.detail);
|
|
303
|
+
await pause(120);
|
|
304
|
+
last = await statusManagedCustomerGateway({ repository: options.repository, fetch: options.fetch });
|
|
305
|
+
}
|
|
306
|
+
throw new Error(`The operating-system-managed Gateway did not become healthy before the startup deadline. ${last.detail}`);
|
|
307
|
+
}
|
|
283
308
|
function configuredGatewayPorts(environment) {
|
|
284
309
|
const value = environment.WITNORA_GATEWAY_PORT?.trim();
|
|
285
310
|
if (!value)
|
|
@@ -11,11 +11,25 @@ export async function activateRealPathIntegrations(options) {
|
|
|
11
11
|
if (!response.ok)
|
|
12
12
|
throw new Error(`Could not load approved real-path integrations (${response.status}).`);
|
|
13
13
|
const body = await boundedJson(response);
|
|
14
|
-
const approved = Array.isArray(body.integrations) ? body.integrations.map(parsePlan).filter((plan) => plan.status === "READY_TO_ACTIVATE") : [];
|
|
14
|
+
const approved = Array.isArray(body.integrations) ? body.integrations.map(parsePlan).filter((plan) => plan.status === "READY_TO_ACTIVATE" || plan.status === "HARNESS_ACTIVE") : [];
|
|
15
15
|
const plans = approved.filter((plan) => ["STRIPE_REFUND", "SHOPIFY_DISPUTE", "ZENDESK_TICKET", "SALESFORCE_RECORD", "HUBSPOT_CRM_RECORD", "POSTGRES_RECORD"].includes(plan.generated.providerPackId) && plan.environment === "sandbox" && plan.customerSummary.evaluationMode === "SHADOW");
|
|
16
16
|
if (!plans.length)
|
|
17
17
|
return { state: "NOT_CONFIGURED", created: false, activations: [], generatedFiles: [], rollback: async () => undefined };
|
|
18
18
|
const environment = options.env ?? process.env;
|
|
19
|
+
const modulePath = join(repository, "witnora.assurance-harness.mjs");
|
|
20
|
+
const manifestPath = join(repository, ".witnora", "gateway", "real-path-activations.json");
|
|
21
|
+
const source = generatedProviderHarness(plans);
|
|
22
|
+
const moduleDigestSha256 = sha(source);
|
|
23
|
+
const current = await readFile(modulePath, "utf8").catch((error) => error.code === "ENOENT" ? undefined : Promise.reject(error));
|
|
24
|
+
const priorSource = await readFile(manifestPath, "utf8").catch((error) => error.code === "ENOENT" ? undefined : Promise.reject(error));
|
|
25
|
+
const prior = priorSource === undefined ? undefined : JSON.parse(priorSource);
|
|
26
|
+
const cachedActivations = prior?.projectId === options.projectId && prior.moduleDigestSha256 === moduleDigestSha256 && current === source
|
|
27
|
+
&& Array.isArray(prior.activations) && sameActivationPlans(plans, prior.activations) ? structuredClone(prior.activations) : undefined;
|
|
28
|
+
if (cachedActivations) {
|
|
29
|
+
for (const plan of plans)
|
|
30
|
+
await persistProviderCredential(repository, plan, environment);
|
|
31
|
+
return { state: "READY_TO_START", created: false, modulePath: "witnora.assurance-harness.mjs", activations: cachedActivations, generatedFiles: [], previousGeneratedModuleSha256: moduleDigestSha256, rollback: async () => undefined };
|
|
32
|
+
}
|
|
19
33
|
const activations = [];
|
|
20
34
|
const scenarios = [];
|
|
21
35
|
for (const plan of plans) {
|
|
@@ -25,15 +39,8 @@ export async function activateRealPathIntegrations(options) {
|
|
|
25
39
|
activations.push({ integrationId: plan.id, integrationDigestSha256: plan.digestSha256, taskContractId: plan.taskContractId, taskContractDigestSha256: plan.taskContractDigestSha256, agentId: plan.subject.agentId, agentVersion: plan.subject.agentVersion, environment: plan.environment, providerPackId: plan.generated.providerPackId, providerContractDigestSha256: plan.generated.providerContractDigestSha256, actionPathIds: plan.generated.actionPathBindings.map((item) => item.actionPathId), acceptance });
|
|
26
40
|
scenarios.push({ plan, value: [preflight.scenario] });
|
|
27
41
|
}
|
|
28
|
-
const modulePath = join(repository, "witnora.assurance-harness.mjs");
|
|
29
|
-
const manifestPath = join(repository, ".witnora", "gateway", "real-path-activations.json");
|
|
30
|
-
const source = generatedProviderHarness(plans);
|
|
31
|
-
const moduleDigestSha256 = sha(source);
|
|
32
42
|
let created = false;
|
|
33
43
|
const generatedFiles = [];
|
|
34
|
-
const current = await readFile(modulePath, "utf8").catch((error) => error.code === "ENOENT" ? undefined : Promise.reject(error));
|
|
35
|
-
const priorSource = await readFile(manifestPath, "utf8").catch((error) => error.code === "ENOENT" ? undefined : Promise.reject(error));
|
|
36
|
-
const prior = priorSource === undefined ? undefined : JSON.parse(priorSource);
|
|
37
44
|
const previousGeneratedModuleSha256 = current !== undefined && sha(current) === prior?.moduleDigestSha256 ? prior.moduleDigestSha256 : undefined;
|
|
38
45
|
if (current === undefined) {
|
|
39
46
|
await writeFile(modulePath, source, { encoding: "utf8", mode: 0o600, flag: "wx" });
|
|
@@ -253,16 +260,30 @@ async function persistProviderCredential(repository, plan, environment) {
|
|
|
253
260
|
return;
|
|
254
261
|
const name = providerCredentialEnvironmentName(plan.generated.providerPackId);
|
|
255
262
|
const value = environment[name];
|
|
256
|
-
if (!value)
|
|
257
|
-
throw new Error(`${plan.generated.providerPackId} activation requires its read-only credential in the customer environment.`);
|
|
258
263
|
const directory = join(repository, ".witnora", "provider-credentials");
|
|
259
264
|
const target = join(directory, `${plan.id}.secret`);
|
|
260
|
-
const
|
|
265
|
+
const current = await readFile(target, "utf8").catch((error) => error.code === "ENOENT" ? undefined : Promise.reject(error));
|
|
266
|
+
if (!value) {
|
|
267
|
+
if (current !== undefined)
|
|
268
|
+
return;
|
|
269
|
+
throw new Error(`${plan.generated.providerPackId} activation requires its read-only credential in the customer environment.`);
|
|
270
|
+
}
|
|
271
|
+
if (current === value)
|
|
272
|
+
return;
|
|
261
273
|
await mkdir(directory, { recursive: true });
|
|
262
274
|
await writeFile(join(directory, ".gitignore"), "*\n!.gitignore\n", { encoding: "utf8", mode: 0o600, flag: "wx" }).catch((error) => { if (error.code !== "EEXIST")
|
|
263
275
|
throw error; });
|
|
264
|
-
await writeFile(
|
|
265
|
-
|
|
276
|
+
await writeFile(target, value, { encoding: "utf8", mode: 0o600 });
|
|
277
|
+
}
|
|
278
|
+
function sameActivationPlans(plans, activations) {
|
|
279
|
+
if (plans.length !== activations.length)
|
|
280
|
+
return false;
|
|
281
|
+
return plans.every((plan) => activations.some((activation) => activation.integrationId === plan.id && activation.integrationDigestSha256 === plan.digestSha256
|
|
282
|
+
&& activation.taskContractId === plan.taskContractId && activation.taskContractDigestSha256 === plan.taskContractDigestSha256
|
|
283
|
+
&& activation.agentId === plan.subject.agentId && activation.agentVersion === plan.subject.agentVersion && activation.environment === plan.environment
|
|
284
|
+
&& activation.providerPackId === plan.generated.providerPackId && activation.providerContractDigestSha256 === plan.generated.providerContractDigestSha256
|
|
285
|
+
&& canonical([...activation.actionPathIds].sort()) === canonical(plan.generated.actionPathBindings.map((item) => item.actionPathId).sort())
|
|
286
|
+
&& activation.acceptance?.kind === "READ_ONLY_PROVIDER_PREFLIGHT" && activation.acceptance.productionWrites === 0 && digest(activation.acceptance.observationDigestSha256)));
|
|
266
287
|
}
|
|
267
288
|
function providerCredentialEnvironmentName(packId) {
|
|
268
289
|
if (packId === "STRIPE_REFUND")
|