@the-open-engine/zeroshot 6.28.0 → 6.29.1
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 +3 -3
- package/cli/index.js +20 -224
- package/docker/zeroshot-cluster/Dockerfile +2 -3
- package/lib/cluster/client.cjs +30 -7
- package/lib/cluster/client.d.cts +52 -0
- package/lib/cluster/client.d.mts +52 -0
- package/lib/cluster/client.d.ts +4 -6
- package/lib/cluster/client.mjs +32 -9
- package/lib/cluster/connection-state.cjs +25 -0
- package/lib/cluster/connection-state.d.cts +13 -0
- package/lib/cluster/connection-state.d.mts +13 -0
- package/lib/cluster/connection-state.d.ts +13 -0
- package/lib/cluster/connection-state.mjs +21 -0
- package/lib/cluster/connection-types.cjs +2 -0
- package/lib/cluster/connection-types.d.cts +33 -0
- package/lib/cluster/connection-types.d.mts +33 -0
- package/lib/cluster/connection-types.d.ts +33 -0
- package/lib/cluster/connection-types.mjs +1 -0
- package/lib/cluster/connection.cjs +18 -46
- package/lib/cluster/connection.d.cts +26 -0
- package/lib/cluster/connection.d.mts +26 -0
- package/lib/cluster/connection.d.ts +7 -25
- package/lib/cluster/connection.mjs +12 -42
- package/lib/cluster/errors.cjs +9 -1
- package/lib/cluster/errors.d.cts +29 -0
- package/lib/cluster/errors.d.mts +29 -0
- package/lib/cluster/errors.d.ts +4 -0
- package/lib/cluster/errors.mjs +7 -0
- package/lib/cluster/frames.d.cts +12 -0
- package/lib/cluster/frames.d.mts +12 -0
- package/lib/cluster/generated/protocol-schema.d.cts +1 -0
- package/lib/cluster/generated/protocol-schema.d.mts +1 -0
- package/lib/cluster/generated/protocol.d.cts +781 -0
- package/lib/cluster/generated/protocol.d.mts +781 -0
- package/lib/cluster/index.cjs +2 -2
- package/lib/cluster/index.d.cts +13 -0
- package/lib/cluster/index.d.mts +13 -0
- package/lib/cluster/index.d.ts +3 -3
- package/lib/cluster/index.mjs +2 -2
- package/lib/cluster/json-source.cjs +1 -0
- package/lib/cluster/json-source.d.cts +5 -0
- package/lib/cluster/json-source.d.mts +5 -0
- package/lib/cluster/json-source.d.ts +1 -0
- package/lib/cluster/json-source.mjs +1 -0
- package/lib/cluster/payload-value.cjs +1 -0
- package/lib/cluster/payload-value.d.cts +8 -0
- package/lib/cluster/payload-value.d.mts +8 -0
- package/lib/cluster/payload-value.d.ts +1 -0
- package/lib/cluster/payload-value.mjs +1 -0
- package/lib/cluster/queue.d.cts +15 -0
- package/lib/cluster/queue.d.mts +15 -0
- package/lib/cluster/socket.cjs +8 -0
- package/lib/cluster/socket.d.cts +13 -0
- package/lib/cluster/socket.d.mts +13 -0
- package/lib/cluster/socket.d.ts +2 -0
- package/lib/cluster/socket.mjs +7 -0
- package/lib/cluster/subscriptions.d.cts +73 -0
- package/lib/cluster/subscriptions.d.mts +73 -0
- package/lib/cluster/subscriptions.d.ts +5 -1
- package/lib/cluster/validators.cjs +1 -0
- package/lib/cluster/validators.d.cts +7 -0
- package/lib/cluster/validators.d.mts +7 -0
- package/lib/cluster/validators.d.ts +1 -0
- package/lib/cluster/validators.mjs +1 -0
- package/lib/cluster-worker/engine-adapter.js +1 -11
- package/lib/cluster-worker/engine-input.js +14 -0
- package/lib/hosted-session/authority.cjs +61 -0
- package/lib/hosted-session/authority.d.cts +3 -0
- package/lib/hosted-session/authority.d.mts +3 -0
- package/lib/hosted-session/authority.d.ts +3 -0
- package/lib/hosted-session/authority.mjs +57 -0
- package/lib/hosted-session/coordinator.cjs +78 -51
- package/lib/hosted-session/coordinator.d.cts +11 -0
- package/lib/hosted-session/coordinator.d.mts +11 -0
- package/lib/hosted-session/coordinator.d.ts +4 -2
- package/lib/hosted-session/coordinator.mjs +75 -51
- package/lib/hosted-session/errors.cjs +25 -0
- package/lib/hosted-session/errors.d.cts +10 -0
- package/lib/hosted-session/errors.d.mts +10 -0
- package/lib/hosted-session/errors.d.ts +10 -0
- package/lib/hosted-session/errors.mjs +19 -0
- package/lib/hosted-session/index.cjs +4 -1
- package/lib/hosted-session/index.d.cts +2 -0
- package/lib/hosted-session/index.d.mts +2 -0
- package/lib/hosted-session/index.d.ts +2 -2
- package/lib/hosted-session/index.mjs +1 -1
- package/lib/hosted-session/reconnecting-watch.cjs +131 -0
- package/lib/hosted-session/reconnecting-watch.d.cts +13 -0
- package/lib/hosted-session/reconnecting-watch.d.mts +13 -0
- package/lib/hosted-session/reconnecting-watch.d.ts +13 -0
- package/lib/hosted-session/reconnecting-watch.mjs +127 -0
- package/lib/hosted-session/types.d.cts +32 -0
- package/lib/hosted-session/types.d.mts +32 -0
- package/lib/hosted-session/types.d.ts +19 -7
- package/lib/hosted-target/access-url.cjs +44 -0
- package/lib/hosted-target/access-url.d.cts +2 -0
- package/lib/hosted-target/access-url.d.mts +2 -0
- package/lib/hosted-target/access-url.d.ts +2 -0
- package/lib/hosted-target/access-url.mjs +41 -0
- package/lib/hosted-target/adapter-request.cjs +12 -0
- package/lib/hosted-target/adapter-request.d.cts +17 -0
- package/lib/hosted-target/adapter-request.d.mts +17 -0
- package/lib/hosted-target/adapter-request.d.ts +17 -0
- package/lib/hosted-target/adapter-request.mjs +9 -0
- package/lib/hosted-target/adapter-types.cjs +2 -0
- package/lib/hosted-target/adapter-types.d.cts +27 -0
- package/lib/hosted-target/adapter-types.d.mts +27 -0
- package/lib/hosted-target/adapter-types.d.ts +27 -0
- package/lib/hosted-target/adapter-types.mjs +1 -0
- package/lib/hosted-target/bounds.cjs +10 -0
- package/lib/hosted-target/bounds.d.cts +7 -0
- package/lib/hosted-target/bounds.d.mts +7 -0
- package/lib/hosted-target/bounds.d.ts +7 -0
- package/lib/hosted-target/bounds.mjs +7 -0
- package/lib/hosted-target/capsule-error-response.cjs +76 -0
- package/lib/hosted-target/capsule-error-response.d.cts +2 -0
- package/lib/hosted-target/capsule-error-response.d.mts +2 -0
- package/lib/hosted-target/capsule-error-response.d.ts +2 -0
- package/lib/hosted-target/capsule-error-response.mjs +73 -0
- package/lib/hosted-target/errors.cjs +88 -0
- package/lib/hosted-target/errors.d.cts +36 -0
- package/lib/hosted-target/errors.d.mts +36 -0
- package/lib/hosted-target/errors.d.ts +36 -0
- package/lib/hosted-target/errors.mjs +75 -0
- package/lib/hosted-target/index.cjs +16 -0
- package/lib/hosted-target/index.d.cts +3 -0
- package/lib/hosted-target/index.d.mts +3 -0
- package/lib/hosted-target/index.d.ts +3 -0
- package/lib/hosted-target/index.mjs +2 -0
- package/lib/hosted-target/response-validation.cjs +169 -0
- package/lib/hosted-target/response-validation.d.cts +5 -0
- package/lib/hosted-target/response-validation.d.mts +5 -0
- package/lib/hosted-target/response-validation.d.ts +5 -0
- package/lib/hosted-target/response-validation.mjs +163 -0
- package/lib/hosted-target/retry-executor.cjs +51 -0
- package/lib/hosted-target/retry-executor.d.cts +8 -0
- package/lib/hosted-target/retry-executor.d.mts +8 -0
- package/lib/hosted-target/retry-executor.d.ts +8 -0
- package/lib/hosted-target/retry-executor.mjs +48 -0
- package/lib/hosted-target/retry.cjs +78 -0
- package/lib/hosted-target/retry.d.cts +9 -0
- package/lib/hosted-target/retry.d.mts +9 -0
- package/lib/hosted-target/retry.d.ts +9 -0
- package/lib/hosted-target/retry.mjs +73 -0
- package/lib/hosted-target/target-adapter.cjs +10 -0
- package/lib/hosted-target/target-adapter.d.cts +3 -0
- package/lib/hosted-target/target-adapter.d.mts +3 -0
- package/lib/hosted-target/target-adapter.d.ts +3 -0
- package/lib/hosted-target/target-adapter.mjs +7 -0
- package/lib/hosted-target/types.cjs +4 -0
- package/lib/hosted-target/types.d.cts +50 -0
- package/lib/hosted-target/types.d.mts +50 -0
- package/lib/hosted-target/types.d.ts +50 -0
- package/lib/hosted-target/types.mjs +1 -0
- package/lib/hosted-target/zero-cloud-v1-adapter.cjs +185 -0
- package/lib/hosted-target/zero-cloud-v1-adapter.d.cts +13 -0
- package/lib/hosted-target/zero-cloud-v1-adapter.d.mts +13 -0
- package/lib/hosted-target/zero-cloud-v1-adapter.d.ts +13 -0
- package/lib/hosted-target/zero-cloud-v1-adapter.mjs +181 -0
- package/lib/target/bounded-response.cjs +51 -0
- package/lib/target/bounded-response.d.cts +1 -0
- package/lib/target/bounded-response.d.mts +1 -0
- package/lib/target/bounded-response.d.ts +1 -0
- package/lib/target/bounded-response.js +51 -0
- package/lib/target/bounded-response.mjs +48 -0
- package/lib/target/credential-lock.js +1 -3
- package/lib/target/credential-store.js +9 -4
- package/lib/target/device-flow.cjs +213 -0
- package/lib/target/device-flow.d.cts +54 -0
- package/lib/target/device-flow.d.mts +54 -0
- package/lib/target/device-flow.d.ts +26 -10
- package/lib/target/device-flow.js +162 -53
- package/lib/target/device-flow.mjs +203 -0
- package/lib/target/discovery-errors.cjs +10 -0
- package/lib/target/discovery-errors.d.cts +3 -0
- package/lib/target/discovery-errors.d.mts +3 -0
- package/lib/target/discovery-errors.d.ts +3 -0
- package/lib/target/discovery-errors.js +10 -0
- package/lib/target/discovery-errors.mjs +6 -0
- package/lib/target/discovery-sections.cjs +191 -0
- package/lib/target/discovery-sections.d.cts +52 -0
- package/lib/target/discovery-sections.d.mts +52 -0
- package/lib/target/discovery-sections.d.ts +52 -0
- package/lib/target/discovery-sections.js +191 -0
- package/lib/target/discovery-sections.mjs +179 -0
- package/lib/target/discovery-validation.cjs +109 -0
- package/lib/target/discovery-validation.d.cts +28 -0
- package/lib/target/discovery-validation.d.mts +28 -0
- package/lib/target/discovery-validation.d.ts +28 -0
- package/lib/target/discovery-validation.js +109 -0
- package/lib/target/discovery-validation.mjs +99 -0
- package/lib/target/discovery.cjs +112 -0
- package/lib/target/discovery.d.cts +74 -0
- package/lib/target/discovery.d.mts +74 -0
- package/lib/target/discovery.d.ts +68 -5
- package/lib/target/discovery.js +93 -101
- package/lib/target/discovery.mjs +105 -0
- package/lib/target/index.d.ts +6 -6
- package/lib/target/index.js +36 -36
- package/lib/target/oauth-http.d.ts +2 -0
- package/lib/target/oauth-http.js +25 -0
- package/lib/target/refresh-exchange.d.ts +11 -0
- package/lib/target/refresh-exchange.js +24 -0
- package/lib/target/refresh-revocation.d.ts +8 -0
- package/lib/target/refresh-revocation.js +19 -0
- package/lib/target/route-template.cjs +85 -0
- package/lib/target/route-template.d.cts +7 -0
- package/lib/target/route-template.d.mts +7 -0
- package/lib/target/route-template.d.ts +7 -0
- package/lib/target/route-template.js +85 -0
- package/lib/target/route-template.mjs +81 -0
- package/lib/target/session-errors.d.ts +4 -0
- package/lib/target/session-errors.js +12 -0
- package/lib/target/session-verification.d.ts +10 -0
- package/lib/target/session-verification.js +42 -0
- package/lib/target/target-registry.d.ts +7 -3
- package/lib/target/target-registry.js +41 -10
- package/lib/target/target-session-manager.d.ts +48 -0
- package/lib/target/target-session-manager.js +226 -0
- package/lib/target/target-session.d.ts +39 -31
- package/lib/target/target-session.js +63 -150
- package/lib/target/token-response.cjs +51 -0
- package/lib/target/token-response.d.cts +7 -0
- package/lib/target/token-response.d.mts +7 -0
- package/lib/target/token-response.d.ts +7 -0
- package/lib/target/token-response.js +51 -0
- package/lib/target/token-response.mjs +48 -0
- package/package.json +16 -6
- package/scripts/audit-production-dependencies.js +150 -0
- package/scripts/build-cluster.js +23 -3
- package/scripts/opcore-agent-gate.js +159 -0
- package/scripts/opcore-agent-tool-overlays.js +154 -0
- package/scripts/opcore-introduced-check.js +288 -0
- package/src/cluster/client.ts +42 -15
- package/src/cluster/connection-state.ts +33 -0
- package/src/cluster/connection-types.ts +28 -0
- package/src/cluster/connection.ts +37 -68
- package/src/cluster/errors.ts +5 -0
- package/src/cluster/index.ts +3 -1
- package/src/cluster/json-source.ts +1 -0
- package/src/cluster/payload-value.ts +1 -0
- package/src/cluster/socket.ts +13 -0
- package/src/cluster/subscriptions.ts +7 -2
- package/src/cluster/validators.ts +1 -0
- package/src/cluster/ws.d.ts +1 -1
- package/src/hosted-session/authority.ts +77 -0
- package/src/hosted-session/coordinator.ts +113 -56
- package/src/hosted-session/errors.ts +21 -0
- package/src/hosted-session/index.ts +14 -2
- package/src/hosted-session/reconnecting-watch.ts +148 -0
- package/src/hosted-session/types.ts +22 -8
- package/src/hosted-target/access-url.ts +46 -0
- package/src/hosted-target/adapter-request.ts +28 -0
- package/src/hosted-target/adapter-types.ts +39 -0
- package/src/hosted-target/bounds.ts +1 -0
- package/src/hosted-target/capsule-error-response.ts +107 -0
- package/src/hosted-target/errors.ts +36 -35
- package/src/hosted-target/index.ts +10 -23
- package/src/hosted-target/response-validation.ts +170 -62
- package/src/hosted-target/retry-executor.ts +62 -0
- package/src/hosted-target/retry.ts +47 -11
- package/src/hosted-target/target-adapter.ts +12 -8
- package/src/hosted-target/types.ts +19 -18
- package/src/hosted-target/zero-cloud-v1-adapter.ts +229 -316
- package/src/target/bounded-response.ts +68 -0
- package/src/target/credential-lock.ts +1 -3
- package/src/target/credential-store.ts +14 -10
- package/src/target/device-flow.ts +206 -71
- package/src/target/discovery-errors.ts +6 -0
- package/src/target/discovery-sections.ts +251 -0
- package/src/target/discovery-validation.ts +144 -0
- package/src/target/discovery.ts +163 -115
- package/src/target/index.ts +15 -11
- package/src/target/oauth-http.ts +27 -0
- package/src/target/refresh-exchange.ts +36 -0
- package/src/target/refresh-revocation.ts +29 -0
- package/src/target/route-template.ts +105 -0
- package/src/target/session-errors.ts +9 -0
- package/src/target/session-verification.ts +51 -0
- package/src/target/target-registry.ts +60 -27
- package/src/target/target-session-manager.ts +285 -0
- package/src/target/target-session.ts +105 -222
- package/src/target/token-response.ts +62 -0
|
@@ -1,162 +1,75 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.LoginRequiredError = void 0;
|
|
3
|
+
exports.TargetSessionManager = exports.LoginRequiredError = void 0;
|
|
4
4
|
exports.targetLogin = targetLogin;
|
|
5
5
|
exports.refreshAccessToken = refreshAccessToken;
|
|
6
6
|
exports.getAccessTokenProvider = getAccessTokenProvider;
|
|
7
7
|
exports.revokeAndCleanup = revokeAndCleanup;
|
|
8
|
-
const
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
8
|
+
const target_session_manager_js_1 = require("./target-session-manager.js");
|
|
9
|
+
var target_session_manager_js_2 = require("./target-session-manager.js");
|
|
10
|
+
Object.defineProperty(exports, "LoginRequiredError", { enumerable: true, get: function () { return target_session_manager_js_2.LoginRequiredError; } });
|
|
11
|
+
Object.defineProperty(exports, "TargetSessionManager", { enumerable: true, get: function () { return target_session_manager_js_2.TargetSessionManager; } });
|
|
12
|
+
function transientSettings(targetName, target) {
|
|
13
|
+
const state = {
|
|
14
|
+
_targets: { [targetName]: target },
|
|
15
|
+
};
|
|
16
|
+
return {
|
|
17
|
+
load: () => state,
|
|
18
|
+
mutate: (mutator) => mutator(state),
|
|
19
|
+
};
|
|
18
20
|
}
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
throw new device_flow_ts_1.UnboundSessionError(codeResponse.verification_uri);
|
|
36
|
-
}
|
|
37
|
-
const serviceKey = (0, credential_store_ts_1.targetServiceKey)(target.id);
|
|
38
|
-
const release = await acquireLock();
|
|
39
|
-
try {
|
|
40
|
-
await credentialStore.set(serviceKey, credential_store_ts_1.TARGET_ACCOUNT, tokenResponse.refresh_token);
|
|
41
|
-
}
|
|
42
|
-
finally {
|
|
43
|
-
await release();
|
|
44
|
-
}
|
|
45
|
-
(0, target_registry_ts_1.updateTargetOrganization)(targetName, tokenResponse.organization, settings);
|
|
46
|
-
return { organization: tokenResponse.organization };
|
|
21
|
+
function legacyManager(init) {
|
|
22
|
+
const clock = init.clock ?? init.deps.clock ?? { now: () => Date.now() };
|
|
23
|
+
return new target_session_manager_js_1.TargetSessionManager({
|
|
24
|
+
targetName: init.targetName,
|
|
25
|
+
target: init.target,
|
|
26
|
+
credentialStore: init.credentialStore,
|
|
27
|
+
acquireLock: init.acquireLock,
|
|
28
|
+
settings: init.deps.settings ?? transientSettings(init.targetName, init.target),
|
|
29
|
+
deps: {
|
|
30
|
+
http: init.deps.http,
|
|
31
|
+
clock,
|
|
32
|
+
browserOpener: { open: () => Promise.resolve() },
|
|
33
|
+
stderr: { write: () => undefined },
|
|
34
|
+
discoveryEndpoints: init.deps.discoveryEndpoints,
|
|
35
|
+
},
|
|
36
|
+
});
|
|
47
37
|
}
|
|
48
|
-
|
|
49
|
-
const
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
const body = new URLSearchParams({
|
|
59
|
-
grant_type: 'refresh_token',
|
|
60
|
-
refresh_token: currentRefreshToken,
|
|
61
|
-
client_id: clientId,
|
|
62
|
-
});
|
|
63
|
-
let tokenResponse;
|
|
64
|
-
const response = await http.fetch(tokenEndpoint, {
|
|
65
|
-
method: 'POST',
|
|
66
|
-
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
|
|
67
|
-
body: body.toString(),
|
|
68
|
-
redirect: 'error',
|
|
69
|
-
});
|
|
70
|
-
if (!response.ok) {
|
|
71
|
-
const errorBody = (await response.json().catch(() => ({ error: 'unknown' })));
|
|
72
|
-
if (errorBody.error === 'invalid_grant') {
|
|
73
|
-
await credentialStore.delete(serviceKey, credential_store_ts_1.TARGET_ACCOUNT);
|
|
74
|
-
throw new LoginRequiredError(targetName);
|
|
75
|
-
}
|
|
76
|
-
throw new Error(`Token refresh failed (${response.status}): ${errorBody.error}`);
|
|
77
|
-
}
|
|
78
|
-
tokenResponse = (await response.json());
|
|
79
|
-
try {
|
|
80
|
-
await credentialStore.set(serviceKey, credential_store_ts_1.TARGET_ACCOUNT, tokenResponse.refresh_token);
|
|
81
|
-
}
|
|
82
|
-
catch {
|
|
83
|
-
await bestEffortRevoke(tokenResponse.refresh_token, revocationEndpoint, clientId, http);
|
|
84
|
-
await credentialStore.delete(serviceKey, credential_store_ts_1.TARGET_ACCOUNT);
|
|
85
|
-
throw new LoginRequiredError(targetName);
|
|
86
|
-
}
|
|
87
|
-
return { accessToken: tokenResponse.access_token, expiresIn: tokenResponse.expires_in };
|
|
88
|
-
}
|
|
89
|
-
finally {
|
|
90
|
-
await release();
|
|
91
|
-
}
|
|
38
|
+
function targetLogin(...args) {
|
|
39
|
+
const [targetName, target, credentialStore, acquireLock, settings, deps] = args;
|
|
40
|
+
return new target_session_manager_js_1.TargetSessionManager({
|
|
41
|
+
targetName,
|
|
42
|
+
target,
|
|
43
|
+
credentialStore,
|
|
44
|
+
acquireLock,
|
|
45
|
+
settings,
|
|
46
|
+
deps,
|
|
47
|
+
}).login();
|
|
92
48
|
}
|
|
93
|
-
async function
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
})
|
|
102
|
-
|
|
103
|
-
method: 'POST',
|
|
104
|
-
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
|
|
105
|
-
body: body.toString(),
|
|
106
|
-
redirect: 'error',
|
|
107
|
-
});
|
|
108
|
-
}
|
|
109
|
-
catch {
|
|
110
|
-
// Best-effort
|
|
111
|
-
}
|
|
49
|
+
async function refreshAccessToken(...args) {
|
|
50
|
+
const [targetName, target, credentialStore, acquireLock, deps, clock] = args;
|
|
51
|
+
return legacyManager({
|
|
52
|
+
targetName,
|
|
53
|
+
target,
|
|
54
|
+
credentialStore,
|
|
55
|
+
acquireLock,
|
|
56
|
+
deps,
|
|
57
|
+
...(clock === undefined ? {} : { clock }),
|
|
58
|
+
}).getAccessTokenWithLifetime('capsule');
|
|
112
59
|
}
|
|
113
|
-
function getAccessTokenProvider(
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
expiresAt = clock.now() + result.expiresIn * 1000;
|
|
124
|
-
return result.accessToken;
|
|
125
|
-
},
|
|
126
|
-
};
|
|
60
|
+
function getAccessTokenProvider(...args) {
|
|
61
|
+
const [targetName, target, credentialStore, acquireLock, deps, clock] = args;
|
|
62
|
+
return legacyManager({
|
|
63
|
+
targetName,
|
|
64
|
+
target,
|
|
65
|
+
credentialStore,
|
|
66
|
+
acquireLock,
|
|
67
|
+
deps,
|
|
68
|
+
...(clock === undefined ? {} : { clock }),
|
|
69
|
+
}).tokenProvider('capsule');
|
|
127
70
|
}
|
|
128
|
-
|
|
129
|
-
const
|
|
130
|
-
const
|
|
131
|
-
|
|
132
|
-
const release = await acquireLock();
|
|
133
|
-
try {
|
|
134
|
-
const refreshToken = await credentialStore.get(serviceKey, credential_store_ts_1.TARGET_ACCOUNT);
|
|
135
|
-
if (refreshToken && revocationEndpoint) {
|
|
136
|
-
const body = new URLSearchParams({
|
|
137
|
-
token: refreshToken,
|
|
138
|
-
client_id: clientId,
|
|
139
|
-
token_type_hint: 'refresh_token',
|
|
140
|
-
});
|
|
141
|
-
try {
|
|
142
|
-
const response = await http.fetch(revocationEndpoint, {
|
|
143
|
-
method: 'POST',
|
|
144
|
-
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
|
|
145
|
-
body: body.toString(),
|
|
146
|
-
redirect: 'error',
|
|
147
|
-
});
|
|
148
|
-
if (!response.ok && !force) {
|
|
149
|
-
throw new Error(`Remote revocation failed (${response.status}). Use --force to remove anyway.`);
|
|
150
|
-
}
|
|
151
|
-
}
|
|
152
|
-
catch (err) {
|
|
153
|
-
if (!force)
|
|
154
|
-
throw err;
|
|
155
|
-
}
|
|
156
|
-
}
|
|
157
|
-
await credentialStore.delete(serviceKey, credential_store_ts_1.TARGET_ACCOUNT);
|
|
158
|
-
}
|
|
159
|
-
finally {
|
|
160
|
-
await release();
|
|
161
|
-
}
|
|
71
|
+
function revokeAndCleanup(...args) {
|
|
72
|
+
const [target, credentialStore, acquireLock, deps, force] = args;
|
|
73
|
+
const targetName = deps.targetName ?? target.id;
|
|
74
|
+
return legacyManager({ targetName, target, credentialStore, acquireLock, deps }).revoke(force);
|
|
162
75
|
}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.parseTokenResponse = parseTokenResponse;
|
|
4
|
+
const MAX_TOKEN_BYTES = 16 * 1024;
|
|
5
|
+
const TOKEN_RESPONSE_FIELDS = [
|
|
6
|
+
'access_token',
|
|
7
|
+
'refresh_token',
|
|
8
|
+
'token_type',
|
|
9
|
+
'expires_in',
|
|
10
|
+
'refresh_expires_in',
|
|
11
|
+
'scope',
|
|
12
|
+
];
|
|
13
|
+
function boundedString(value, maxBytes) {
|
|
14
|
+
return typeof value === 'string' && value.length > 0 &&
|
|
15
|
+
new TextEncoder().encode(value).byteLength <= maxBytes;
|
|
16
|
+
}
|
|
17
|
+
function tokenFieldsValid(token) {
|
|
18
|
+
const fields = Object.keys(token);
|
|
19
|
+
return fields.length === TOKEN_RESPONSE_FIELDS.length &&
|
|
20
|
+
fields.every((key) => TOKEN_RESPONSE_FIELDS.includes(key));
|
|
21
|
+
}
|
|
22
|
+
function tokenLifetimesValid(token) {
|
|
23
|
+
return Number.isSafeInteger(token.expires_in) &&
|
|
24
|
+
token.expires_in > 0 &&
|
|
25
|
+
token.expires_in <= 86_400 &&
|
|
26
|
+
Number.isSafeInteger(token.refresh_expires_in) &&
|
|
27
|
+
token.refresh_expires_in > 0 &&
|
|
28
|
+
token.refresh_expires_in <= 31_536_000;
|
|
29
|
+
}
|
|
30
|
+
function tokenStringsValid(token) {
|
|
31
|
+
return boundedString(token.access_token, MAX_TOKEN_BYTES) &&
|
|
32
|
+
boundedString(token.refresh_token, MAX_TOKEN_BYTES) &&
|
|
33
|
+
token.token_type === 'Bearer' &&
|
|
34
|
+
boundedString(token.scope, 512) &&
|
|
35
|
+
!/[\u0000-\u001f\u007f]/.test(token.scope);
|
|
36
|
+
}
|
|
37
|
+
function parseTokenResponse(value) {
|
|
38
|
+
if (value === null || typeof value !== 'object' || Array.isArray(value)) {
|
|
39
|
+
throw new Error('Token response is malformed');
|
|
40
|
+
}
|
|
41
|
+
const token = value;
|
|
42
|
+
if (!tokenFieldsValid(token) || !tokenLifetimesValid(token) || !tokenStringsValid(token)) {
|
|
43
|
+
throw new Error('Token response is malformed');
|
|
44
|
+
}
|
|
45
|
+
return Object.freeze({
|
|
46
|
+
access_token: token.access_token,
|
|
47
|
+
refresh_token: token.refresh_token,
|
|
48
|
+
token_type: 'Bearer',
|
|
49
|
+
expires_in: token.expires_in,
|
|
50
|
+
});
|
|
51
|
+
}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.parseTokenResponse = parseTokenResponse;
|
|
4
|
+
const MAX_TOKEN_BYTES = 16 * 1024;
|
|
5
|
+
const TOKEN_RESPONSE_FIELDS = [
|
|
6
|
+
'access_token',
|
|
7
|
+
'refresh_token',
|
|
8
|
+
'token_type',
|
|
9
|
+
'expires_in',
|
|
10
|
+
'refresh_expires_in',
|
|
11
|
+
'scope',
|
|
12
|
+
];
|
|
13
|
+
function boundedString(value, maxBytes) {
|
|
14
|
+
return typeof value === 'string' && value.length > 0 &&
|
|
15
|
+
new TextEncoder().encode(value).byteLength <= maxBytes;
|
|
16
|
+
}
|
|
17
|
+
function tokenFieldsValid(token) {
|
|
18
|
+
const fields = Object.keys(token);
|
|
19
|
+
return fields.length === TOKEN_RESPONSE_FIELDS.length &&
|
|
20
|
+
fields.every((key) => TOKEN_RESPONSE_FIELDS.includes(key));
|
|
21
|
+
}
|
|
22
|
+
function tokenLifetimesValid(token) {
|
|
23
|
+
return Number.isSafeInteger(token.expires_in) &&
|
|
24
|
+
token.expires_in > 0 &&
|
|
25
|
+
token.expires_in <= 86_400 &&
|
|
26
|
+
Number.isSafeInteger(token.refresh_expires_in) &&
|
|
27
|
+
token.refresh_expires_in > 0 &&
|
|
28
|
+
token.refresh_expires_in <= 31_536_000;
|
|
29
|
+
}
|
|
30
|
+
function tokenStringsValid(token) {
|
|
31
|
+
return boundedString(token.access_token, MAX_TOKEN_BYTES) &&
|
|
32
|
+
boundedString(token.refresh_token, MAX_TOKEN_BYTES) &&
|
|
33
|
+
token.token_type === 'Bearer' &&
|
|
34
|
+
boundedString(token.scope, 512) &&
|
|
35
|
+
!/[\u0000-\u001f\u007f]/.test(token.scope);
|
|
36
|
+
}
|
|
37
|
+
function parseTokenResponse(value) {
|
|
38
|
+
if (value === null || typeof value !== 'object' || Array.isArray(value)) {
|
|
39
|
+
throw new Error('Token response is malformed');
|
|
40
|
+
}
|
|
41
|
+
const token = value;
|
|
42
|
+
if (!tokenFieldsValid(token) || !tokenLifetimesValid(token) || !tokenStringsValid(token)) {
|
|
43
|
+
throw new Error('Token response is malformed');
|
|
44
|
+
}
|
|
45
|
+
return Object.freeze({
|
|
46
|
+
access_token: token.access_token,
|
|
47
|
+
refresh_token: token.refresh_token,
|
|
48
|
+
token_type: 'Bearer',
|
|
49
|
+
expires_in: token.expires_in,
|
|
50
|
+
});
|
|
51
|
+
}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
const MAX_TOKEN_BYTES = 16 * 1024;
|
|
2
|
+
const TOKEN_RESPONSE_FIELDS = [
|
|
3
|
+
'access_token',
|
|
4
|
+
'refresh_token',
|
|
5
|
+
'token_type',
|
|
6
|
+
'expires_in',
|
|
7
|
+
'refresh_expires_in',
|
|
8
|
+
'scope',
|
|
9
|
+
];
|
|
10
|
+
function boundedString(value, maxBytes) {
|
|
11
|
+
return typeof value === 'string' && value.length > 0 &&
|
|
12
|
+
new TextEncoder().encode(value).byteLength <= maxBytes;
|
|
13
|
+
}
|
|
14
|
+
function tokenFieldsValid(token) {
|
|
15
|
+
const fields = Object.keys(token);
|
|
16
|
+
return fields.length === TOKEN_RESPONSE_FIELDS.length &&
|
|
17
|
+
fields.every((key) => TOKEN_RESPONSE_FIELDS.includes(key));
|
|
18
|
+
}
|
|
19
|
+
function tokenLifetimesValid(token) {
|
|
20
|
+
return Number.isSafeInteger(token.expires_in) &&
|
|
21
|
+
token.expires_in > 0 &&
|
|
22
|
+
token.expires_in <= 86_400 &&
|
|
23
|
+
Number.isSafeInteger(token.refresh_expires_in) &&
|
|
24
|
+
token.refresh_expires_in > 0 &&
|
|
25
|
+
token.refresh_expires_in <= 31_536_000;
|
|
26
|
+
}
|
|
27
|
+
function tokenStringsValid(token) {
|
|
28
|
+
return boundedString(token.access_token, MAX_TOKEN_BYTES) &&
|
|
29
|
+
boundedString(token.refresh_token, MAX_TOKEN_BYTES) &&
|
|
30
|
+
token.token_type === 'Bearer' &&
|
|
31
|
+
boundedString(token.scope, 512) &&
|
|
32
|
+
!/[\u0000-\u001f\u007f]/.test(token.scope);
|
|
33
|
+
}
|
|
34
|
+
export function parseTokenResponse(value) {
|
|
35
|
+
if (value === null || typeof value !== 'object' || Array.isArray(value)) {
|
|
36
|
+
throw new Error('Token response is malformed');
|
|
37
|
+
}
|
|
38
|
+
const token = value;
|
|
39
|
+
if (!tokenFieldsValid(token) || !tokenLifetimesValid(token) || !tokenStringsValid(token)) {
|
|
40
|
+
throw new Error('Token response is malformed');
|
|
41
|
+
}
|
|
42
|
+
return Object.freeze({
|
|
43
|
+
access_token: token.access_token,
|
|
44
|
+
refresh_token: token.refresh_token,
|
|
45
|
+
token_type: 'Bearer',
|
|
46
|
+
expires_in: token.expires_in,
|
|
47
|
+
});
|
|
48
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@the-open-engine/zeroshot",
|
|
3
|
-
"version": "6.
|
|
3
|
+
"version": "6.29.1",
|
|
4
4
|
"description": "Multi-agent orchestration engine for Claude, Codex, and Gemini",
|
|
5
5
|
"main": "src/orchestrator.js",
|
|
6
6
|
"bin": {
|
|
@@ -44,22 +44,31 @@
|
|
|
44
44
|
"typecheck:agent-cli-provider": "tsc --project tsconfig.agent-cli-provider.json",
|
|
45
45
|
"typecheck:hosted-target": "tsc --project tsconfig.hosted-target.json",
|
|
46
46
|
"typecheck:hosted-session": "tsc --project tsconfig.hosted-session.json",
|
|
47
|
-
"test:hosted-target": "node --test tests/hosted-target/*.test.ts",
|
|
47
|
+
"test:hosted-target": "npm run build:cluster && node --test tests/hosted-target/*.test.ts",
|
|
48
48
|
"test:target": "npm run build:agent-cli-provider && npm run build:target && node --test tests/target/*.test.ts",
|
|
49
49
|
"typecheck:target": "tsc --project tsconfig.target.json",
|
|
50
50
|
"typecheck:cluster": "tsc --project tsconfig.cluster.json",
|
|
51
51
|
"lint:agent-cli-provider": "eslint \"src/agent-cli-provider/**/*.ts\" \"tests/agent-cli-provider/**/*.ts\"",
|
|
52
52
|
"build:agent-cli-provider": "tsc --project tsconfig.agent-cli-provider.build.json",
|
|
53
53
|
"build:target": "tsc --project tsconfig.target.build.json",
|
|
54
|
-
"build:cluster": "npm run protocol:generate && tsc --project tsconfig.cluster.cjs.json && tsc --project tsconfig.cluster.esm.json && tsc --project tsconfig.hosted-session.cjs.json && tsc --project tsconfig.hosted-session.esm.json && node scripts/build-cluster.js",
|
|
54
|
+
"build:cluster": "npm run protocol:generate && tsc --project tsconfig.cluster.cjs.json && tsc --project tsconfig.cluster.esm.json && tsc --project tsconfig.hosted-target.cjs.json && tsc --project tsconfig.hosted-target.esm.json && tsc --project tsconfig.hosted-session.cjs.json && tsc --project tsconfig.hosted-session.esm.json && node scripts/build-cluster.js",
|
|
55
55
|
"test:agent-cli-provider": "node --test tests/agent-cli-provider/*.test.js",
|
|
56
56
|
"test:omp": "npm run build:agent-cli-provider && node --test tests/agent-cli-provider/omp-*.test.js && node tests/run-tests.js tests/omp-rpc-watcher.test.js tests/omp-isolation-capability.test.js tests/omp-docker-auth.test.js tests/omp-docker-fresh-only.test.js",
|
|
57
57
|
"test:providers:live": "npm run build:agent-cli-provider && node scripts/live-provider-smoke.js",
|
|
58
58
|
"check:agent-cli-provider": "npm run check:agent-cli-provider:ci",
|
|
59
59
|
"check:agent-cli-provider:ci": "npm run typecheck:agent-cli-provider && npm run lint:agent-cli-provider && npm run build:agent-cli-provider && npm run test:agent-cli-provider",
|
|
60
|
-
"test:cluster-client": "npm run build:cluster && node --test tests/cluster/client.test.js tests/cluster/parity.test.js tests/cluster/architecture.test.js tests/cluster/verifier-regressions.test.js tests/cluster/request-validation.test.js tests/hosted-session/coordinator.test.js",
|
|
60
|
+
"test:cluster-client": "npm run build:cluster && node --test tests/cluster/client.test.js tests/cluster/client-lifecycle.test.js tests/cluster/parity.test.js tests/cluster/architecture.test.js tests/cluster/verifier-regressions.test.js tests/cluster/request-validation.test.js tests/hosted-session/coordinator.test.js tests/hosted-session/coordinator-cancellation.test.js",
|
|
61
61
|
"test:cluster-package": "npm run build:agent-cli-provider && npm run build:cluster && npm run build:target && node --test tests/cluster/package.test.js",
|
|
62
62
|
"dev:link": "npm link",
|
|
63
|
+
"opcore:status": "opcore status --repo . --json",
|
|
64
|
+
"opcore:scan": "opcore --repo . --json",
|
|
65
|
+
"opcore:check": "node scripts/opcore-introduced-check.js",
|
|
66
|
+
"opcore:check:staged": "node scripts/opcore-introduced-check.js --staged",
|
|
67
|
+
"opcore:install:rust-metrics": "cargo install rust-code-analysis-cli --version 0.0.25 --locked",
|
|
68
|
+
"opcore:graph:build": "opcore graph build --repo . --json",
|
|
69
|
+
"opcore:graph:update": "opcore graph update --repo . --json",
|
|
70
|
+
"opcore:measure": "opcore measure --repo . --json",
|
|
71
|
+
"audit:production": "node scripts/audit-production-dependencies.js",
|
|
63
72
|
"lint": "eslint .",
|
|
64
73
|
"lint:fix": "eslint . --fix",
|
|
65
74
|
"validate:templates": "node scripts/validate-templates.js",
|
|
@@ -122,7 +131,7 @@
|
|
|
122
131
|
"url": "https://github.com/the-open-engine/zeroshot/issues"
|
|
123
132
|
},
|
|
124
133
|
"engines": {
|
|
125
|
-
"node": ">=
|
|
134
|
+
"node": ">=22.0.0"
|
|
126
135
|
},
|
|
127
136
|
"publishConfig": {
|
|
128
137
|
"access": "public",
|
|
@@ -169,8 +178,8 @@
|
|
|
169
178
|
"commander": "^14.0.2",
|
|
170
179
|
"node-pty": "^1.1.0",
|
|
171
180
|
"omelette": "^0.4.17",
|
|
172
|
-
"pidusage": "^4.0.1",
|
|
173
181
|
"open": "^10.1.0",
|
|
182
|
+
"pidusage": "^4.0.1",
|
|
174
183
|
"proper-lockfile": "^4.1.2"
|
|
175
184
|
},
|
|
176
185
|
"optionalDependencies": {
|
|
@@ -196,6 +205,7 @@
|
|
|
196
205
|
"jscpd": "^3.5.10",
|
|
197
206
|
"lint-staged": "^16.2.7",
|
|
198
207
|
"mocha": "^11.7.5",
|
|
208
|
+
"opcore": "0.2.1",
|
|
199
209
|
"prettier": "^3.7.4",
|
|
200
210
|
"semantic-release": "^25.0.2",
|
|
201
211
|
"sinon": "^21.0.0",
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
'use strict';
|
|
3
|
+
|
|
4
|
+
const { spawnSync } = require('node:child_process');
|
|
5
|
+
|
|
6
|
+
const severityRank = new Map([
|
|
7
|
+
['info', 0],
|
|
8
|
+
['low', 1],
|
|
9
|
+
['moderate', 2],
|
|
10
|
+
['high', 3],
|
|
11
|
+
['critical', 4],
|
|
12
|
+
]);
|
|
13
|
+
const approvedLeafAdvisories = new Map([
|
|
14
|
+
['brace-expansion', new Set(['1123898', '1130591'])],
|
|
15
|
+
['smol-toml', new Set(['1115393'])],
|
|
16
|
+
]);
|
|
17
|
+
const approvedLeafPaths = new Map([
|
|
18
|
+
['brace-expansion', 'node_modules/opcore/node_modules/brace-expansion'],
|
|
19
|
+
['smol-toml', 'node_modules/opcore/node_modules/smol-toml'],
|
|
20
|
+
]);
|
|
21
|
+
const approvedVersions = new Map([
|
|
22
|
+
['node_modules/opcore', '0.2.1'],
|
|
23
|
+
['node_modules/opcore/node_modules/brace-expansion', '5.0.6'],
|
|
24
|
+
['node_modules/opcore/node_modules/smol-toml', '1.6.0'],
|
|
25
|
+
]);
|
|
26
|
+
|
|
27
|
+
function isRelevant(vulnerability) {
|
|
28
|
+
return (severityRank.get(vulnerability.severity) ?? Number.POSITIVE_INFINITY) >= 2;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
function hasExpectedNodes(name, vulnerability) {
|
|
32
|
+
const nodes = vulnerability.nodes;
|
|
33
|
+
if (!Array.isArray(nodes) || nodes.length === 0) return false;
|
|
34
|
+
const leafPath = approvedLeafPaths.get(name);
|
|
35
|
+
if (leafPath !== undefined) return nodes.length === 1 && nodes[0] === leafPath;
|
|
36
|
+
if (name === 'opcore') return nodes.length === 1 && nodes[0] === 'node_modules/opcore';
|
|
37
|
+
return nodes.every((node) => node.startsWith('node_modules/opcore/node_modules/'));
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
function isApprovedLeaf(name, vulnerability) {
|
|
41
|
+
const approvedSources = approvedLeafAdvisories.get(name);
|
|
42
|
+
if (approvedSources === undefined || !hasExpectedNodes(name, vulnerability)) return false;
|
|
43
|
+
if (!Array.isArray(vulnerability.via) || vulnerability.via.length === 0) return false;
|
|
44
|
+
return vulnerability.via.every(
|
|
45
|
+
(advisory) =>
|
|
46
|
+
advisory !== null &&
|
|
47
|
+
typeof advisory === 'object' &&
|
|
48
|
+
approvedSources.has(String(advisory.source))
|
|
49
|
+
);
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
function isApprovedVulnerability(name, vulnerabilities, memo, active) {
|
|
53
|
+
if (memo.has(name)) return memo.get(name);
|
|
54
|
+
if (active.has(name)) return false;
|
|
55
|
+
const vulnerability = vulnerabilities[name];
|
|
56
|
+
if (vulnerability === undefined || !hasExpectedNodes(name, vulnerability)) return false;
|
|
57
|
+
if (isApprovedLeaf(name, vulnerability)) {
|
|
58
|
+
memo.set(name, true);
|
|
59
|
+
return true;
|
|
60
|
+
}
|
|
61
|
+
if (!Array.isArray(vulnerability.via) || vulnerability.via.length === 0) return false;
|
|
62
|
+
if (!vulnerability.via.every((dependency) => typeof dependency === 'string')) return false;
|
|
63
|
+
|
|
64
|
+
active.add(name);
|
|
65
|
+
const approved = vulnerability.via.every((dependency) =>
|
|
66
|
+
isApprovedVulnerability(dependency, vulnerabilities, memo, active)
|
|
67
|
+
);
|
|
68
|
+
active.delete(name);
|
|
69
|
+
memo.set(name, approved);
|
|
70
|
+
return approved;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
function exceptionVersionsMatch(lock) {
|
|
74
|
+
if (lock?.packages?.['']?.dependencies?.opcore !== '0.2.1') return false;
|
|
75
|
+
return Array.from(approvedVersions).every(
|
|
76
|
+
([packagePath, version]) => lock?.packages?.[packagePath]?.version === version
|
|
77
|
+
);
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
function evaluateAudit(payload, lock) {
|
|
81
|
+
if (payload === null || typeof payload !== 'object' || payload.error !== undefined) {
|
|
82
|
+
throw new Error('npm audit did not return a valid vulnerability report');
|
|
83
|
+
}
|
|
84
|
+
const vulnerabilities = payload.vulnerabilities;
|
|
85
|
+
if (vulnerabilities === null || typeof vulnerabilities !== 'object') {
|
|
86
|
+
throw new Error('npm audit report is missing vulnerabilities');
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
const relevant = Object.entries(vulnerabilities).filter(([, vulnerability]) =>
|
|
90
|
+
isRelevant(vulnerability)
|
|
91
|
+
);
|
|
92
|
+
const memo = new Map();
|
|
93
|
+
const allowed = relevant.filter(([name]) =>
|
|
94
|
+
isApprovedVulnerability(name, vulnerabilities, memo, new Set())
|
|
95
|
+
);
|
|
96
|
+
if (allowed.length > 0 && !exceptionVersionsMatch(lock)) {
|
|
97
|
+
return { allowed: [], blocked: relevant, versionMismatch: true };
|
|
98
|
+
}
|
|
99
|
+
const allowedNames = new Set(allowed.map(([name]) => name));
|
|
100
|
+
return {
|
|
101
|
+
allowed,
|
|
102
|
+
blocked: relevant.filter(([name]) => !allowedNames.has(name)),
|
|
103
|
+
versionMismatch: false,
|
|
104
|
+
};
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
function runAudit() {
|
|
108
|
+
const npm = process.platform === 'win32' ? 'npm.cmd' : 'npm';
|
|
109
|
+
const result = spawnSync(npm, ['audit', '--audit-level=moderate', '--omit=dev', '--json'], {
|
|
110
|
+
encoding: 'utf8',
|
|
111
|
+
maxBuffer: 16 * 1024 * 1024,
|
|
112
|
+
});
|
|
113
|
+
if (result.error) throw result.error;
|
|
114
|
+
|
|
115
|
+
let payload;
|
|
116
|
+
try {
|
|
117
|
+
payload = JSON.parse(result.stdout);
|
|
118
|
+
} catch {
|
|
119
|
+
throw new Error(
|
|
120
|
+
result.stderr || result.stdout || `npm audit exited with status ${result.status}`
|
|
121
|
+
);
|
|
122
|
+
}
|
|
123
|
+
const lock = require('../package-lock.json');
|
|
124
|
+
return evaluateAudit(payload, lock);
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
function main() {
|
|
128
|
+
const result = runAudit();
|
|
129
|
+
if (result.blocked.length > 0) {
|
|
130
|
+
const suffix = result.versionMismatch ? ' (Opcore exception version mismatch)' : '';
|
|
131
|
+
console.error(
|
|
132
|
+
`Production dependency audit failed${suffix}: ${result.blocked.map(([name]) => name).join(', ')}`
|
|
133
|
+
);
|
|
134
|
+
process.exitCode = 1;
|
|
135
|
+
return;
|
|
136
|
+
}
|
|
137
|
+
if (result.allowed.length > 0) {
|
|
138
|
+
console.warn(
|
|
139
|
+
`Production dependency audit passed with pinned Opcore advisories: ${result.allowed
|
|
140
|
+
.map(([name]) => name)
|
|
141
|
+
.join(', ')}`
|
|
142
|
+
);
|
|
143
|
+
return;
|
|
144
|
+
}
|
|
145
|
+
console.log('Production dependency audit passed');
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
if (require.main === module) main();
|
|
149
|
+
|
|
150
|
+
module.exports = { evaluateAudit };
|