@probelabs/visor 0.1.173-ee → 0.1.173
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/index.js +23 -1840
- package/dist/output/traces/run-2026-03-09T15-21-25-122Z.ndjson +138 -0
- package/dist/output/traces/run-2026-03-09T15-22-05-255Z.ndjson +2280 -0
- package/dist/sdk/a2a-frontend-VHOQ45CR.mjs +1658 -0
- package/dist/sdk/a2a-frontend-VHOQ45CR.mjs.map +1 -0
- package/dist/sdk/check-provider-registry-65GO3SCO.mjs +30 -0
- package/dist/sdk/{check-provider-registry-ZMSJFQSU.mjs → check-provider-registry-DBTS7OXY.mjs} +2 -2
- package/dist/sdk/{chunk-CMEYDK6S.mjs → chunk-7CWJNSL2.mjs} +9 -9
- package/dist/sdk/{chunk-CMEYDK6S.mjs.map → chunk-7CWJNSL2.mjs.map} +1 -1
- package/dist/sdk/chunk-AV6KML52.mjs +45016 -0
- package/dist/sdk/chunk-AV6KML52.mjs.map +1 -0
- package/dist/sdk/chunk-GVPMO6QD.mjs +1502 -0
- package/dist/sdk/chunk-GVPMO6QD.mjs.map +1 -0
- package/dist/sdk/chunk-LTHHE6Z5.mjs +516 -0
- package/dist/sdk/chunk-LTHHE6Z5.mjs.map +1 -0
- package/dist/sdk/chunk-VVHALCWV.mjs +739 -0
- package/dist/sdk/chunk-VVHALCWV.mjs.map +1 -0
- package/dist/sdk/failure-condition-evaluator-Q4KNMX6F.mjs +18 -0
- package/dist/sdk/github-frontend-OOP26667.mjs +1386 -0
- package/dist/sdk/github-frontend-OOP26667.mjs.map +1 -0
- package/dist/sdk/{host-TAGO66M6.mjs → host-VYPJ2UGQ.mjs} +3 -3
- package/dist/sdk/routing-DBQHPP2O.mjs +26 -0
- package/dist/sdk/schedule-tool-2FIVKPVJ.mjs +36 -0
- package/dist/sdk/schedule-tool-2FIVKPVJ.mjs.map +1 -0
- package/dist/sdk/{schedule-tool-LPBO3TNY.mjs → schedule-tool-MHICRNCI.mjs} +2 -2
- package/dist/sdk/schedule-tool-MHICRNCI.mjs.map +1 -0
- package/dist/sdk/{schedule-tool-handler-A7YKDVLZ.mjs → schedule-tool-handler-3ES4WON7.mjs} +2 -2
- package/dist/sdk/schedule-tool-handler-3ES4WON7.mjs.map +1 -0
- package/dist/sdk/schedule-tool-handler-FQGAWC5N.mjs +40 -0
- package/dist/sdk/schedule-tool-handler-FQGAWC5N.mjs.map +1 -0
- package/dist/sdk/sdk.js +281 -1655
- package/dist/sdk/sdk.js.map +1 -1
- package/dist/sdk/sdk.mjs +4 -4
- package/dist/sdk/trace-helpers-ZFDJ55SH.mjs +29 -0
- package/dist/sdk/trace-helpers-ZFDJ55SH.mjs.map +1 -0
- package/dist/sdk/workflow-check-provider-5KQTXKWS.mjs +30 -0
- package/dist/sdk/workflow-check-provider-5KQTXKWS.mjs.map +1 -0
- package/dist/sdk/{workflow-check-provider-FXTRMKJ2.mjs → workflow-check-provider-F5DTEX6E.mjs} +2 -2
- package/dist/sdk/workflow-check-provider-F5DTEX6E.mjs.map +1 -0
- package/dist/traces/run-2026-03-09T15-21-25-122Z.ndjson +138 -0
- package/dist/traces/run-2026-03-09T15-22-05-255Z.ndjson +2280 -0
- package/package.json +1 -1
- package/dist/sdk/knex-store-QCEW4I4R.mjs +0 -527
- package/dist/sdk/knex-store-QCEW4I4R.mjs.map +0 -1
- package/dist/sdk/loader-Q7K76ZIY.mjs +0 -89
- package/dist/sdk/loader-Q7K76ZIY.mjs.map +0 -1
- package/dist/sdk/opa-policy-engine-QCSSIMUF.mjs +0 -655
- package/dist/sdk/opa-policy-engine-QCSSIMUF.mjs.map +0 -1
- package/dist/sdk/validator-XTZJZZJH.mjs +0 -134
- package/dist/sdk/validator-XTZJZZJH.mjs.map +0 -1
- /package/dist/sdk/{check-provider-registry-ZMSJFQSU.mjs.map → check-provider-registry-65GO3SCO.mjs.map} +0 -0
- /package/dist/sdk/{schedule-tool-LPBO3TNY.mjs.map → check-provider-registry-DBTS7OXY.mjs.map} +0 -0
- /package/dist/sdk/{schedule-tool-handler-A7YKDVLZ.mjs.map → failure-condition-evaluator-Q4KNMX6F.mjs.map} +0 -0
- /package/dist/sdk/{host-TAGO66M6.mjs.map → host-VYPJ2UGQ.mjs.map} +0 -0
- /package/dist/sdk/{workflow-check-provider-FXTRMKJ2.mjs.map → routing-DBQHPP2O.mjs.map} +0 -0
package/dist/sdk/sdk.js
CHANGED
|
@@ -704,7 +704,7 @@ var require_package = __commonJS({
|
|
|
704
704
|
"package.json"(exports2, module2) {
|
|
705
705
|
module2.exports = {
|
|
706
706
|
name: "@probelabs/visor",
|
|
707
|
-
version: "0.1.
|
|
707
|
+
version: "0.1.173",
|
|
708
708
|
main: "dist/index.js",
|
|
709
709
|
bin: {
|
|
710
710
|
visor: "./dist/index.js"
|
|
@@ -1150,11 +1150,11 @@ function getTracer() {
|
|
|
1150
1150
|
}
|
|
1151
1151
|
async function withActiveSpan(name, attrs, fn) {
|
|
1152
1152
|
const tracer = getTracer();
|
|
1153
|
-
return await new Promise((
|
|
1153
|
+
return await new Promise((resolve15, reject) => {
|
|
1154
1154
|
const callback = async (span) => {
|
|
1155
1155
|
try {
|
|
1156
1156
|
const res = await fn(span);
|
|
1157
|
-
|
|
1157
|
+
resolve15(res);
|
|
1158
1158
|
} catch (err) {
|
|
1159
1159
|
try {
|
|
1160
1160
|
if (err instanceof Error) span.recordException(err);
|
|
@@ -1279,19 +1279,19 @@ function __getOrCreateNdjsonPath() {
|
|
|
1279
1279
|
try {
|
|
1280
1280
|
if (process.env.VISOR_TELEMETRY_SINK && process.env.VISOR_TELEMETRY_SINK !== "file")
|
|
1281
1281
|
return null;
|
|
1282
|
-
const
|
|
1283
|
-
const
|
|
1282
|
+
const path29 = require("path");
|
|
1283
|
+
const fs25 = require("fs");
|
|
1284
1284
|
if (process.env.VISOR_FALLBACK_TRACE_FILE) {
|
|
1285
1285
|
__ndjsonPath = process.env.VISOR_FALLBACK_TRACE_FILE;
|
|
1286
|
-
const dir =
|
|
1287
|
-
if (!
|
|
1286
|
+
const dir = path29.dirname(__ndjsonPath);
|
|
1287
|
+
if (!fs25.existsSync(dir)) fs25.mkdirSync(dir, { recursive: true });
|
|
1288
1288
|
return __ndjsonPath;
|
|
1289
1289
|
}
|
|
1290
|
-
const outDir = process.env.VISOR_TRACE_DIR ||
|
|
1291
|
-
if (!
|
|
1290
|
+
const outDir = process.env.VISOR_TRACE_DIR || path29.join(process.cwd(), "output", "traces");
|
|
1291
|
+
if (!fs25.existsSync(outDir)) fs25.mkdirSync(outDir, { recursive: true });
|
|
1292
1292
|
if (!__ndjsonPath) {
|
|
1293
1293
|
const ts = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
1294
|
-
__ndjsonPath =
|
|
1294
|
+
__ndjsonPath = path29.join(outDir, `${ts}.ndjson`);
|
|
1295
1295
|
}
|
|
1296
1296
|
return __ndjsonPath;
|
|
1297
1297
|
} catch {
|
|
@@ -1300,11 +1300,11 @@ function __getOrCreateNdjsonPath() {
|
|
|
1300
1300
|
}
|
|
1301
1301
|
function _appendRunMarker() {
|
|
1302
1302
|
try {
|
|
1303
|
-
const
|
|
1303
|
+
const fs25 = require("fs");
|
|
1304
1304
|
const p = __getOrCreateNdjsonPath();
|
|
1305
1305
|
if (!p) return;
|
|
1306
1306
|
const line = { name: "visor.run", attributes: { started: true } };
|
|
1307
|
-
|
|
1307
|
+
fs25.appendFileSync(p, JSON.stringify(line) + "\n", "utf8");
|
|
1308
1308
|
} catch {
|
|
1309
1309
|
}
|
|
1310
1310
|
}
|
|
@@ -3391,7 +3391,7 @@ var init_failure_condition_evaluator = __esm({
|
|
|
3391
3391
|
*/
|
|
3392
3392
|
evaluateExpression(condition, context2) {
|
|
3393
3393
|
try {
|
|
3394
|
-
const
|
|
3394
|
+
const normalize4 = (expr) => {
|
|
3395
3395
|
const trimmed = expr.trim();
|
|
3396
3396
|
if (!/[\n;]/.test(trimmed)) return trimmed;
|
|
3397
3397
|
const parts = trimmed.split(/[\n;]+/).map((s) => s.trim()).filter((s) => s.length > 0 && !s.startsWith("//"));
|
|
@@ -3549,7 +3549,7 @@ var init_failure_condition_evaluator = __esm({
|
|
|
3549
3549
|
try {
|
|
3550
3550
|
exec2 = this.sandbox.compile(`return (${raw});`);
|
|
3551
3551
|
} catch {
|
|
3552
|
-
const normalizedExpr =
|
|
3552
|
+
const normalizedExpr = normalize4(condition);
|
|
3553
3553
|
exec2 = this.sandbox.compile(`return (${normalizedExpr});`);
|
|
3554
3554
|
}
|
|
3555
3555
|
const result = exec2(scope).run();
|
|
@@ -3932,9 +3932,9 @@ function configureLiquidWithExtensions(liquid) {
|
|
|
3932
3932
|
});
|
|
3933
3933
|
liquid.registerFilter("get", (obj, pathExpr) => {
|
|
3934
3934
|
if (obj == null) return void 0;
|
|
3935
|
-
const
|
|
3936
|
-
if (!
|
|
3937
|
-
const parts =
|
|
3935
|
+
const path29 = typeof pathExpr === "string" ? pathExpr : String(pathExpr || "");
|
|
3936
|
+
if (!path29) return obj;
|
|
3937
|
+
const parts = path29.split(".");
|
|
3938
3938
|
let cur = obj;
|
|
3939
3939
|
for (const p of parts) {
|
|
3940
3940
|
if (cur == null) return void 0;
|
|
@@ -4053,9 +4053,9 @@ function configureLiquidWithExtensions(liquid) {
|
|
|
4053
4053
|
}
|
|
4054
4054
|
}
|
|
4055
4055
|
const defaultRole = typeof rolesCfg.default === "string" && rolesCfg.default.trim() ? rolesCfg.default.trim() : void 0;
|
|
4056
|
-
const getNested = (obj,
|
|
4057
|
-
if (!obj || !
|
|
4058
|
-
const parts =
|
|
4056
|
+
const getNested = (obj, path29) => {
|
|
4057
|
+
if (!obj || !path29) return void 0;
|
|
4058
|
+
const parts = path29.split(".");
|
|
4059
4059
|
let cur = obj;
|
|
4060
4060
|
for (const p of parts) {
|
|
4061
4061
|
if (cur == null) return void 0;
|
|
@@ -6607,8 +6607,8 @@ var init_dependency_gating = __esm({
|
|
|
6607
6607
|
async function renderTemplateContent(checkId, checkConfig, reviewSummary) {
|
|
6608
6608
|
try {
|
|
6609
6609
|
const { createExtendedLiquid: createExtendedLiquid2 } = await Promise.resolve().then(() => (init_liquid_extensions(), liquid_extensions_exports));
|
|
6610
|
-
const
|
|
6611
|
-
const
|
|
6610
|
+
const fs25 = await import("fs/promises");
|
|
6611
|
+
const path29 = await import("path");
|
|
6612
6612
|
const schemaRaw = checkConfig.schema || "plain";
|
|
6613
6613
|
const schema = typeof schemaRaw === "string" ? schemaRaw : "code-review";
|
|
6614
6614
|
let templateContent;
|
|
@@ -6616,24 +6616,24 @@ async function renderTemplateContent(checkId, checkConfig, reviewSummary) {
|
|
|
6616
6616
|
templateContent = String(checkConfig.template.content);
|
|
6617
6617
|
} else if (checkConfig.template && checkConfig.template.file) {
|
|
6618
6618
|
const file = String(checkConfig.template.file);
|
|
6619
|
-
const resolved =
|
|
6620
|
-
templateContent = await
|
|
6619
|
+
const resolved = path29.resolve(process.cwd(), file);
|
|
6620
|
+
templateContent = await fs25.readFile(resolved, "utf-8");
|
|
6621
6621
|
} else if (schema && schema !== "plain") {
|
|
6622
6622
|
const sanitized = String(schema).replace(/[^a-zA-Z0-9-]/g, "");
|
|
6623
6623
|
if (sanitized) {
|
|
6624
6624
|
const candidatePaths = [
|
|
6625
|
-
|
|
6625
|
+
path29.join(__dirname, "output", sanitized, "template.liquid"),
|
|
6626
6626
|
// bundled: dist/output/
|
|
6627
|
-
|
|
6627
|
+
path29.join(__dirname, "..", "..", "output", sanitized, "template.liquid"),
|
|
6628
6628
|
// source: output/
|
|
6629
|
-
|
|
6629
|
+
path29.join(process.cwd(), "output", sanitized, "template.liquid"),
|
|
6630
6630
|
// fallback: cwd/output/
|
|
6631
|
-
|
|
6631
|
+
path29.join(process.cwd(), "dist", "output", sanitized, "template.liquid")
|
|
6632
6632
|
// fallback: cwd/dist/output/
|
|
6633
6633
|
];
|
|
6634
6634
|
for (const p of candidatePaths) {
|
|
6635
6635
|
try {
|
|
6636
|
-
templateContent = await
|
|
6636
|
+
templateContent = await fs25.readFile(p, "utf-8");
|
|
6637
6637
|
if (templateContent) break;
|
|
6638
6638
|
} catch {
|
|
6639
6639
|
}
|
|
@@ -7038,7 +7038,7 @@ async function processDiffWithOutline(diffContent) {
|
|
|
7038
7038
|
}
|
|
7039
7039
|
try {
|
|
7040
7040
|
const originalProbePath = process.env.PROBE_PATH;
|
|
7041
|
-
const
|
|
7041
|
+
const fs25 = require("fs");
|
|
7042
7042
|
const possiblePaths = [
|
|
7043
7043
|
// Relative to current working directory (most common in production)
|
|
7044
7044
|
path6.join(process.cwd(), "node_modules/@probelabs/probe/bin/probe-binary"),
|
|
@@ -7049,7 +7049,7 @@ async function processDiffWithOutline(diffContent) {
|
|
|
7049
7049
|
];
|
|
7050
7050
|
let probeBinaryPath;
|
|
7051
7051
|
for (const candidatePath of possiblePaths) {
|
|
7052
|
-
if (
|
|
7052
|
+
if (fs25.existsSync(candidatePath)) {
|
|
7053
7053
|
probeBinaryPath = candidatePath;
|
|
7054
7054
|
break;
|
|
7055
7055
|
}
|
|
@@ -7156,7 +7156,7 @@ async function renderMermaidToPng(mermaidCode) {
|
|
|
7156
7156
|
if (chromiumPath) {
|
|
7157
7157
|
env.PUPPETEER_EXECUTABLE_PATH = chromiumPath;
|
|
7158
7158
|
}
|
|
7159
|
-
const result = await new Promise((
|
|
7159
|
+
const result = await new Promise((resolve15) => {
|
|
7160
7160
|
const proc = (0, import_child_process.spawn)(
|
|
7161
7161
|
"npx",
|
|
7162
7162
|
[
|
|
@@ -7186,13 +7186,13 @@ async function renderMermaidToPng(mermaidCode) {
|
|
|
7186
7186
|
});
|
|
7187
7187
|
proc.on("close", (code) => {
|
|
7188
7188
|
if (code === 0) {
|
|
7189
|
-
|
|
7189
|
+
resolve15({ success: true });
|
|
7190
7190
|
} else {
|
|
7191
|
-
|
|
7191
|
+
resolve15({ success: false, error: stderr || `Exit code ${code}` });
|
|
7192
7192
|
}
|
|
7193
7193
|
});
|
|
7194
7194
|
proc.on("error", (err) => {
|
|
7195
|
-
|
|
7195
|
+
resolve15({ success: false, error: err.message });
|
|
7196
7196
|
});
|
|
7197
7197
|
});
|
|
7198
7198
|
if (!result.success) {
|
|
@@ -8354,8 +8354,8 @@ ${schemaString}`);
|
|
|
8354
8354
|
}
|
|
8355
8355
|
if (process.env.VISOR_DEBUG_AI_SESSIONS === "true") {
|
|
8356
8356
|
try {
|
|
8357
|
-
const
|
|
8358
|
-
const
|
|
8357
|
+
const fs25 = require("fs");
|
|
8358
|
+
const path29 = require("path");
|
|
8359
8359
|
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
8360
8360
|
const provider = this.config.provider || "auto";
|
|
8361
8361
|
const model = this.config.model || "default";
|
|
@@ -8469,20 +8469,20 @@ ${"=".repeat(60)}
|
|
|
8469
8469
|
`;
|
|
8470
8470
|
readableVersion += `${"=".repeat(60)}
|
|
8471
8471
|
`;
|
|
8472
|
-
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS ||
|
|
8473
|
-
if (!
|
|
8474
|
-
|
|
8472
|
+
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS || path29.join(process.cwd(), "debug-artifacts");
|
|
8473
|
+
if (!fs25.existsSync(debugArtifactsDir)) {
|
|
8474
|
+
fs25.mkdirSync(debugArtifactsDir, { recursive: true });
|
|
8475
8475
|
}
|
|
8476
|
-
const debugFile =
|
|
8476
|
+
const debugFile = path29.join(
|
|
8477
8477
|
debugArtifactsDir,
|
|
8478
8478
|
`prompt-${_checkName || "unknown"}-${timestamp}.json`
|
|
8479
8479
|
);
|
|
8480
|
-
|
|
8481
|
-
const readableFile =
|
|
8480
|
+
fs25.writeFileSync(debugFile, debugJson, "utf-8");
|
|
8481
|
+
const readableFile = path29.join(
|
|
8482
8482
|
debugArtifactsDir,
|
|
8483
8483
|
`prompt-${_checkName || "unknown"}-${timestamp}.txt`
|
|
8484
8484
|
);
|
|
8485
|
-
|
|
8485
|
+
fs25.writeFileSync(readableFile, readableVersion, "utf-8");
|
|
8486
8486
|
log(`
|
|
8487
8487
|
\u{1F4BE} Full debug info saved to:`);
|
|
8488
8488
|
log(` JSON: ${debugFile}`);
|
|
@@ -8520,8 +8520,8 @@ ${"=".repeat(60)}
|
|
|
8520
8520
|
log(`\u{1F4E4} Response length: ${response.length} characters`);
|
|
8521
8521
|
if (process.env.VISOR_DEBUG_AI_SESSIONS === "true") {
|
|
8522
8522
|
try {
|
|
8523
|
-
const
|
|
8524
|
-
const
|
|
8523
|
+
const fs25 = require("fs");
|
|
8524
|
+
const path29 = require("path");
|
|
8525
8525
|
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
8526
8526
|
const agentAny2 = agent;
|
|
8527
8527
|
let fullHistory = [];
|
|
@@ -8532,8 +8532,8 @@ ${"=".repeat(60)}
|
|
|
8532
8532
|
} else if (agentAny2._messages) {
|
|
8533
8533
|
fullHistory = agentAny2._messages;
|
|
8534
8534
|
}
|
|
8535
|
-
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS ||
|
|
8536
|
-
const sessionBase =
|
|
8535
|
+
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS || path29.join(process.cwd(), "debug-artifacts");
|
|
8536
|
+
const sessionBase = path29.join(
|
|
8537
8537
|
debugArtifactsDir,
|
|
8538
8538
|
`session-${_checkName || "unknown"}-${timestamp}`
|
|
8539
8539
|
);
|
|
@@ -8545,7 +8545,7 @@ ${"=".repeat(60)}
|
|
|
8545
8545
|
schema: effectiveSchema,
|
|
8546
8546
|
totalMessages: fullHistory.length
|
|
8547
8547
|
};
|
|
8548
|
-
|
|
8548
|
+
fs25.writeFileSync(sessionBase + ".json", JSON.stringify(sessionData, null, 2), "utf-8");
|
|
8549
8549
|
let readable = `=============================================================
|
|
8550
8550
|
`;
|
|
8551
8551
|
readable += `COMPLETE AI SESSION HISTORY (AFTER RESPONSE)
|
|
@@ -8572,7 +8572,7 @@ ${"=".repeat(60)}
|
|
|
8572
8572
|
`;
|
|
8573
8573
|
readable += content + "\n";
|
|
8574
8574
|
});
|
|
8575
|
-
|
|
8575
|
+
fs25.writeFileSync(sessionBase + ".summary.txt", readable, "utf-8");
|
|
8576
8576
|
log(`\u{1F4BE} Complete session history saved:`);
|
|
8577
8577
|
log(` - Contains ALL ${fullHistory.length} messages (prompts + responses)`);
|
|
8578
8578
|
} catch (error) {
|
|
@@ -8581,11 +8581,11 @@ ${"=".repeat(60)}
|
|
|
8581
8581
|
}
|
|
8582
8582
|
if (process.env.VISOR_DEBUG_AI_SESSIONS === "true") {
|
|
8583
8583
|
try {
|
|
8584
|
-
const
|
|
8585
|
-
const
|
|
8584
|
+
const fs25 = require("fs");
|
|
8585
|
+
const path29 = require("path");
|
|
8586
8586
|
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
8587
|
-
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS ||
|
|
8588
|
-
const responseFile =
|
|
8587
|
+
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS || path29.join(process.cwd(), "debug-artifacts");
|
|
8588
|
+
const responseFile = path29.join(
|
|
8589
8589
|
debugArtifactsDir,
|
|
8590
8590
|
`response-${_checkName || "unknown"}-${timestamp}.txt`
|
|
8591
8591
|
);
|
|
@@ -8618,7 +8618,7 @@ ${"=".repeat(60)}
|
|
|
8618
8618
|
`;
|
|
8619
8619
|
responseContent += `${"=".repeat(60)}
|
|
8620
8620
|
`;
|
|
8621
|
-
|
|
8621
|
+
fs25.writeFileSync(responseFile, responseContent, "utf-8");
|
|
8622
8622
|
log(`\u{1F4BE} Response saved to: ${responseFile}`);
|
|
8623
8623
|
} catch (error) {
|
|
8624
8624
|
log(`\u26A0\uFE0F Could not save response file: ${error}`);
|
|
@@ -8634,9 +8634,9 @@ ${"=".repeat(60)}
|
|
|
8634
8634
|
await agentAny._telemetryConfig.shutdown();
|
|
8635
8635
|
log(`\u{1F4CA} OpenTelemetry trace saved to: ${agentAny._traceFilePath}`);
|
|
8636
8636
|
if (process.env.GITHUB_ACTIONS) {
|
|
8637
|
-
const
|
|
8638
|
-
if (
|
|
8639
|
-
const stats =
|
|
8637
|
+
const fs25 = require("fs");
|
|
8638
|
+
if (fs25.existsSync(agentAny._traceFilePath)) {
|
|
8639
|
+
const stats = fs25.statSync(agentAny._traceFilePath);
|
|
8640
8640
|
console.log(
|
|
8641
8641
|
`::notice title=AI Trace Saved::${agentAny._traceFilePath} (${stats.size} bytes)`
|
|
8642
8642
|
);
|
|
@@ -8849,9 +8849,9 @@ ${schemaString}`);
|
|
|
8849
8849
|
const model = this.config.model || "default";
|
|
8850
8850
|
if (process.env.VISOR_DEBUG_AI_SESSIONS === "true") {
|
|
8851
8851
|
try {
|
|
8852
|
-
const
|
|
8853
|
-
const
|
|
8854
|
-
const
|
|
8852
|
+
const fs25 = require("fs");
|
|
8853
|
+
const path29 = require("path");
|
|
8854
|
+
const os2 = require("os");
|
|
8855
8855
|
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
8856
8856
|
const debugData = {
|
|
8857
8857
|
timestamp,
|
|
@@ -8923,19 +8923,19 @@ ${"=".repeat(60)}
|
|
|
8923
8923
|
`;
|
|
8924
8924
|
readableVersion += `${"=".repeat(60)}
|
|
8925
8925
|
`;
|
|
8926
|
-
const tempDir =
|
|
8927
|
-
const promptFile =
|
|
8928
|
-
|
|
8926
|
+
const tempDir = os2.tmpdir();
|
|
8927
|
+
const promptFile = path29.join(tempDir, `visor-prompt-${timestamp}.txt`);
|
|
8928
|
+
fs25.writeFileSync(promptFile, prompt, "utf-8");
|
|
8929
8929
|
log(`
|
|
8930
8930
|
\u{1F4BE} Prompt saved to: ${promptFile}`);
|
|
8931
|
-
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS ||
|
|
8931
|
+
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS || path29.join(process.cwd(), "debug-artifacts");
|
|
8932
8932
|
try {
|
|
8933
|
-
const base =
|
|
8933
|
+
const base = path29.join(
|
|
8934
8934
|
debugArtifactsDir,
|
|
8935
8935
|
`prompt-${_checkName || "unknown"}-${timestamp}`
|
|
8936
8936
|
);
|
|
8937
|
-
|
|
8938
|
-
|
|
8937
|
+
fs25.writeFileSync(base + ".json", debugJson, "utf-8");
|
|
8938
|
+
fs25.writeFileSync(base + ".summary.txt", readableVersion, "utf-8");
|
|
8939
8939
|
log(`
|
|
8940
8940
|
\u{1F4BE} Full debug info saved to directory: ${debugArtifactsDir}`);
|
|
8941
8941
|
} catch {
|
|
@@ -8985,8 +8985,8 @@ $ ${cliCommand}
|
|
|
8985
8985
|
log(`\u{1F4E4} Response length: ${response.length} characters`);
|
|
8986
8986
|
if (process.env.VISOR_DEBUG_AI_SESSIONS === "true") {
|
|
8987
8987
|
try {
|
|
8988
|
-
const
|
|
8989
|
-
const
|
|
8988
|
+
const fs25 = require("fs");
|
|
8989
|
+
const path29 = require("path");
|
|
8990
8990
|
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
8991
8991
|
const agentAny = agent;
|
|
8992
8992
|
let fullHistory = [];
|
|
@@ -8997,8 +8997,8 @@ $ ${cliCommand}
|
|
|
8997
8997
|
} else if (agentAny._messages) {
|
|
8998
8998
|
fullHistory = agentAny._messages;
|
|
8999
8999
|
}
|
|
9000
|
-
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS ||
|
|
9001
|
-
const sessionBase =
|
|
9000
|
+
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS || path29.join(process.cwd(), "debug-artifacts");
|
|
9001
|
+
const sessionBase = path29.join(
|
|
9002
9002
|
debugArtifactsDir,
|
|
9003
9003
|
`session-${_checkName || "unknown"}-${timestamp}`
|
|
9004
9004
|
);
|
|
@@ -9010,7 +9010,7 @@ $ ${cliCommand}
|
|
|
9010
9010
|
schema: effectiveSchema,
|
|
9011
9011
|
totalMessages: fullHistory.length
|
|
9012
9012
|
};
|
|
9013
|
-
|
|
9013
|
+
fs25.writeFileSync(sessionBase + ".json", JSON.stringify(sessionData, null, 2), "utf-8");
|
|
9014
9014
|
let readable = `=============================================================
|
|
9015
9015
|
`;
|
|
9016
9016
|
readable += `COMPLETE AI SESSION HISTORY (AFTER RESPONSE)
|
|
@@ -9037,7 +9037,7 @@ ${"=".repeat(60)}
|
|
|
9037
9037
|
`;
|
|
9038
9038
|
readable += content + "\n";
|
|
9039
9039
|
});
|
|
9040
|
-
|
|
9040
|
+
fs25.writeFileSync(sessionBase + ".summary.txt", readable, "utf-8");
|
|
9041
9041
|
log(`\u{1F4BE} Complete session history saved:`);
|
|
9042
9042
|
log(` - Contains ALL ${fullHistory.length} messages (prompts + responses)`);
|
|
9043
9043
|
} catch (error) {
|
|
@@ -9046,11 +9046,11 @@ ${"=".repeat(60)}
|
|
|
9046
9046
|
}
|
|
9047
9047
|
if (process.env.VISOR_DEBUG_AI_SESSIONS === "true") {
|
|
9048
9048
|
try {
|
|
9049
|
-
const
|
|
9050
|
-
const
|
|
9049
|
+
const fs25 = require("fs");
|
|
9050
|
+
const path29 = require("path");
|
|
9051
9051
|
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
9052
|
-
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS ||
|
|
9053
|
-
const responseFile =
|
|
9052
|
+
const debugArtifactsDir = process.env.VISOR_DEBUG_ARTIFACTS || path29.join(process.cwd(), "debug-artifacts");
|
|
9053
|
+
const responseFile = path29.join(
|
|
9054
9054
|
debugArtifactsDir,
|
|
9055
9055
|
`response-${_checkName || "unknown"}-${timestamp}.txt`
|
|
9056
9056
|
);
|
|
@@ -9083,7 +9083,7 @@ ${"=".repeat(60)}
|
|
|
9083
9083
|
`;
|
|
9084
9084
|
responseContent += `${"=".repeat(60)}
|
|
9085
9085
|
`;
|
|
9086
|
-
|
|
9086
|
+
fs25.writeFileSync(responseFile, responseContent, "utf-8");
|
|
9087
9087
|
log(`\u{1F4BE} Response saved to: ${responseFile}`);
|
|
9088
9088
|
} catch (error) {
|
|
9089
9089
|
log(`\u26A0\uFE0F Could not save response file: ${error}`);
|
|
@@ -9101,9 +9101,9 @@ ${"=".repeat(60)}
|
|
|
9101
9101
|
await telemetry.shutdown();
|
|
9102
9102
|
log(`\u{1F4CA} OpenTelemetry trace saved to: ${traceFilePath}`);
|
|
9103
9103
|
if (process.env.GITHUB_ACTIONS) {
|
|
9104
|
-
const
|
|
9105
|
-
if (
|
|
9106
|
-
const stats =
|
|
9104
|
+
const fs25 = require("fs");
|
|
9105
|
+
if (fs25.existsSync(traceFilePath)) {
|
|
9106
|
+
const stats = fs25.statSync(traceFilePath);
|
|
9107
9107
|
console.log(
|
|
9108
9108
|
`::notice title=AI Trace Saved::OpenTelemetry trace file size: ${stats.size} bytes`
|
|
9109
9109
|
);
|
|
@@ -9141,8 +9141,8 @@ ${"=".repeat(60)}
|
|
|
9141
9141
|
* Load schema content from schema files or inline definitions
|
|
9142
9142
|
*/
|
|
9143
9143
|
async loadSchemaContent(schema) {
|
|
9144
|
-
const
|
|
9145
|
-
const
|
|
9144
|
+
const fs25 = require("fs").promises;
|
|
9145
|
+
const path29 = require("path");
|
|
9146
9146
|
if (typeof schema === "object" && schema !== null) {
|
|
9147
9147
|
log("\u{1F4CB} Using inline schema object from configuration");
|
|
9148
9148
|
return JSON.stringify(schema);
|
|
@@ -9155,14 +9155,14 @@ ${"=".repeat(60)}
|
|
|
9155
9155
|
}
|
|
9156
9156
|
} catch {
|
|
9157
9157
|
}
|
|
9158
|
-
if ((schema.startsWith("./") || schema.includes(".json")) && !
|
|
9158
|
+
if ((schema.startsWith("./") || schema.includes(".json")) && !path29.isAbsolute(schema)) {
|
|
9159
9159
|
if (schema.includes("..") || schema.includes("\0")) {
|
|
9160
9160
|
throw new Error("Invalid schema path: path traversal not allowed");
|
|
9161
9161
|
}
|
|
9162
9162
|
try {
|
|
9163
|
-
const schemaPath =
|
|
9163
|
+
const schemaPath = path29.resolve(process.cwd(), schema);
|
|
9164
9164
|
log(`\u{1F4CB} Loading custom schema from file: ${schemaPath}`);
|
|
9165
|
-
const schemaContent = await
|
|
9165
|
+
const schemaContent = await fs25.readFile(schemaPath, "utf-8");
|
|
9166
9166
|
return schemaContent.trim();
|
|
9167
9167
|
} catch (error) {
|
|
9168
9168
|
throw new Error(
|
|
@@ -9176,22 +9176,22 @@ ${"=".repeat(60)}
|
|
|
9176
9176
|
}
|
|
9177
9177
|
const candidatePaths = [
|
|
9178
9178
|
// GitHub Action bundle location
|
|
9179
|
-
|
|
9179
|
+
path29.join(__dirname, "output", sanitizedSchemaName, "schema.json"),
|
|
9180
9180
|
// Historical fallback when src/output was inadvertently bundled as output1/
|
|
9181
|
-
|
|
9181
|
+
path29.join(__dirname, "output1", sanitizedSchemaName, "schema.json"),
|
|
9182
9182
|
// Local dev (repo root)
|
|
9183
|
-
|
|
9183
|
+
path29.join(process.cwd(), "output", sanitizedSchemaName, "schema.json")
|
|
9184
9184
|
];
|
|
9185
9185
|
for (const schemaPath of candidatePaths) {
|
|
9186
9186
|
try {
|
|
9187
|
-
const schemaContent = await
|
|
9187
|
+
const schemaContent = await fs25.readFile(schemaPath, "utf-8");
|
|
9188
9188
|
return schemaContent.trim();
|
|
9189
9189
|
} catch {
|
|
9190
9190
|
}
|
|
9191
9191
|
}
|
|
9192
|
-
const distPath =
|
|
9193
|
-
const distAltPath =
|
|
9194
|
-
const cwdPath =
|
|
9192
|
+
const distPath = path29.join(__dirname, "output", sanitizedSchemaName, "schema.json");
|
|
9193
|
+
const distAltPath = path29.join(__dirname, "output1", sanitizedSchemaName, "schema.json");
|
|
9194
|
+
const cwdPath = path29.join(process.cwd(), "output", sanitizedSchemaName, "schema.json");
|
|
9195
9195
|
throw new Error(
|
|
9196
9196
|
`Failed to load schema '${sanitizedSchemaName}'. Tried: ${distPath}, ${distAltPath}, and ${cwdPath}. Ensure build copies 'output/' into dist (build:cli), or provide a custom schema file/path.`
|
|
9197
9197
|
);
|
|
@@ -9433,7 +9433,7 @@ ${"=".repeat(60)}
|
|
|
9433
9433
|
* Generate mock response for testing
|
|
9434
9434
|
*/
|
|
9435
9435
|
async generateMockResponse(_prompt, _checkName, _schema) {
|
|
9436
|
-
await new Promise((
|
|
9436
|
+
await new Promise((resolve15) => setTimeout(resolve15, 500));
|
|
9437
9437
|
const name = (_checkName || "").toLowerCase();
|
|
9438
9438
|
if (name.includes("extract-facts")) {
|
|
9439
9439
|
const arr = Array.from({ length: 6 }, (_, i) => ({
|
|
@@ -9794,7 +9794,7 @@ var init_command_executor = __esm({
|
|
|
9794
9794
|
* Execute command with stdin input
|
|
9795
9795
|
*/
|
|
9796
9796
|
executeWithStdin(command, options) {
|
|
9797
|
-
return new Promise((
|
|
9797
|
+
return new Promise((resolve15, reject) => {
|
|
9798
9798
|
const childProcess = (0, import_child_process2.exec)(
|
|
9799
9799
|
command,
|
|
9800
9800
|
{
|
|
@@ -9806,7 +9806,7 @@ var init_command_executor = __esm({
|
|
|
9806
9806
|
if (error && error.killed && (error.code === "ETIMEDOUT" || error.signal === "SIGTERM")) {
|
|
9807
9807
|
reject(new Error(`Command timed out after ${options.timeout || 3e4}ms`));
|
|
9808
9808
|
} else {
|
|
9809
|
-
|
|
9809
|
+
resolve15({
|
|
9810
9810
|
stdout: stdout || "",
|
|
9811
9811
|
stderr: stderr || "",
|
|
9812
9812
|
exitCode: error ? error.code || 1 : 0
|
|
@@ -18299,17 +18299,17 @@ var init_workflow_check_provider = __esm({
|
|
|
18299
18299
|
* so it can be executed by the state machine as a nested workflow.
|
|
18300
18300
|
*/
|
|
18301
18301
|
async loadWorkflowFromConfigPath(sourcePath, baseDir) {
|
|
18302
|
-
const
|
|
18303
|
-
const
|
|
18302
|
+
const path29 = require("path");
|
|
18303
|
+
const fs25 = require("fs");
|
|
18304
18304
|
const yaml5 = require("js-yaml");
|
|
18305
|
-
const resolved =
|
|
18306
|
-
if (!
|
|
18305
|
+
const resolved = path29.isAbsolute(sourcePath) ? sourcePath : path29.resolve(baseDir, sourcePath);
|
|
18306
|
+
if (!fs25.existsSync(resolved)) {
|
|
18307
18307
|
throw new Error(`Workflow config not found at: ${resolved}`);
|
|
18308
18308
|
}
|
|
18309
|
-
const rawContent =
|
|
18309
|
+
const rawContent = fs25.readFileSync(resolved, "utf8");
|
|
18310
18310
|
const rawData = yaml5.load(rawContent);
|
|
18311
18311
|
if (rawData.imports && Array.isArray(rawData.imports)) {
|
|
18312
|
-
const configDir =
|
|
18312
|
+
const configDir = path29.dirname(resolved);
|
|
18313
18313
|
for (const source of rawData.imports) {
|
|
18314
18314
|
const results = await this.registry.import(source, {
|
|
18315
18315
|
basePath: configDir,
|
|
@@ -18339,8 +18339,8 @@ ${errors}`);
|
|
|
18339
18339
|
if (!steps || Object.keys(steps).length === 0) {
|
|
18340
18340
|
throw new Error(`Config '${resolved}' does not contain any steps to execute as a workflow`);
|
|
18341
18341
|
}
|
|
18342
|
-
const id =
|
|
18343
|
-
const name = loaded.name || `Workflow from ${
|
|
18342
|
+
const id = path29.basename(resolved).replace(/\.(ya?ml)$/i, "");
|
|
18343
|
+
const name = loaded.name || `Workflow from ${path29.basename(resolved)}`;
|
|
18344
18344
|
const workflowDef = {
|
|
18345
18345
|
id,
|
|
18346
18346
|
name,
|
|
@@ -19149,8 +19149,8 @@ async function createStoreBackend(storageConfig, haConfig) {
|
|
|
19149
19149
|
case "mssql": {
|
|
19150
19150
|
try {
|
|
19151
19151
|
const loaderPath = "../../enterprise/loader";
|
|
19152
|
-
const { loadEnterpriseStoreBackend
|
|
19153
|
-
return await
|
|
19152
|
+
const { loadEnterpriseStoreBackend } = await import(loaderPath);
|
|
19153
|
+
return await loadEnterpriseStoreBackend(driver, storageConfig, haConfig);
|
|
19154
19154
|
} catch (err) {
|
|
19155
19155
|
const msg = err instanceof Error ? err.message : String(err);
|
|
19156
19156
|
logger.error(`[StoreFactory] Failed to load enterprise ${driver} backend: ${msg}`);
|
|
@@ -21838,7 +21838,7 @@ var init_mcp_custom_sse_server = __esm({
|
|
|
21838
21838
|
* Returns the actual bound port number
|
|
21839
21839
|
*/
|
|
21840
21840
|
async start() {
|
|
21841
|
-
return new Promise((
|
|
21841
|
+
return new Promise((resolve15, reject) => {
|
|
21842
21842
|
try {
|
|
21843
21843
|
this.server = import_http.default.createServer((req, res) => {
|
|
21844
21844
|
this.handleRequest(req, res).catch((error) => {
|
|
@@ -21872,7 +21872,7 @@ var init_mcp_custom_sse_server = __esm({
|
|
|
21872
21872
|
);
|
|
21873
21873
|
}
|
|
21874
21874
|
this.startKeepalive();
|
|
21875
|
-
|
|
21875
|
+
resolve15(this.port);
|
|
21876
21876
|
});
|
|
21877
21877
|
} catch (error) {
|
|
21878
21878
|
reject(error);
|
|
@@ -21935,7 +21935,7 @@ var init_mcp_custom_sse_server = __esm({
|
|
|
21935
21935
|
logger.debug(
|
|
21936
21936
|
`[CustomToolsSSEServer:${this.sessionId}] Grace period before stop: ${waitMs}ms (activeToolCalls=${this.activeToolCalls})`
|
|
21937
21937
|
);
|
|
21938
|
-
await new Promise((
|
|
21938
|
+
await new Promise((resolve15) => setTimeout(resolve15, waitMs));
|
|
21939
21939
|
}
|
|
21940
21940
|
}
|
|
21941
21941
|
if (this.activeToolCalls > 0) {
|
|
@@ -21944,7 +21944,7 @@ var init_mcp_custom_sse_server = __esm({
|
|
|
21944
21944
|
`[CustomToolsSSEServer:${this.sessionId}] Waiting for ${this.activeToolCalls} active tool call(s) before stop`
|
|
21945
21945
|
);
|
|
21946
21946
|
while (this.activeToolCalls > 0 && Date.now() - startedAt < effectiveDrainTimeoutMs) {
|
|
21947
|
-
await new Promise((
|
|
21947
|
+
await new Promise((resolve15) => setTimeout(resolve15, 250));
|
|
21948
21948
|
}
|
|
21949
21949
|
if (this.activeToolCalls > 0) {
|
|
21950
21950
|
logger.warn(
|
|
@@ -21969,21 +21969,21 @@ var init_mcp_custom_sse_server = __esm({
|
|
|
21969
21969
|
}
|
|
21970
21970
|
this.connections.clear();
|
|
21971
21971
|
if (this.server) {
|
|
21972
|
-
await new Promise((
|
|
21972
|
+
await new Promise((resolve15, reject) => {
|
|
21973
21973
|
const timeout = setTimeout(() => {
|
|
21974
21974
|
if (this.debug) {
|
|
21975
21975
|
logger.debug(
|
|
21976
21976
|
`[CustomToolsSSEServer:${this.sessionId}] Force closing server after timeout`
|
|
21977
21977
|
);
|
|
21978
21978
|
}
|
|
21979
|
-
this.server?.close(() =>
|
|
21979
|
+
this.server?.close(() => resolve15());
|
|
21980
21980
|
}, 5e3);
|
|
21981
21981
|
this.server.close((error) => {
|
|
21982
21982
|
clearTimeout(timeout);
|
|
21983
21983
|
if (error) {
|
|
21984
21984
|
reject(error);
|
|
21985
21985
|
} else {
|
|
21986
|
-
|
|
21986
|
+
resolve15();
|
|
21987
21987
|
}
|
|
21988
21988
|
});
|
|
21989
21989
|
});
|
|
@@ -22433,7 +22433,7 @@ var init_mcp_custom_sse_server = __esm({
|
|
|
22433
22433
|
logger.warn(
|
|
22434
22434
|
`[CustomToolsSSEServer:${this.sessionId}] Tool ${toolName} failed (attempt ${attempt + 1}/${retryCount + 1}): ${errorMsg}. Retrying in ${delay}ms`
|
|
22435
22435
|
);
|
|
22436
|
-
await new Promise((
|
|
22436
|
+
await new Promise((resolve15) => setTimeout(resolve15, delay));
|
|
22437
22437
|
attempt++;
|
|
22438
22438
|
}
|
|
22439
22439
|
}
|
|
@@ -22825,9 +22825,9 @@ var init_ai_check_provider = __esm({
|
|
|
22825
22825
|
} else {
|
|
22826
22826
|
resolvedPath = import_path8.default.resolve(process.cwd(), str);
|
|
22827
22827
|
}
|
|
22828
|
-
const
|
|
22828
|
+
const fs25 = require("fs").promises;
|
|
22829
22829
|
try {
|
|
22830
|
-
const stat2 = await
|
|
22830
|
+
const stat2 = await fs25.stat(resolvedPath);
|
|
22831
22831
|
return stat2.isFile();
|
|
22832
22832
|
} catch {
|
|
22833
22833
|
return hasFileExtension && (isRelativePath || isAbsolutePath || hasPathSeparators);
|
|
@@ -28929,14 +28929,14 @@ var require_util = __commonJS({
|
|
|
28929
28929
|
}
|
|
28930
28930
|
const port = url.port != null ? url.port : url.protocol === "https:" ? 443 : 80;
|
|
28931
28931
|
let origin = url.origin != null ? url.origin : `${url.protocol}//${url.hostname}:${port}`;
|
|
28932
|
-
let
|
|
28932
|
+
let path29 = url.path != null ? url.path : `${url.pathname || ""}${url.search || ""}`;
|
|
28933
28933
|
if (origin.endsWith("/")) {
|
|
28934
28934
|
origin = origin.substring(0, origin.length - 1);
|
|
28935
28935
|
}
|
|
28936
|
-
if (
|
|
28937
|
-
|
|
28936
|
+
if (path29 && !path29.startsWith("/")) {
|
|
28937
|
+
path29 = `/${path29}`;
|
|
28938
28938
|
}
|
|
28939
|
-
url = new URL(origin +
|
|
28939
|
+
url = new URL(origin + path29);
|
|
28940
28940
|
}
|
|
28941
28941
|
return url;
|
|
28942
28942
|
}
|
|
@@ -30550,20 +30550,20 @@ var require_parseParams = __commonJS({
|
|
|
30550
30550
|
var require_basename = __commonJS({
|
|
30551
30551
|
"node_modules/@fastify/busboy/lib/utils/basename.js"(exports2, module2) {
|
|
30552
30552
|
"use strict";
|
|
30553
|
-
module2.exports = function basename4(
|
|
30554
|
-
if (typeof
|
|
30553
|
+
module2.exports = function basename4(path29) {
|
|
30554
|
+
if (typeof path29 !== "string") {
|
|
30555
30555
|
return "";
|
|
30556
30556
|
}
|
|
30557
|
-
for (var i =
|
|
30558
|
-
switch (
|
|
30557
|
+
for (var i = path29.length - 1; i >= 0; --i) {
|
|
30558
|
+
switch (path29.charCodeAt(i)) {
|
|
30559
30559
|
case 47:
|
|
30560
30560
|
// '/'
|
|
30561
30561
|
case 92:
|
|
30562
|
-
|
|
30563
|
-
return
|
|
30562
|
+
path29 = path29.slice(i + 1);
|
|
30563
|
+
return path29 === ".." || path29 === "." ? "" : path29;
|
|
30564
30564
|
}
|
|
30565
30565
|
}
|
|
30566
|
-
return
|
|
30566
|
+
return path29 === ".." || path29 === "." ? "" : path29;
|
|
30567
30567
|
};
|
|
30568
30568
|
}
|
|
30569
30569
|
});
|
|
@@ -31567,11 +31567,11 @@ var require_util2 = __commonJS({
|
|
|
31567
31567
|
var assert = require("assert");
|
|
31568
31568
|
var { isUint8Array } = require("util/types");
|
|
31569
31569
|
var supportedHashes = [];
|
|
31570
|
-
var
|
|
31570
|
+
var crypto7;
|
|
31571
31571
|
try {
|
|
31572
|
-
|
|
31572
|
+
crypto7 = require("crypto");
|
|
31573
31573
|
const possibleRelevantHashes = ["sha256", "sha384", "sha512"];
|
|
31574
|
-
supportedHashes =
|
|
31574
|
+
supportedHashes = crypto7.getHashes().filter((hash) => possibleRelevantHashes.includes(hash));
|
|
31575
31575
|
} catch {
|
|
31576
31576
|
}
|
|
31577
31577
|
function responseURL(response) {
|
|
@@ -31848,7 +31848,7 @@ var require_util2 = __commonJS({
|
|
|
31848
31848
|
}
|
|
31849
31849
|
}
|
|
31850
31850
|
function bytesMatch(bytes, metadataList) {
|
|
31851
|
-
if (
|
|
31851
|
+
if (crypto7 === void 0) {
|
|
31852
31852
|
return true;
|
|
31853
31853
|
}
|
|
31854
31854
|
const parsedMetadata = parseMetadata(metadataList);
|
|
@@ -31863,7 +31863,7 @@ var require_util2 = __commonJS({
|
|
|
31863
31863
|
for (const item of metadata) {
|
|
31864
31864
|
const algorithm = item.algo;
|
|
31865
31865
|
const expectedValue = item.hash;
|
|
31866
|
-
let actualValue =
|
|
31866
|
+
let actualValue = crypto7.createHash(algorithm).update(bytes).digest("base64");
|
|
31867
31867
|
if (actualValue[actualValue.length - 1] === "=") {
|
|
31868
31868
|
if (actualValue[actualValue.length - 2] === "=") {
|
|
31869
31869
|
actualValue = actualValue.slice(0, -2);
|
|
@@ -31956,8 +31956,8 @@ var require_util2 = __commonJS({
|
|
|
31956
31956
|
function createDeferredPromise() {
|
|
31957
31957
|
let res;
|
|
31958
31958
|
let rej;
|
|
31959
|
-
const promise = new Promise((
|
|
31960
|
-
res =
|
|
31959
|
+
const promise = new Promise((resolve15, reject) => {
|
|
31960
|
+
res = resolve15;
|
|
31961
31961
|
rej = reject;
|
|
31962
31962
|
});
|
|
31963
31963
|
return { promise, resolve: res, reject: rej };
|
|
@@ -33210,8 +33210,8 @@ var require_body = __commonJS({
|
|
|
33210
33210
|
var { parseMIMEType, serializeAMimeType } = require_dataURL();
|
|
33211
33211
|
var random;
|
|
33212
33212
|
try {
|
|
33213
|
-
const
|
|
33214
|
-
random = (max) =>
|
|
33213
|
+
const crypto7 = require("crypto");
|
|
33214
|
+
random = (max) => crypto7.randomInt(0, max);
|
|
33215
33215
|
} catch {
|
|
33216
33216
|
random = (max) => Math.floor(Math.random(max));
|
|
33217
33217
|
}
|
|
@@ -33462,8 +33462,8 @@ Content-Type: ${value.type || "application/octet-stream"}\r
|
|
|
33462
33462
|
});
|
|
33463
33463
|
}
|
|
33464
33464
|
});
|
|
33465
|
-
const busboyResolve = new Promise((
|
|
33466
|
-
busboy.on("finish",
|
|
33465
|
+
const busboyResolve = new Promise((resolve15, reject) => {
|
|
33466
|
+
busboy.on("finish", resolve15);
|
|
33467
33467
|
busboy.on("error", (err) => reject(new TypeError(err)));
|
|
33468
33468
|
});
|
|
33469
33469
|
if (this.body !== null) for await (const chunk of consumeBody(this[kState].body)) busboy.write(chunk);
|
|
@@ -33594,7 +33594,7 @@ var require_request = __commonJS({
|
|
|
33594
33594
|
}
|
|
33595
33595
|
var Request2 = class _Request {
|
|
33596
33596
|
constructor(origin, {
|
|
33597
|
-
path:
|
|
33597
|
+
path: path29,
|
|
33598
33598
|
method,
|
|
33599
33599
|
body,
|
|
33600
33600
|
headers,
|
|
@@ -33608,11 +33608,11 @@ var require_request = __commonJS({
|
|
|
33608
33608
|
throwOnError,
|
|
33609
33609
|
expectContinue
|
|
33610
33610
|
}, handler) {
|
|
33611
|
-
if (typeof
|
|
33611
|
+
if (typeof path29 !== "string") {
|
|
33612
33612
|
throw new InvalidArgumentError("path must be a string");
|
|
33613
|
-
} else if (
|
|
33613
|
+
} else if (path29[0] !== "/" && !(path29.startsWith("http://") || path29.startsWith("https://")) && method !== "CONNECT") {
|
|
33614
33614
|
throw new InvalidArgumentError("path must be an absolute URL or start with a slash");
|
|
33615
|
-
} else if (invalidPathRegex.exec(
|
|
33615
|
+
} else if (invalidPathRegex.exec(path29) !== null) {
|
|
33616
33616
|
throw new InvalidArgumentError("invalid request path");
|
|
33617
33617
|
}
|
|
33618
33618
|
if (typeof method !== "string") {
|
|
@@ -33675,7 +33675,7 @@ var require_request = __commonJS({
|
|
|
33675
33675
|
this.completed = false;
|
|
33676
33676
|
this.aborted = false;
|
|
33677
33677
|
this.upgrade = upgrade || null;
|
|
33678
|
-
this.path = query ? util.buildURL(
|
|
33678
|
+
this.path = query ? util.buildURL(path29, query) : path29;
|
|
33679
33679
|
this.origin = origin;
|
|
33680
33680
|
this.idempotent = idempotent == null ? method === "HEAD" || method === "GET" : idempotent;
|
|
33681
33681
|
this.blocking = blocking == null ? false : blocking;
|
|
@@ -33997,9 +33997,9 @@ var require_dispatcher_base = __commonJS({
|
|
|
33997
33997
|
}
|
|
33998
33998
|
close(callback) {
|
|
33999
33999
|
if (callback === void 0) {
|
|
34000
|
-
return new Promise((
|
|
34000
|
+
return new Promise((resolve15, reject) => {
|
|
34001
34001
|
this.close((err, data) => {
|
|
34002
|
-
return err ? reject(err) :
|
|
34002
|
+
return err ? reject(err) : resolve15(data);
|
|
34003
34003
|
});
|
|
34004
34004
|
});
|
|
34005
34005
|
}
|
|
@@ -34037,12 +34037,12 @@ var require_dispatcher_base = __commonJS({
|
|
|
34037
34037
|
err = null;
|
|
34038
34038
|
}
|
|
34039
34039
|
if (callback === void 0) {
|
|
34040
|
-
return new Promise((
|
|
34040
|
+
return new Promise((resolve15, reject) => {
|
|
34041
34041
|
this.destroy(err, (err2, data) => {
|
|
34042
34042
|
return err2 ? (
|
|
34043
34043
|
/* istanbul ignore next: should never error */
|
|
34044
34044
|
reject(err2)
|
|
34045
|
-
) :
|
|
34045
|
+
) : resolve15(data);
|
|
34046
34046
|
});
|
|
34047
34047
|
});
|
|
34048
34048
|
}
|
|
@@ -34683,9 +34683,9 @@ var require_RedirectHandler = __commonJS({
|
|
|
34683
34683
|
return this.handler.onHeaders(statusCode, headers, resume, statusText);
|
|
34684
34684
|
}
|
|
34685
34685
|
const { origin, pathname, search } = util.parseURL(new URL(this.location, this.opts.origin && new URL(this.opts.path, this.opts.origin)));
|
|
34686
|
-
const
|
|
34686
|
+
const path29 = search ? `${pathname}${search}` : pathname;
|
|
34687
34687
|
this.opts.headers = cleanRequestHeaders(this.opts.headers, statusCode === 303, this.opts.origin !== origin);
|
|
34688
|
-
this.opts.path =
|
|
34688
|
+
this.opts.path = path29;
|
|
34689
34689
|
this.opts.origin = origin;
|
|
34690
34690
|
this.opts.maxRedirections = 0;
|
|
34691
34691
|
this.opts.query = null;
|
|
@@ -35104,16 +35104,16 @@ var require_client = __commonJS({
|
|
|
35104
35104
|
return this[kNeedDrain] < 2;
|
|
35105
35105
|
}
|
|
35106
35106
|
async [kClose]() {
|
|
35107
|
-
return new Promise((
|
|
35107
|
+
return new Promise((resolve15) => {
|
|
35108
35108
|
if (!this[kSize]) {
|
|
35109
|
-
|
|
35109
|
+
resolve15(null);
|
|
35110
35110
|
} else {
|
|
35111
|
-
this[kClosedResolve] =
|
|
35111
|
+
this[kClosedResolve] = resolve15;
|
|
35112
35112
|
}
|
|
35113
35113
|
});
|
|
35114
35114
|
}
|
|
35115
35115
|
async [kDestroy](err) {
|
|
35116
|
-
return new Promise((
|
|
35116
|
+
return new Promise((resolve15) => {
|
|
35117
35117
|
const requests = this[kQueue].splice(this[kPendingIdx]);
|
|
35118
35118
|
for (let i = 0; i < requests.length; i++) {
|
|
35119
35119
|
const request = requests[i];
|
|
@@ -35124,7 +35124,7 @@ var require_client = __commonJS({
|
|
|
35124
35124
|
this[kClosedResolve]();
|
|
35125
35125
|
this[kClosedResolve] = null;
|
|
35126
35126
|
}
|
|
35127
|
-
|
|
35127
|
+
resolve15();
|
|
35128
35128
|
};
|
|
35129
35129
|
if (this[kHTTP2Session] != null) {
|
|
35130
35130
|
util.destroy(this[kHTTP2Session], err);
|
|
@@ -35704,7 +35704,7 @@ var require_client = __commonJS({
|
|
|
35704
35704
|
});
|
|
35705
35705
|
}
|
|
35706
35706
|
try {
|
|
35707
|
-
const socket = await new Promise((
|
|
35707
|
+
const socket = await new Promise((resolve15, reject) => {
|
|
35708
35708
|
client[kConnector]({
|
|
35709
35709
|
host,
|
|
35710
35710
|
hostname,
|
|
@@ -35716,7 +35716,7 @@ var require_client = __commonJS({
|
|
|
35716
35716
|
if (err) {
|
|
35717
35717
|
reject(err);
|
|
35718
35718
|
} else {
|
|
35719
|
-
|
|
35719
|
+
resolve15(socket2);
|
|
35720
35720
|
}
|
|
35721
35721
|
});
|
|
35722
35722
|
});
|
|
@@ -35927,7 +35927,7 @@ var require_client = __commonJS({
|
|
|
35927
35927
|
writeH2(client, client[kHTTP2Session], request);
|
|
35928
35928
|
return;
|
|
35929
35929
|
}
|
|
35930
|
-
const { body, method, path:
|
|
35930
|
+
const { body, method, path: path29, host, upgrade, headers, blocking, reset } = request;
|
|
35931
35931
|
const expectsPayload = method === "PUT" || method === "POST" || method === "PATCH";
|
|
35932
35932
|
if (body && typeof body.read === "function") {
|
|
35933
35933
|
body.read(0);
|
|
@@ -35977,7 +35977,7 @@ var require_client = __commonJS({
|
|
|
35977
35977
|
if (blocking) {
|
|
35978
35978
|
socket[kBlocking] = true;
|
|
35979
35979
|
}
|
|
35980
|
-
let header = `${method} ${
|
|
35980
|
+
let header = `${method} ${path29} HTTP/1.1\r
|
|
35981
35981
|
`;
|
|
35982
35982
|
if (typeof host === "string") {
|
|
35983
35983
|
header += `host: ${host}\r
|
|
@@ -36040,7 +36040,7 @@ upgrade: ${upgrade}\r
|
|
|
36040
36040
|
return true;
|
|
36041
36041
|
}
|
|
36042
36042
|
function writeH2(client, session, request) {
|
|
36043
|
-
const { body, method, path:
|
|
36043
|
+
const { body, method, path: path29, host, upgrade, expectContinue, signal, headers: reqHeaders } = request;
|
|
36044
36044
|
let headers;
|
|
36045
36045
|
if (typeof reqHeaders === "string") headers = Request2[kHTTP2CopyHeaders](reqHeaders.trim());
|
|
36046
36046
|
else headers = reqHeaders;
|
|
@@ -36083,7 +36083,7 @@ upgrade: ${upgrade}\r
|
|
|
36083
36083
|
});
|
|
36084
36084
|
return true;
|
|
36085
36085
|
}
|
|
36086
|
-
headers[HTTP2_HEADER_PATH] =
|
|
36086
|
+
headers[HTTP2_HEADER_PATH] = path29;
|
|
36087
36087
|
headers[HTTP2_HEADER_SCHEME] = "https";
|
|
36088
36088
|
const expectsPayload = method === "PUT" || method === "POST" || method === "PATCH";
|
|
36089
36089
|
if (body && typeof body.read === "function") {
|
|
@@ -36340,12 +36340,12 @@ upgrade: ${upgrade}\r
|
|
|
36340
36340
|
cb();
|
|
36341
36341
|
}
|
|
36342
36342
|
}
|
|
36343
|
-
const waitForDrain = () => new Promise((
|
|
36343
|
+
const waitForDrain = () => new Promise((resolve15, reject) => {
|
|
36344
36344
|
assert(callback === null);
|
|
36345
36345
|
if (socket[kError]) {
|
|
36346
36346
|
reject(socket[kError]);
|
|
36347
36347
|
} else {
|
|
36348
|
-
callback =
|
|
36348
|
+
callback = resolve15;
|
|
36349
36349
|
}
|
|
36350
36350
|
});
|
|
36351
36351
|
if (client[kHTTPConnVersion] === "h2") {
|
|
@@ -36691,8 +36691,8 @@ var require_pool_base = __commonJS({
|
|
|
36691
36691
|
if (this[kQueue].isEmpty()) {
|
|
36692
36692
|
return Promise.all(this[kClients].map((c) => c.close()));
|
|
36693
36693
|
} else {
|
|
36694
|
-
return new Promise((
|
|
36695
|
-
this[kClosedResolve] =
|
|
36694
|
+
return new Promise((resolve15) => {
|
|
36695
|
+
this[kClosedResolve] = resolve15;
|
|
36696
36696
|
});
|
|
36697
36697
|
}
|
|
36698
36698
|
}
|
|
@@ -37270,7 +37270,7 @@ var require_readable = __commonJS({
|
|
|
37270
37270
|
if (this.closed) {
|
|
37271
37271
|
return Promise.resolve(null);
|
|
37272
37272
|
}
|
|
37273
|
-
return new Promise((
|
|
37273
|
+
return new Promise((resolve15, reject) => {
|
|
37274
37274
|
const signalListenerCleanup = signal ? util.addAbortListener(signal, () => {
|
|
37275
37275
|
this.destroy();
|
|
37276
37276
|
}) : noop;
|
|
@@ -37279,7 +37279,7 @@ var require_readable = __commonJS({
|
|
|
37279
37279
|
if (signal && signal.aborted) {
|
|
37280
37280
|
reject(signal.reason || Object.assign(new Error("The operation was aborted"), { name: "AbortError" }));
|
|
37281
37281
|
} else {
|
|
37282
|
-
|
|
37282
|
+
resolve15(null);
|
|
37283
37283
|
}
|
|
37284
37284
|
}).on("error", noop).on("data", function(chunk) {
|
|
37285
37285
|
limit -= chunk.length;
|
|
@@ -37301,11 +37301,11 @@ var require_readable = __commonJS({
|
|
|
37301
37301
|
throw new TypeError("unusable");
|
|
37302
37302
|
}
|
|
37303
37303
|
assert(!stream[kConsume]);
|
|
37304
|
-
return new Promise((
|
|
37304
|
+
return new Promise((resolve15, reject) => {
|
|
37305
37305
|
stream[kConsume] = {
|
|
37306
37306
|
type,
|
|
37307
37307
|
stream,
|
|
37308
|
-
resolve:
|
|
37308
|
+
resolve: resolve15,
|
|
37309
37309
|
reject,
|
|
37310
37310
|
length: 0,
|
|
37311
37311
|
body: []
|
|
@@ -37340,12 +37340,12 @@ var require_readable = __commonJS({
|
|
|
37340
37340
|
}
|
|
37341
37341
|
}
|
|
37342
37342
|
function consumeEnd(consume2) {
|
|
37343
|
-
const { type, body, resolve:
|
|
37343
|
+
const { type, body, resolve: resolve15, stream, length } = consume2;
|
|
37344
37344
|
try {
|
|
37345
37345
|
if (type === "text") {
|
|
37346
|
-
|
|
37346
|
+
resolve15(toUSVString(Buffer.concat(body)));
|
|
37347
37347
|
} else if (type === "json") {
|
|
37348
|
-
|
|
37348
|
+
resolve15(JSON.parse(Buffer.concat(body)));
|
|
37349
37349
|
} else if (type === "arrayBuffer") {
|
|
37350
37350
|
const dst = new Uint8Array(length);
|
|
37351
37351
|
let pos = 0;
|
|
@@ -37353,12 +37353,12 @@ var require_readable = __commonJS({
|
|
|
37353
37353
|
dst.set(buf, pos);
|
|
37354
37354
|
pos += buf.byteLength;
|
|
37355
37355
|
}
|
|
37356
|
-
|
|
37356
|
+
resolve15(dst.buffer);
|
|
37357
37357
|
} else if (type === "blob") {
|
|
37358
37358
|
if (!Blob2) {
|
|
37359
37359
|
Blob2 = require("buffer").Blob;
|
|
37360
37360
|
}
|
|
37361
|
-
|
|
37361
|
+
resolve15(new Blob2(body, { type: stream[kContentType] }));
|
|
37362
37362
|
}
|
|
37363
37363
|
consumeFinish(consume2);
|
|
37364
37364
|
} catch (err) {
|
|
@@ -37615,9 +37615,9 @@ var require_api_request = __commonJS({
|
|
|
37615
37615
|
};
|
|
37616
37616
|
function request(opts, callback) {
|
|
37617
37617
|
if (callback === void 0) {
|
|
37618
|
-
return new Promise((
|
|
37618
|
+
return new Promise((resolve15, reject) => {
|
|
37619
37619
|
request.call(this, opts, (err, data) => {
|
|
37620
|
-
return err ? reject(err) :
|
|
37620
|
+
return err ? reject(err) : resolve15(data);
|
|
37621
37621
|
});
|
|
37622
37622
|
});
|
|
37623
37623
|
}
|
|
@@ -37790,9 +37790,9 @@ var require_api_stream = __commonJS({
|
|
|
37790
37790
|
};
|
|
37791
37791
|
function stream(opts, factory, callback) {
|
|
37792
37792
|
if (callback === void 0) {
|
|
37793
|
-
return new Promise((
|
|
37793
|
+
return new Promise((resolve15, reject) => {
|
|
37794
37794
|
stream.call(this, opts, factory, (err, data) => {
|
|
37795
|
-
return err ? reject(err) :
|
|
37795
|
+
return err ? reject(err) : resolve15(data);
|
|
37796
37796
|
});
|
|
37797
37797
|
});
|
|
37798
37798
|
}
|
|
@@ -38073,9 +38073,9 @@ var require_api_upgrade = __commonJS({
|
|
|
38073
38073
|
};
|
|
38074
38074
|
function upgrade(opts, callback) {
|
|
38075
38075
|
if (callback === void 0) {
|
|
38076
|
-
return new Promise((
|
|
38076
|
+
return new Promise((resolve15, reject) => {
|
|
38077
38077
|
upgrade.call(this, opts, (err, data) => {
|
|
38078
|
-
return err ? reject(err) :
|
|
38078
|
+
return err ? reject(err) : resolve15(data);
|
|
38079
38079
|
});
|
|
38080
38080
|
});
|
|
38081
38081
|
}
|
|
@@ -38164,9 +38164,9 @@ var require_api_connect = __commonJS({
|
|
|
38164
38164
|
};
|
|
38165
38165
|
function connect(opts, callback) {
|
|
38166
38166
|
if (callback === void 0) {
|
|
38167
|
-
return new Promise((
|
|
38167
|
+
return new Promise((resolve15, reject) => {
|
|
38168
38168
|
connect.call(this, opts, (err, data) => {
|
|
38169
|
-
return err ? reject(err) :
|
|
38169
|
+
return err ? reject(err) : resolve15(data);
|
|
38170
38170
|
});
|
|
38171
38171
|
});
|
|
38172
38172
|
}
|
|
@@ -38326,20 +38326,20 @@ var require_mock_utils = __commonJS({
|
|
|
38326
38326
|
}
|
|
38327
38327
|
return true;
|
|
38328
38328
|
}
|
|
38329
|
-
function safeUrl(
|
|
38330
|
-
if (typeof
|
|
38331
|
-
return
|
|
38329
|
+
function safeUrl(path29) {
|
|
38330
|
+
if (typeof path29 !== "string") {
|
|
38331
|
+
return path29;
|
|
38332
38332
|
}
|
|
38333
|
-
const pathSegments =
|
|
38333
|
+
const pathSegments = path29.split("?");
|
|
38334
38334
|
if (pathSegments.length !== 2) {
|
|
38335
|
-
return
|
|
38335
|
+
return path29;
|
|
38336
38336
|
}
|
|
38337
38337
|
const qp = new URLSearchParams(pathSegments.pop());
|
|
38338
38338
|
qp.sort();
|
|
38339
38339
|
return [...pathSegments, qp.toString()].join("?");
|
|
38340
38340
|
}
|
|
38341
|
-
function matchKey(mockDispatch2, { path:
|
|
38342
|
-
const pathMatch = matchValue(mockDispatch2.path,
|
|
38341
|
+
function matchKey(mockDispatch2, { path: path29, method, body, headers }) {
|
|
38342
|
+
const pathMatch = matchValue(mockDispatch2.path, path29);
|
|
38343
38343
|
const methodMatch = matchValue(mockDispatch2.method, method);
|
|
38344
38344
|
const bodyMatch = typeof mockDispatch2.body !== "undefined" ? matchValue(mockDispatch2.body, body) : true;
|
|
38345
38345
|
const headersMatch = matchHeaders(mockDispatch2, headers);
|
|
@@ -38357,7 +38357,7 @@ var require_mock_utils = __commonJS({
|
|
|
38357
38357
|
function getMockDispatch(mockDispatches, key) {
|
|
38358
38358
|
const basePath = key.query ? buildURL(key.path, key.query) : key.path;
|
|
38359
38359
|
const resolvedPath = typeof basePath === "string" ? safeUrl(basePath) : basePath;
|
|
38360
|
-
let matchedMockDispatches = mockDispatches.filter(({ consumed }) => !consumed).filter(({ path:
|
|
38360
|
+
let matchedMockDispatches = mockDispatches.filter(({ consumed }) => !consumed).filter(({ path: path29 }) => matchValue(safeUrl(path29), resolvedPath));
|
|
38361
38361
|
if (matchedMockDispatches.length === 0) {
|
|
38362
38362
|
throw new MockNotMatchedError(`Mock dispatch not matched for path '${resolvedPath}'`);
|
|
38363
38363
|
}
|
|
@@ -38394,9 +38394,9 @@ var require_mock_utils = __commonJS({
|
|
|
38394
38394
|
}
|
|
38395
38395
|
}
|
|
38396
38396
|
function buildKey(opts) {
|
|
38397
|
-
const { path:
|
|
38397
|
+
const { path: path29, method, body, headers, query } = opts;
|
|
38398
38398
|
return {
|
|
38399
|
-
path:
|
|
38399
|
+
path: path29,
|
|
38400
38400
|
method,
|
|
38401
38401
|
body,
|
|
38402
38402
|
headers,
|
|
@@ -38845,10 +38845,10 @@ var require_pending_interceptors_formatter = __commonJS({
|
|
|
38845
38845
|
}
|
|
38846
38846
|
format(pendingInterceptors) {
|
|
38847
38847
|
const withPrettyHeaders = pendingInterceptors.map(
|
|
38848
|
-
({ method, path:
|
|
38848
|
+
({ method, path: path29, data: { statusCode }, persist, times, timesInvoked, origin }) => ({
|
|
38849
38849
|
Method: method,
|
|
38850
38850
|
Origin: origin,
|
|
38851
|
-
Path:
|
|
38851
|
+
Path: path29,
|
|
38852
38852
|
"Status code": statusCode,
|
|
38853
38853
|
Persistent: persist ? "\u2705" : "\u274C",
|
|
38854
38854
|
Invocations: timesInvoked,
|
|
@@ -41789,7 +41789,7 @@ var require_fetch = __commonJS({
|
|
|
41789
41789
|
async function dispatch({ body }) {
|
|
41790
41790
|
const url = requestCurrentURL(request);
|
|
41791
41791
|
const agent = fetchParams.controller.dispatcher;
|
|
41792
|
-
return new Promise((
|
|
41792
|
+
return new Promise((resolve15, reject) => agent.dispatch(
|
|
41793
41793
|
{
|
|
41794
41794
|
path: url.pathname + url.search,
|
|
41795
41795
|
origin: url.origin,
|
|
@@ -41865,7 +41865,7 @@ var require_fetch = __commonJS({
|
|
|
41865
41865
|
}
|
|
41866
41866
|
}
|
|
41867
41867
|
}
|
|
41868
|
-
|
|
41868
|
+
resolve15({
|
|
41869
41869
|
status,
|
|
41870
41870
|
statusText,
|
|
41871
41871
|
headersList: headers[kHeadersList],
|
|
@@ -41908,7 +41908,7 @@ var require_fetch = __commonJS({
|
|
|
41908
41908
|
const val = headersList[n + 1].toString("latin1");
|
|
41909
41909
|
headers[kHeadersList].append(key, val);
|
|
41910
41910
|
}
|
|
41911
|
-
|
|
41911
|
+
resolve15({
|
|
41912
41912
|
status,
|
|
41913
41913
|
statusText: STATUS_CODES[status],
|
|
41914
41914
|
headersList: headers[kHeadersList],
|
|
@@ -43469,8 +43469,8 @@ var require_util6 = __commonJS({
|
|
|
43469
43469
|
}
|
|
43470
43470
|
}
|
|
43471
43471
|
}
|
|
43472
|
-
function validateCookiePath(
|
|
43473
|
-
for (const char of
|
|
43472
|
+
function validateCookiePath(path29) {
|
|
43473
|
+
for (const char of path29) {
|
|
43474
43474
|
const code = char.charCodeAt(0);
|
|
43475
43475
|
if (code < 33 || char === ";") {
|
|
43476
43476
|
throw new Error("Invalid cookie path");
|
|
@@ -44267,9 +44267,9 @@ var require_connection = __commonJS({
|
|
|
44267
44267
|
channels.open = diagnosticsChannel.channel("undici:websocket:open");
|
|
44268
44268
|
channels.close = diagnosticsChannel.channel("undici:websocket:close");
|
|
44269
44269
|
channels.socketError = diagnosticsChannel.channel("undici:websocket:socket_error");
|
|
44270
|
-
var
|
|
44270
|
+
var crypto7;
|
|
44271
44271
|
try {
|
|
44272
|
-
|
|
44272
|
+
crypto7 = require("crypto");
|
|
44273
44273
|
} catch {
|
|
44274
44274
|
}
|
|
44275
44275
|
function establishWebSocketConnection(url, protocols, ws, onEstablish, options) {
|
|
@@ -44288,7 +44288,7 @@ var require_connection = __commonJS({
|
|
|
44288
44288
|
const headersList = new Headers(options.headers)[kHeadersList];
|
|
44289
44289
|
request.headersList = headersList;
|
|
44290
44290
|
}
|
|
44291
|
-
const keyValue =
|
|
44291
|
+
const keyValue = crypto7.randomBytes(16).toString("base64");
|
|
44292
44292
|
request.headersList.append("sec-websocket-key", keyValue);
|
|
44293
44293
|
request.headersList.append("sec-websocket-version", "13");
|
|
44294
44294
|
for (const protocol of protocols) {
|
|
@@ -44317,7 +44317,7 @@ var require_connection = __commonJS({
|
|
|
44317
44317
|
return;
|
|
44318
44318
|
}
|
|
44319
44319
|
const secWSAccept = response.headersList.get("Sec-WebSocket-Accept");
|
|
44320
|
-
const digest =
|
|
44320
|
+
const digest = crypto7.createHash("sha1").update(keyValue + uid).digest("base64");
|
|
44321
44321
|
if (secWSAccept !== digest) {
|
|
44322
44322
|
failWebsocketConnection(ws, "Incorrect hash received in Sec-WebSocket-Accept header.");
|
|
44323
44323
|
return;
|
|
@@ -44397,9 +44397,9 @@ var require_frame = __commonJS({
|
|
|
44397
44397
|
"node_modules/undici/lib/websocket/frame.js"(exports2, module2) {
|
|
44398
44398
|
"use strict";
|
|
44399
44399
|
var { maxUnsigned16Bit } = require_constants5();
|
|
44400
|
-
var
|
|
44400
|
+
var crypto7;
|
|
44401
44401
|
try {
|
|
44402
|
-
|
|
44402
|
+
crypto7 = require("crypto");
|
|
44403
44403
|
} catch {
|
|
44404
44404
|
}
|
|
44405
44405
|
var WebsocketFrameSend = class {
|
|
@@ -44408,7 +44408,7 @@ var require_frame = __commonJS({
|
|
|
44408
44408
|
*/
|
|
44409
44409
|
constructor(data) {
|
|
44410
44410
|
this.frameData = data;
|
|
44411
|
-
this.maskKey =
|
|
44411
|
+
this.maskKey = crypto7.randomBytes(4);
|
|
44412
44412
|
}
|
|
44413
44413
|
createFrame(opcode) {
|
|
44414
44414
|
const bodyLength = this.frameData?.byteLength ?? 0;
|
|
@@ -45150,11 +45150,11 @@ var require_undici = __commonJS({
|
|
|
45150
45150
|
if (typeof opts.path !== "string") {
|
|
45151
45151
|
throw new InvalidArgumentError("invalid opts.path");
|
|
45152
45152
|
}
|
|
45153
|
-
let
|
|
45153
|
+
let path29 = opts.path;
|
|
45154
45154
|
if (!opts.path.startsWith("/")) {
|
|
45155
|
-
|
|
45155
|
+
path29 = `/${path29}`;
|
|
45156
45156
|
}
|
|
45157
|
-
url = new URL(util.parseOrigin(url).origin +
|
|
45157
|
+
url = new URL(util.parseOrigin(url).origin + path29);
|
|
45158
45158
|
} else {
|
|
45159
45159
|
if (!opts) {
|
|
45160
45160
|
opts = typeof url === "object" ? url : {};
|
|
@@ -45723,7 +45723,7 @@ var init_mcp_check_provider = __esm({
|
|
|
45723
45723
|
logger.warn(
|
|
45724
45724
|
`MCP ${transportName} failed (attempt ${attempt + 1}/${maxRetries + 1}), retrying in ${delay}ms: ${error instanceof Error ? error.message : String(error)}`
|
|
45725
45725
|
);
|
|
45726
|
-
await new Promise((
|
|
45726
|
+
await new Promise((resolve15) => setTimeout(resolve15, delay));
|
|
45727
45727
|
attempt += 1;
|
|
45728
45728
|
} finally {
|
|
45729
45729
|
try {
|
|
@@ -46016,7 +46016,7 @@ async function acquirePromptLock() {
|
|
|
46016
46016
|
);
|
|
46017
46017
|
}, 1e4);
|
|
46018
46018
|
try {
|
|
46019
|
-
await new Promise((
|
|
46019
|
+
await new Promise((resolve15) => waiters.push(resolve15));
|
|
46020
46020
|
} finally {
|
|
46021
46021
|
clearInterval(reminder);
|
|
46022
46022
|
const waitedMs = Date.now() - queuedAt;
|
|
@@ -46035,7 +46035,7 @@ function releasePromptLock() {
|
|
|
46035
46035
|
}
|
|
46036
46036
|
async function interactivePrompt(options) {
|
|
46037
46037
|
await acquirePromptLock();
|
|
46038
|
-
return new Promise((
|
|
46038
|
+
return new Promise((resolve15, reject) => {
|
|
46039
46039
|
const dbg = process.env.VISOR_DEBUG === "true";
|
|
46040
46040
|
try {
|
|
46041
46041
|
if (dbg) {
|
|
@@ -46122,12 +46122,12 @@ async function interactivePrompt(options) {
|
|
|
46122
46122
|
};
|
|
46123
46123
|
const finish = (value) => {
|
|
46124
46124
|
cleanup();
|
|
46125
|
-
|
|
46125
|
+
resolve15(value);
|
|
46126
46126
|
};
|
|
46127
46127
|
if (options.timeout && options.timeout > 0) {
|
|
46128
46128
|
timeoutId = setTimeout(() => {
|
|
46129
46129
|
cleanup();
|
|
46130
|
-
if (defaultValue !== void 0) return
|
|
46130
|
+
if (defaultValue !== void 0) return resolve15(defaultValue);
|
|
46131
46131
|
return reject(new Error("Input timeout"));
|
|
46132
46132
|
}, options.timeout);
|
|
46133
46133
|
}
|
|
@@ -46259,7 +46259,7 @@ async function interactivePrompt(options) {
|
|
|
46259
46259
|
});
|
|
46260
46260
|
}
|
|
46261
46261
|
async function simplePrompt(prompt) {
|
|
46262
|
-
return new Promise((
|
|
46262
|
+
return new Promise((resolve15) => {
|
|
46263
46263
|
const rl = readline.createInterface({
|
|
46264
46264
|
input: process.stdin,
|
|
46265
46265
|
output: process.stdout
|
|
@@ -46275,7 +46275,7 @@ async function simplePrompt(prompt) {
|
|
|
46275
46275
|
rl.question(`${prompt}
|
|
46276
46276
|
> `, (answer) => {
|
|
46277
46277
|
rl.close();
|
|
46278
|
-
|
|
46278
|
+
resolve15(answer.trim());
|
|
46279
46279
|
});
|
|
46280
46280
|
});
|
|
46281
46281
|
}
|
|
@@ -46443,7 +46443,7 @@ function isStdinAvailable() {
|
|
|
46443
46443
|
return !process.stdin.isTTY;
|
|
46444
46444
|
}
|
|
46445
46445
|
async function readStdin(timeout, maxSize = 1024 * 1024) {
|
|
46446
|
-
return new Promise((
|
|
46446
|
+
return new Promise((resolve15, reject) => {
|
|
46447
46447
|
let data = "";
|
|
46448
46448
|
let timeoutId;
|
|
46449
46449
|
if (timeout) {
|
|
@@ -46470,7 +46470,7 @@ async function readStdin(timeout, maxSize = 1024 * 1024) {
|
|
|
46470
46470
|
};
|
|
46471
46471
|
const onEnd = () => {
|
|
46472
46472
|
cleanup();
|
|
46473
|
-
|
|
46473
|
+
resolve15(data.trim());
|
|
46474
46474
|
};
|
|
46475
46475
|
const onError = (err) => {
|
|
46476
46476
|
cleanup();
|
|
@@ -51170,23 +51170,23 @@ __export(renderer_schema_exports, {
|
|
|
51170
51170
|
});
|
|
51171
51171
|
async function loadRendererSchema(name) {
|
|
51172
51172
|
try {
|
|
51173
|
-
const
|
|
51174
|
-
const
|
|
51173
|
+
const fs25 = await import("fs/promises");
|
|
51174
|
+
const path29 = await import("path");
|
|
51175
51175
|
const sanitized = String(name).replace(/[^a-zA-Z0-9-]/g, "");
|
|
51176
51176
|
if (!sanitized) return void 0;
|
|
51177
51177
|
const candidates = [
|
|
51178
51178
|
// When bundled with ncc, __dirname is dist/ and output/ is at dist/output/
|
|
51179
|
-
|
|
51179
|
+
path29.join(__dirname, "output", sanitized, "schema.json"),
|
|
51180
51180
|
// When running from source, __dirname is src/state-machine/dispatch/ and output/ is at output/
|
|
51181
|
-
|
|
51181
|
+
path29.join(__dirname, "..", "..", "output", sanitized, "schema.json"),
|
|
51182
51182
|
// When running from a checkout with output/ folder copied to CWD
|
|
51183
|
-
|
|
51183
|
+
path29.join(process.cwd(), "output", sanitized, "schema.json"),
|
|
51184
51184
|
// Fallback: cwd/dist/output/
|
|
51185
|
-
|
|
51185
|
+
path29.join(process.cwd(), "dist", "output", sanitized, "schema.json")
|
|
51186
51186
|
];
|
|
51187
51187
|
for (const p of candidates) {
|
|
51188
51188
|
try {
|
|
51189
|
-
const raw = await
|
|
51189
|
+
const raw = await fs25.readFile(p, "utf-8");
|
|
51190
51190
|
return JSON.parse(raw);
|
|
51191
51191
|
} catch {
|
|
51192
51192
|
}
|
|
@@ -53631,8 +53631,8 @@ function updateStats2(results, state, isForEachIteration = false) {
|
|
|
53631
53631
|
async function renderTemplateContent2(checkId, checkConfig, reviewSummary) {
|
|
53632
53632
|
try {
|
|
53633
53633
|
const { createExtendedLiquid: createExtendedLiquid2 } = await Promise.resolve().then(() => (init_liquid_extensions(), liquid_extensions_exports));
|
|
53634
|
-
const
|
|
53635
|
-
const
|
|
53634
|
+
const fs25 = await import("fs/promises");
|
|
53635
|
+
const path29 = await import("path");
|
|
53636
53636
|
const schemaRaw = checkConfig.schema || "plain";
|
|
53637
53637
|
const schema = typeof schemaRaw === "string" && !schemaRaw.includes("{{") && !schemaRaw.includes("{%") ? schemaRaw : typeof schemaRaw === "object" ? "code-review" : "plain";
|
|
53638
53638
|
let templateContent;
|
|
@@ -53641,27 +53641,27 @@ async function renderTemplateContent2(checkId, checkConfig, reviewSummary) {
|
|
|
53641
53641
|
logger.debug(`[LevelDispatch] Using inline template for ${checkId}`);
|
|
53642
53642
|
} else if (checkConfig.template && checkConfig.template.file) {
|
|
53643
53643
|
const file = String(checkConfig.template.file);
|
|
53644
|
-
const resolved =
|
|
53645
|
-
templateContent = await
|
|
53644
|
+
const resolved = path29.resolve(process.cwd(), file);
|
|
53645
|
+
templateContent = await fs25.readFile(resolved, "utf-8");
|
|
53646
53646
|
logger.debug(`[LevelDispatch] Using template file for ${checkId}: ${resolved}`);
|
|
53647
53647
|
} else if (schema && schema !== "plain") {
|
|
53648
53648
|
const sanitized = String(schema).replace(/[^a-zA-Z0-9-]/g, "");
|
|
53649
53649
|
if (sanitized) {
|
|
53650
53650
|
const candidatePaths = [
|
|
53651
|
-
|
|
53651
|
+
path29.join(__dirname, "output", sanitized, "template.liquid"),
|
|
53652
53652
|
// bundled: dist/output/
|
|
53653
|
-
|
|
53653
|
+
path29.join(__dirname, "..", "..", "output", sanitized, "template.liquid"),
|
|
53654
53654
|
// source (from state-machine/states)
|
|
53655
|
-
|
|
53655
|
+
path29.join(__dirname, "..", "..", "..", "output", sanitized, "template.liquid"),
|
|
53656
53656
|
// source (alternate)
|
|
53657
|
-
|
|
53657
|
+
path29.join(process.cwd(), "output", sanitized, "template.liquid"),
|
|
53658
53658
|
// fallback: cwd/output/
|
|
53659
|
-
|
|
53659
|
+
path29.join(process.cwd(), "dist", "output", sanitized, "template.liquid")
|
|
53660
53660
|
// fallback: cwd/dist/output/
|
|
53661
53661
|
];
|
|
53662
53662
|
for (const p of candidatePaths) {
|
|
53663
53663
|
try {
|
|
53664
|
-
templateContent = await
|
|
53664
|
+
templateContent = await fs25.readFile(p, "utf-8");
|
|
53665
53665
|
if (templateContent) {
|
|
53666
53666
|
logger.debug(`[LevelDispatch] Using schema template for ${checkId}: ${p}`);
|
|
53667
53667
|
break;
|
|
@@ -55801,8 +55801,8 @@ var init_workspace_manager = __esm({
|
|
|
55801
55801
|
);
|
|
55802
55802
|
if (this.cleanupRequested && this.activeOperations === 0) {
|
|
55803
55803
|
logger.debug(`[Workspace] All references released, proceeding with deferred cleanup`);
|
|
55804
|
-
for (const
|
|
55805
|
-
|
|
55804
|
+
for (const resolve15 of this.cleanupResolvers) {
|
|
55805
|
+
resolve15();
|
|
55806
55806
|
}
|
|
55807
55807
|
this.cleanupResolvers = [];
|
|
55808
55808
|
}
|
|
@@ -55981,19 +55981,19 @@ var init_workspace_manager = __esm({
|
|
|
55981
55981
|
);
|
|
55982
55982
|
this.cleanupRequested = true;
|
|
55983
55983
|
await Promise.race([
|
|
55984
|
-
new Promise((
|
|
55984
|
+
new Promise((resolve15) => {
|
|
55985
55985
|
if (this.activeOperations === 0) {
|
|
55986
|
-
|
|
55986
|
+
resolve15();
|
|
55987
55987
|
} else {
|
|
55988
|
-
this.cleanupResolvers.push(
|
|
55988
|
+
this.cleanupResolvers.push(resolve15);
|
|
55989
55989
|
}
|
|
55990
55990
|
}),
|
|
55991
|
-
new Promise((
|
|
55991
|
+
new Promise((resolve15) => {
|
|
55992
55992
|
setTimeout(() => {
|
|
55993
55993
|
logger.warn(
|
|
55994
55994
|
`[Workspace] Cleanup timeout after ${timeout}ms, proceeding anyway (${this.activeOperations} operations still active)`
|
|
55995
55995
|
);
|
|
55996
|
-
|
|
55996
|
+
resolve15();
|
|
55997
55997
|
}, timeout);
|
|
55998
55998
|
})
|
|
55999
55999
|
]);
|
|
@@ -56387,8 +56387,8 @@ var init_fair_concurrency_limiter = __esm({
|
|
|
56387
56387
|
);
|
|
56388
56388
|
const queuedAt = Date.now();
|
|
56389
56389
|
const effectiveTimeout = queueTimeout ?? 12e4;
|
|
56390
|
-
return new Promise((
|
|
56391
|
-
const entry = { resolve:
|
|
56390
|
+
return new Promise((resolve15, reject) => {
|
|
56391
|
+
const entry = { resolve: resolve15, reject, queuedAt };
|
|
56392
56392
|
entry.reminder = setInterval(() => {
|
|
56393
56393
|
const waited = Math.round((Date.now() - queuedAt) / 1e3);
|
|
56394
56394
|
const curQueued = this._totalQueued();
|
|
@@ -56695,1380 +56695,6 @@ var init_build_engine_context = __esm({
|
|
|
56695
56695
|
}
|
|
56696
56696
|
});
|
|
56697
56697
|
|
|
56698
|
-
// src/policy/default-engine.ts
|
|
56699
|
-
var DefaultPolicyEngine;
|
|
56700
|
-
var init_default_engine = __esm({
|
|
56701
|
-
"src/policy/default-engine.ts"() {
|
|
56702
|
-
"use strict";
|
|
56703
|
-
DefaultPolicyEngine = class {
|
|
56704
|
-
async initialize(_config) {
|
|
56705
|
-
}
|
|
56706
|
-
async evaluateCheckExecution(_checkId, _checkConfig) {
|
|
56707
|
-
return { allowed: true };
|
|
56708
|
-
}
|
|
56709
|
-
async evaluateToolInvocation(_serverName, _methodName, _transport) {
|
|
56710
|
-
return { allowed: true };
|
|
56711
|
-
}
|
|
56712
|
-
async evaluateCapabilities(_checkId, _capabilities) {
|
|
56713
|
-
return { allowed: true };
|
|
56714
|
-
}
|
|
56715
|
-
async shutdown() {
|
|
56716
|
-
}
|
|
56717
|
-
};
|
|
56718
|
-
}
|
|
56719
|
-
});
|
|
56720
|
-
|
|
56721
|
-
// src/enterprise/license/validator.ts
|
|
56722
|
-
var validator_exports = {};
|
|
56723
|
-
__export(validator_exports, {
|
|
56724
|
-
LicenseValidator: () => LicenseValidator
|
|
56725
|
-
});
|
|
56726
|
-
var crypto3, fs21, path26, LicenseValidator;
|
|
56727
|
-
var init_validator = __esm({
|
|
56728
|
-
"src/enterprise/license/validator.ts"() {
|
|
56729
|
-
"use strict";
|
|
56730
|
-
crypto3 = __toESM(require("crypto"));
|
|
56731
|
-
fs21 = __toESM(require("fs"));
|
|
56732
|
-
path26 = __toESM(require("path"));
|
|
56733
|
-
LicenseValidator = class _LicenseValidator {
|
|
56734
|
-
/** Ed25519 public key for license verification (PEM format). */
|
|
56735
|
-
static PUBLIC_KEY = "-----BEGIN PUBLIC KEY-----\nMCowBQYDK2VwAyEAI/Zd08EFmgIdrDm/HXd0l3/5GBt7R1PrdvhdmEXhJlU=\n-----END PUBLIC KEY-----\n";
|
|
56736
|
-
cache = null;
|
|
56737
|
-
static CACHE_TTL = 5 * 60 * 1e3;
|
|
56738
|
-
// 5 minutes
|
|
56739
|
-
static GRACE_PERIOD = 72 * 3600 * 1e3;
|
|
56740
|
-
// 72 hours after expiry
|
|
56741
|
-
/**
|
|
56742
|
-
* Load and validate license from environment or file.
|
|
56743
|
-
*
|
|
56744
|
-
* Resolution order:
|
|
56745
|
-
* 1. VISOR_LICENSE env var (JWT string)
|
|
56746
|
-
* 2. VISOR_LICENSE_FILE env var (path to file)
|
|
56747
|
-
* 3. .visor-license in project root (cwd)
|
|
56748
|
-
* 4. .visor-license in ~/.config/visor/
|
|
56749
|
-
*/
|
|
56750
|
-
async loadAndValidate() {
|
|
56751
|
-
if (this.cache && Date.now() - this.cache.validatedAt < _LicenseValidator.CACHE_TTL) {
|
|
56752
|
-
return this.cache.payload;
|
|
56753
|
-
}
|
|
56754
|
-
const token = this.resolveToken();
|
|
56755
|
-
if (!token) return null;
|
|
56756
|
-
const payload = this.verifyAndDecode(token);
|
|
56757
|
-
if (!payload) return null;
|
|
56758
|
-
this.cache = { payload, validatedAt: Date.now() };
|
|
56759
|
-
return payload;
|
|
56760
|
-
}
|
|
56761
|
-
/** Check if a specific feature is licensed */
|
|
56762
|
-
hasFeature(feature) {
|
|
56763
|
-
if (!this.cache) return false;
|
|
56764
|
-
return this.cache.payload.features.includes(feature);
|
|
56765
|
-
}
|
|
56766
|
-
/** Check if license is valid (with grace period) */
|
|
56767
|
-
isValid() {
|
|
56768
|
-
if (!this.cache) return false;
|
|
56769
|
-
const now = Date.now();
|
|
56770
|
-
const expiryMs = this.cache.payload.exp * 1e3;
|
|
56771
|
-
return now < expiryMs + _LicenseValidator.GRACE_PERIOD;
|
|
56772
|
-
}
|
|
56773
|
-
/** Check if the license is within its grace period (expired but still valid) */
|
|
56774
|
-
isInGracePeriod() {
|
|
56775
|
-
if (!this.cache) return false;
|
|
56776
|
-
const now = Date.now();
|
|
56777
|
-
const expiryMs = this.cache.payload.exp * 1e3;
|
|
56778
|
-
return now >= expiryMs && now < expiryMs + _LicenseValidator.GRACE_PERIOD;
|
|
56779
|
-
}
|
|
56780
|
-
resolveToken() {
|
|
56781
|
-
if (process.env.VISOR_LICENSE) {
|
|
56782
|
-
return process.env.VISOR_LICENSE.trim();
|
|
56783
|
-
}
|
|
56784
|
-
if (process.env.VISOR_LICENSE_FILE) {
|
|
56785
|
-
const resolved = path26.resolve(process.env.VISOR_LICENSE_FILE);
|
|
56786
|
-
const home2 = process.env.HOME || process.env.USERPROFILE || "";
|
|
56787
|
-
const allowedPrefixes = [path26.normalize(process.cwd())];
|
|
56788
|
-
if (home2) allowedPrefixes.push(path26.normalize(path26.join(home2, ".config", "visor")));
|
|
56789
|
-
let realPath;
|
|
56790
|
-
try {
|
|
56791
|
-
realPath = fs21.realpathSync(resolved);
|
|
56792
|
-
} catch {
|
|
56793
|
-
return null;
|
|
56794
|
-
}
|
|
56795
|
-
const isSafe = allowedPrefixes.some(
|
|
56796
|
-
(prefix) => realPath === prefix || realPath.startsWith(prefix + path26.sep)
|
|
56797
|
-
);
|
|
56798
|
-
if (!isSafe) return null;
|
|
56799
|
-
return this.readFile(realPath);
|
|
56800
|
-
}
|
|
56801
|
-
const cwdPath = path26.join(process.cwd(), ".visor-license");
|
|
56802
|
-
const cwdToken = this.readFile(cwdPath);
|
|
56803
|
-
if (cwdToken) return cwdToken;
|
|
56804
|
-
const home = process.env.HOME || process.env.USERPROFILE || "";
|
|
56805
|
-
if (home) {
|
|
56806
|
-
const configPath = path26.join(home, ".config", "visor", ".visor-license");
|
|
56807
|
-
const configToken = this.readFile(configPath);
|
|
56808
|
-
if (configToken) return configToken;
|
|
56809
|
-
}
|
|
56810
|
-
return null;
|
|
56811
|
-
}
|
|
56812
|
-
readFile(filePath) {
|
|
56813
|
-
try {
|
|
56814
|
-
return fs21.readFileSync(filePath, "utf-8").trim();
|
|
56815
|
-
} catch {
|
|
56816
|
-
return null;
|
|
56817
|
-
}
|
|
56818
|
-
}
|
|
56819
|
-
verifyAndDecode(token) {
|
|
56820
|
-
try {
|
|
56821
|
-
const parts = token.split(".");
|
|
56822
|
-
if (parts.length !== 3) return null;
|
|
56823
|
-
const [headerB64, payloadB64, signatureB64] = parts;
|
|
56824
|
-
const header = JSON.parse(Buffer.from(headerB64, "base64url").toString());
|
|
56825
|
-
if (header.alg !== "EdDSA") return null;
|
|
56826
|
-
const data = `${headerB64}.${payloadB64}`;
|
|
56827
|
-
const signature = Buffer.from(signatureB64, "base64url");
|
|
56828
|
-
const publicKey = crypto3.createPublicKey(_LicenseValidator.PUBLIC_KEY);
|
|
56829
|
-
if (publicKey.asymmetricKeyType !== "ed25519") {
|
|
56830
|
-
return null;
|
|
56831
|
-
}
|
|
56832
|
-
const isValid = crypto3.verify(null, Buffer.from(data), publicKey, signature);
|
|
56833
|
-
if (!isValid) return null;
|
|
56834
|
-
const payload = JSON.parse(Buffer.from(payloadB64, "base64url").toString());
|
|
56835
|
-
if (!payload.org || !Array.isArray(payload.features) || typeof payload.exp !== "number" || typeof payload.iat !== "number" || !payload.sub) {
|
|
56836
|
-
return null;
|
|
56837
|
-
}
|
|
56838
|
-
const now = Date.now();
|
|
56839
|
-
const expiryMs = payload.exp * 1e3;
|
|
56840
|
-
if (now >= expiryMs + _LicenseValidator.GRACE_PERIOD) {
|
|
56841
|
-
return null;
|
|
56842
|
-
}
|
|
56843
|
-
return payload;
|
|
56844
|
-
} catch {
|
|
56845
|
-
return null;
|
|
56846
|
-
}
|
|
56847
|
-
}
|
|
56848
|
-
};
|
|
56849
|
-
}
|
|
56850
|
-
});
|
|
56851
|
-
|
|
56852
|
-
// src/enterprise/policy/opa-compiler.ts
|
|
56853
|
-
var fs22, path27, os2, crypto4, import_child_process8, OpaCompiler;
|
|
56854
|
-
var init_opa_compiler = __esm({
|
|
56855
|
-
"src/enterprise/policy/opa-compiler.ts"() {
|
|
56856
|
-
"use strict";
|
|
56857
|
-
fs22 = __toESM(require("fs"));
|
|
56858
|
-
path27 = __toESM(require("path"));
|
|
56859
|
-
os2 = __toESM(require("os"));
|
|
56860
|
-
crypto4 = __toESM(require("crypto"));
|
|
56861
|
-
import_child_process8 = require("child_process");
|
|
56862
|
-
OpaCompiler = class _OpaCompiler {
|
|
56863
|
-
static CACHE_DIR = path27.join(os2.tmpdir(), "visor-opa-cache");
|
|
56864
|
-
/**
|
|
56865
|
-
* Resolve the input paths to WASM bytes.
|
|
56866
|
-
*
|
|
56867
|
-
* Strategy:
|
|
56868
|
-
* 1. If any path is a .wasm file, read it directly
|
|
56869
|
-
* 2. If a directory contains policy.wasm, read it
|
|
56870
|
-
* 3. Otherwise, collect all .rego files and auto-compile via `opa build`
|
|
56871
|
-
*/
|
|
56872
|
-
async resolveWasmBytes(paths) {
|
|
56873
|
-
const regoFiles = [];
|
|
56874
|
-
for (const p of paths) {
|
|
56875
|
-
const resolved = path27.resolve(p);
|
|
56876
|
-
if (path27.normalize(resolved).includes("..")) {
|
|
56877
|
-
throw new Error(`Policy path contains traversal sequences: ${p}`);
|
|
56878
|
-
}
|
|
56879
|
-
if (resolved.endsWith(".wasm") && fs22.existsSync(resolved)) {
|
|
56880
|
-
return fs22.readFileSync(resolved);
|
|
56881
|
-
}
|
|
56882
|
-
if (!fs22.existsSync(resolved)) continue;
|
|
56883
|
-
const stat2 = fs22.statSync(resolved);
|
|
56884
|
-
if (stat2.isDirectory()) {
|
|
56885
|
-
const wasmCandidate = path27.join(resolved, "policy.wasm");
|
|
56886
|
-
if (fs22.existsSync(wasmCandidate)) {
|
|
56887
|
-
return fs22.readFileSync(wasmCandidate);
|
|
56888
|
-
}
|
|
56889
|
-
const files = fs22.readdirSync(resolved);
|
|
56890
|
-
for (const f of files) {
|
|
56891
|
-
if (f.endsWith(".rego")) {
|
|
56892
|
-
regoFiles.push(path27.join(resolved, f));
|
|
56893
|
-
}
|
|
56894
|
-
}
|
|
56895
|
-
} else if (resolved.endsWith(".rego")) {
|
|
56896
|
-
regoFiles.push(resolved);
|
|
56897
|
-
}
|
|
56898
|
-
}
|
|
56899
|
-
if (regoFiles.length === 0) {
|
|
56900
|
-
throw new Error(
|
|
56901
|
-
`OPA WASM evaluator: no .wasm bundle or .rego files found in: ${paths.join(", ")}`
|
|
56902
|
-
);
|
|
56903
|
-
}
|
|
56904
|
-
return this.compileRego(regoFiles);
|
|
56905
|
-
}
|
|
56906
|
-
/**
|
|
56907
|
-
* Auto-compile .rego files to a WASM bundle using the `opa` CLI.
|
|
56908
|
-
*
|
|
56909
|
-
* Caches the compiled bundle based on a content hash of all input .rego files
|
|
56910
|
-
* so subsequent runs skip compilation if policies haven't changed.
|
|
56911
|
-
*/
|
|
56912
|
-
compileRego(regoFiles) {
|
|
56913
|
-
try {
|
|
56914
|
-
(0, import_child_process8.execFileSync)("opa", ["version"], { stdio: "pipe" });
|
|
56915
|
-
} catch {
|
|
56916
|
-
throw new Error(
|
|
56917
|
-
"OPA CLI (`opa`) not found on PATH. Install it from https://www.openpolicyagent.org/docs/latest/#running-opa\nOr pre-compile your .rego files: opa build -t wasm -e visor -o bundle.tar.gz " + regoFiles.join(" ")
|
|
56918
|
-
);
|
|
56919
|
-
}
|
|
56920
|
-
const hash = crypto4.createHash("sha256");
|
|
56921
|
-
for (const f of regoFiles.sort()) {
|
|
56922
|
-
hash.update(fs22.readFileSync(f));
|
|
56923
|
-
hash.update(f);
|
|
56924
|
-
}
|
|
56925
|
-
const cacheKey = hash.digest("hex").slice(0, 16);
|
|
56926
|
-
const cacheDir = _OpaCompiler.CACHE_DIR;
|
|
56927
|
-
const cachedWasm = path27.join(cacheDir, `${cacheKey}.wasm`);
|
|
56928
|
-
if (fs22.existsSync(cachedWasm)) {
|
|
56929
|
-
return fs22.readFileSync(cachedWasm);
|
|
56930
|
-
}
|
|
56931
|
-
fs22.mkdirSync(cacheDir, { recursive: true });
|
|
56932
|
-
const bundleTar = path27.join(cacheDir, `${cacheKey}-bundle.tar.gz`);
|
|
56933
|
-
try {
|
|
56934
|
-
const args = [
|
|
56935
|
-
"build",
|
|
56936
|
-
"-t",
|
|
56937
|
-
"wasm",
|
|
56938
|
-
"-e",
|
|
56939
|
-
"visor",
|
|
56940
|
-
// entrypoint: the visor package tree
|
|
56941
|
-
"-o",
|
|
56942
|
-
bundleTar,
|
|
56943
|
-
...regoFiles
|
|
56944
|
-
];
|
|
56945
|
-
(0, import_child_process8.execFileSync)("opa", args, {
|
|
56946
|
-
stdio: "pipe",
|
|
56947
|
-
timeout: 3e4
|
|
56948
|
-
});
|
|
56949
|
-
} catch (err) {
|
|
56950
|
-
const stderr = err?.stderr?.toString() || "";
|
|
56951
|
-
throw new Error(
|
|
56952
|
-
`Failed to compile .rego files to WASM:
|
|
56953
|
-
${stderr}
|
|
56954
|
-
Ensure your .rego files are valid and the \`opa\` CLI is installed.`
|
|
56955
|
-
);
|
|
56956
|
-
}
|
|
56957
|
-
try {
|
|
56958
|
-
(0, import_child_process8.execFileSync)("tar", ["-xzf", bundleTar, "-C", cacheDir, "/policy.wasm"], {
|
|
56959
|
-
stdio: "pipe"
|
|
56960
|
-
});
|
|
56961
|
-
const extractedWasm = path27.join(cacheDir, "policy.wasm");
|
|
56962
|
-
if (fs22.existsSync(extractedWasm)) {
|
|
56963
|
-
fs22.renameSync(extractedWasm, cachedWasm);
|
|
56964
|
-
}
|
|
56965
|
-
} catch {
|
|
56966
|
-
try {
|
|
56967
|
-
(0, import_child_process8.execFileSync)("tar", ["-xzf", bundleTar, "-C", cacheDir, "policy.wasm"], {
|
|
56968
|
-
stdio: "pipe"
|
|
56969
|
-
});
|
|
56970
|
-
const extractedWasm = path27.join(cacheDir, "policy.wasm");
|
|
56971
|
-
if (fs22.existsSync(extractedWasm)) {
|
|
56972
|
-
fs22.renameSync(extractedWasm, cachedWasm);
|
|
56973
|
-
}
|
|
56974
|
-
} catch (err2) {
|
|
56975
|
-
throw new Error(`Failed to extract policy.wasm from OPA bundle: ${err2?.message || err2}`);
|
|
56976
|
-
}
|
|
56977
|
-
}
|
|
56978
|
-
try {
|
|
56979
|
-
fs22.unlinkSync(bundleTar);
|
|
56980
|
-
} catch {
|
|
56981
|
-
}
|
|
56982
|
-
if (!fs22.existsSync(cachedWasm)) {
|
|
56983
|
-
throw new Error("OPA build succeeded but policy.wasm was not found in the bundle");
|
|
56984
|
-
}
|
|
56985
|
-
return fs22.readFileSync(cachedWasm);
|
|
56986
|
-
}
|
|
56987
|
-
};
|
|
56988
|
-
}
|
|
56989
|
-
});
|
|
56990
|
-
|
|
56991
|
-
// src/enterprise/policy/opa-wasm-evaluator.ts
|
|
56992
|
-
var fs23, path28, OpaWasmEvaluator;
|
|
56993
|
-
var init_opa_wasm_evaluator = __esm({
|
|
56994
|
-
"src/enterprise/policy/opa-wasm-evaluator.ts"() {
|
|
56995
|
-
"use strict";
|
|
56996
|
-
fs23 = __toESM(require("fs"));
|
|
56997
|
-
path28 = __toESM(require("path"));
|
|
56998
|
-
init_opa_compiler();
|
|
56999
|
-
OpaWasmEvaluator = class {
|
|
57000
|
-
policy = null;
|
|
57001
|
-
dataDocument = {};
|
|
57002
|
-
compiler = new OpaCompiler();
|
|
57003
|
-
async initialize(rulesPath) {
|
|
57004
|
-
const paths = Array.isArray(rulesPath) ? rulesPath : [rulesPath];
|
|
57005
|
-
const wasmBytes = await this.compiler.resolveWasmBytes(paths);
|
|
57006
|
-
try {
|
|
57007
|
-
const { createRequire } = require("module");
|
|
57008
|
-
const runtimeRequire = createRequire(__filename);
|
|
57009
|
-
const opaWasm = runtimeRequire("@open-policy-agent/opa-wasm");
|
|
57010
|
-
const loadPolicy = opaWasm.loadPolicy || opaWasm.default?.loadPolicy;
|
|
57011
|
-
if (!loadPolicy) {
|
|
57012
|
-
throw new Error("loadPolicy not found in @open-policy-agent/opa-wasm");
|
|
57013
|
-
}
|
|
57014
|
-
this.policy = await loadPolicy(wasmBytes);
|
|
57015
|
-
} catch (err) {
|
|
57016
|
-
if (err?.code === "MODULE_NOT_FOUND" || err?.code === "ERR_MODULE_NOT_FOUND") {
|
|
57017
|
-
throw new Error(
|
|
57018
|
-
"OPA WASM evaluator requires @open-policy-agent/opa-wasm. Install it with: npm install @open-policy-agent/opa-wasm"
|
|
57019
|
-
);
|
|
57020
|
-
}
|
|
57021
|
-
throw err;
|
|
57022
|
-
}
|
|
57023
|
-
}
|
|
57024
|
-
/**
|
|
57025
|
-
* Load external data from a JSON file to use as the OPA data document.
|
|
57026
|
-
* The loaded data will be passed to `policy.setData()` during evaluation,
|
|
57027
|
-
* making it available in Rego via `data.<key>`.
|
|
57028
|
-
*/
|
|
57029
|
-
loadData(dataPath) {
|
|
57030
|
-
const resolved = path28.resolve(dataPath);
|
|
57031
|
-
if (path28.normalize(resolved).includes("..")) {
|
|
57032
|
-
throw new Error(`Data path contains traversal sequences: ${dataPath}`);
|
|
57033
|
-
}
|
|
57034
|
-
if (!fs23.existsSync(resolved)) {
|
|
57035
|
-
throw new Error(`OPA data file not found: ${resolved}`);
|
|
57036
|
-
}
|
|
57037
|
-
const stat2 = fs23.statSync(resolved);
|
|
57038
|
-
if (stat2.size > 10 * 1024 * 1024) {
|
|
57039
|
-
throw new Error(`OPA data file exceeds 10MB limit: ${resolved} (${stat2.size} bytes)`);
|
|
57040
|
-
}
|
|
57041
|
-
const raw = fs23.readFileSync(resolved, "utf-8");
|
|
57042
|
-
try {
|
|
57043
|
-
const parsed = JSON.parse(raw);
|
|
57044
|
-
if (typeof parsed !== "object" || parsed === null || Array.isArray(parsed)) {
|
|
57045
|
-
throw new Error("OPA data file must contain a JSON object (not an array or primitive)");
|
|
57046
|
-
}
|
|
57047
|
-
this.dataDocument = parsed;
|
|
57048
|
-
} catch (err) {
|
|
57049
|
-
if (err.message.startsWith("OPA data file must")) {
|
|
57050
|
-
throw err;
|
|
57051
|
-
}
|
|
57052
|
-
throw new Error(`Failed to parse OPA data file ${resolved}: ${err.message}`);
|
|
57053
|
-
}
|
|
57054
|
-
}
|
|
57055
|
-
async evaluate(input) {
|
|
57056
|
-
if (!this.policy) {
|
|
57057
|
-
throw new Error("OPA WASM evaluator not initialized");
|
|
57058
|
-
}
|
|
57059
|
-
this.policy.setData(this.dataDocument);
|
|
57060
|
-
const resultSet = this.policy.evaluate(input);
|
|
57061
|
-
if (Array.isArray(resultSet) && resultSet.length > 0) {
|
|
57062
|
-
return resultSet[0].result;
|
|
57063
|
-
}
|
|
57064
|
-
return void 0;
|
|
57065
|
-
}
|
|
57066
|
-
async shutdown() {
|
|
57067
|
-
if (this.policy) {
|
|
57068
|
-
if (typeof this.policy.close === "function") {
|
|
57069
|
-
try {
|
|
57070
|
-
this.policy.close();
|
|
57071
|
-
} catch {
|
|
57072
|
-
}
|
|
57073
|
-
} else if (typeof this.policy.free === "function") {
|
|
57074
|
-
try {
|
|
57075
|
-
this.policy.free();
|
|
57076
|
-
} catch {
|
|
57077
|
-
}
|
|
57078
|
-
}
|
|
57079
|
-
}
|
|
57080
|
-
this.policy = null;
|
|
57081
|
-
}
|
|
57082
|
-
};
|
|
57083
|
-
}
|
|
57084
|
-
});
|
|
57085
|
-
|
|
57086
|
-
// src/enterprise/policy/opa-http-evaluator.ts
|
|
57087
|
-
var OpaHttpEvaluator;
|
|
57088
|
-
var init_opa_http_evaluator = __esm({
|
|
57089
|
-
"src/enterprise/policy/opa-http-evaluator.ts"() {
|
|
57090
|
-
"use strict";
|
|
57091
|
-
OpaHttpEvaluator = class {
|
|
57092
|
-
baseUrl;
|
|
57093
|
-
timeout;
|
|
57094
|
-
constructor(baseUrl, timeout = 5e3) {
|
|
57095
|
-
let parsed;
|
|
57096
|
-
try {
|
|
57097
|
-
parsed = new URL(baseUrl);
|
|
57098
|
-
} catch {
|
|
57099
|
-
throw new Error(`OPA HTTP evaluator: invalid URL: ${baseUrl}`);
|
|
57100
|
-
}
|
|
57101
|
-
if (!["http:", "https:"].includes(parsed.protocol)) {
|
|
57102
|
-
throw new Error(
|
|
57103
|
-
`OPA HTTP evaluator: url must use http:// or https:// protocol, got: ${baseUrl}`
|
|
57104
|
-
);
|
|
57105
|
-
}
|
|
57106
|
-
const hostname = parsed.hostname;
|
|
57107
|
-
if (this.isBlockedHostname(hostname)) {
|
|
57108
|
-
throw new Error(
|
|
57109
|
-
`OPA HTTP evaluator: url must not point to internal, loopback, or private network addresses`
|
|
57110
|
-
);
|
|
57111
|
-
}
|
|
57112
|
-
this.baseUrl = baseUrl.replace(/\/+$/, "");
|
|
57113
|
-
this.timeout = timeout;
|
|
57114
|
-
}
|
|
57115
|
-
/**
|
|
57116
|
-
* Check if a hostname is blocked due to SSRF concerns.
|
|
57117
|
-
*
|
|
57118
|
-
* Blocks:
|
|
57119
|
-
* - Loopback addresses (127.x.x.x, localhost, 0.0.0.0, ::1)
|
|
57120
|
-
* - Link-local addresses (169.254.x.x)
|
|
57121
|
-
* - Private networks (10.x.x.x, 172.16-31.x.x, 192.168.x.x)
|
|
57122
|
-
* - IPv6 unique local addresses (fd00::/8)
|
|
57123
|
-
* - Cloud metadata services (*.internal)
|
|
57124
|
-
*/
|
|
57125
|
-
isBlockedHostname(hostname) {
|
|
57126
|
-
if (!hostname) return true;
|
|
57127
|
-
const normalized = hostname.toLowerCase().replace(/^\[|\]$/g, "");
|
|
57128
|
-
if (normalized === "metadata.google.internal" || normalized.endsWith(".internal")) {
|
|
57129
|
-
return true;
|
|
57130
|
-
}
|
|
57131
|
-
if (normalized === "localhost" || normalized === "localhost.localdomain") {
|
|
57132
|
-
return true;
|
|
57133
|
-
}
|
|
57134
|
-
if (normalized === "::1" || normalized === "0:0:0:0:0:0:0:1") {
|
|
57135
|
-
return true;
|
|
57136
|
-
}
|
|
57137
|
-
const ipv4Pattern = /^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$/;
|
|
57138
|
-
const ipv4Match = normalized.match(ipv4Pattern);
|
|
57139
|
-
if (ipv4Match) {
|
|
57140
|
-
const octets = ipv4Match.slice(1, 5).map(Number);
|
|
57141
|
-
if (octets.some((octet) => octet > 255)) {
|
|
57142
|
-
return false;
|
|
57143
|
-
}
|
|
57144
|
-
const [a, b] = octets;
|
|
57145
|
-
if (a === 127) {
|
|
57146
|
-
return true;
|
|
57147
|
-
}
|
|
57148
|
-
if (a === 0) {
|
|
57149
|
-
return true;
|
|
57150
|
-
}
|
|
57151
|
-
if (a === 169 && b === 254) {
|
|
57152
|
-
return true;
|
|
57153
|
-
}
|
|
57154
|
-
if (a === 10) {
|
|
57155
|
-
return true;
|
|
57156
|
-
}
|
|
57157
|
-
if (a === 172 && b >= 16 && b <= 31) {
|
|
57158
|
-
return true;
|
|
57159
|
-
}
|
|
57160
|
-
if (a === 192 && b === 168) {
|
|
57161
|
-
return true;
|
|
57162
|
-
}
|
|
57163
|
-
}
|
|
57164
|
-
if (normalized.startsWith("fd") || normalized.startsWith("fc")) {
|
|
57165
|
-
return true;
|
|
57166
|
-
}
|
|
57167
|
-
if (normalized.startsWith("fe80:")) {
|
|
57168
|
-
return true;
|
|
57169
|
-
}
|
|
57170
|
-
return false;
|
|
57171
|
-
}
|
|
57172
|
-
/**
|
|
57173
|
-
* Evaluate a policy rule against an input document via OPA REST API.
|
|
57174
|
-
*
|
|
57175
|
-
* @param input - The input document to evaluate
|
|
57176
|
-
* @param rulePath - OPA rule path (e.g., 'visor/check/execute')
|
|
57177
|
-
* @returns The result object from OPA, or undefined on error
|
|
57178
|
-
*/
|
|
57179
|
-
async evaluate(input, rulePath) {
|
|
57180
|
-
const encodedPath = rulePath.split("/").map((s) => encodeURIComponent(s)).join("/");
|
|
57181
|
-
const url = `${this.baseUrl}/v1/data/${encodedPath}`;
|
|
57182
|
-
const controller = new AbortController();
|
|
57183
|
-
const timer = setTimeout(() => controller.abort(), this.timeout);
|
|
57184
|
-
try {
|
|
57185
|
-
const response = await fetch(url, {
|
|
57186
|
-
method: "POST",
|
|
57187
|
-
headers: { "Content-Type": "application/json" },
|
|
57188
|
-
body: JSON.stringify({ input }),
|
|
57189
|
-
signal: controller.signal
|
|
57190
|
-
});
|
|
57191
|
-
if (!response.ok) {
|
|
57192
|
-
throw new Error(`OPA HTTP ${response.status}: ${response.statusText}`);
|
|
57193
|
-
}
|
|
57194
|
-
let body;
|
|
57195
|
-
try {
|
|
57196
|
-
body = await response.json();
|
|
57197
|
-
} catch (jsonErr) {
|
|
57198
|
-
throw new Error(
|
|
57199
|
-
`OPA HTTP evaluator: failed to parse JSON response: ${jsonErr instanceof Error ? jsonErr.message : String(jsonErr)}`
|
|
57200
|
-
);
|
|
57201
|
-
}
|
|
57202
|
-
return body?.result;
|
|
57203
|
-
} finally {
|
|
57204
|
-
clearTimeout(timer);
|
|
57205
|
-
}
|
|
57206
|
-
}
|
|
57207
|
-
async shutdown() {
|
|
57208
|
-
}
|
|
57209
|
-
};
|
|
57210
|
-
}
|
|
57211
|
-
});
|
|
57212
|
-
|
|
57213
|
-
// src/enterprise/policy/policy-input-builder.ts
|
|
57214
|
-
var PolicyInputBuilder;
|
|
57215
|
-
var init_policy_input_builder = __esm({
|
|
57216
|
-
"src/enterprise/policy/policy-input-builder.ts"() {
|
|
57217
|
-
"use strict";
|
|
57218
|
-
PolicyInputBuilder = class {
|
|
57219
|
-
roles;
|
|
57220
|
-
actor;
|
|
57221
|
-
repository;
|
|
57222
|
-
pullRequest;
|
|
57223
|
-
constructor(policyConfig, actor, repository, pullRequest) {
|
|
57224
|
-
this.roles = policyConfig.roles || {};
|
|
57225
|
-
this.actor = actor;
|
|
57226
|
-
this.repository = repository;
|
|
57227
|
-
this.pullRequest = pullRequest;
|
|
57228
|
-
}
|
|
57229
|
-
/** Resolve which roles apply to the current actor. */
|
|
57230
|
-
resolveRoles() {
|
|
57231
|
-
const matched = [];
|
|
57232
|
-
for (const [roleName, roleConfig] of Object.entries(this.roles)) {
|
|
57233
|
-
let identityMatch = false;
|
|
57234
|
-
if (roleConfig.author_association && this.actor.authorAssociation && roleConfig.author_association.includes(this.actor.authorAssociation)) {
|
|
57235
|
-
identityMatch = true;
|
|
57236
|
-
}
|
|
57237
|
-
if (!identityMatch && roleConfig.users && this.actor.login && roleConfig.users.includes(this.actor.login)) {
|
|
57238
|
-
identityMatch = true;
|
|
57239
|
-
}
|
|
57240
|
-
if (!identityMatch && roleConfig.slack_users && this.actor.slack?.userId && roleConfig.slack_users.includes(this.actor.slack.userId)) {
|
|
57241
|
-
identityMatch = true;
|
|
57242
|
-
}
|
|
57243
|
-
if (!identityMatch && roleConfig.emails && this.actor.slack?.email) {
|
|
57244
|
-
const actorEmail = this.actor.slack.email.toLowerCase();
|
|
57245
|
-
if (roleConfig.emails.some((e) => e.toLowerCase() === actorEmail)) {
|
|
57246
|
-
identityMatch = true;
|
|
57247
|
-
}
|
|
57248
|
-
}
|
|
57249
|
-
if (!identityMatch) continue;
|
|
57250
|
-
if (roleConfig.slack_channels && roleConfig.slack_channels.length > 0) {
|
|
57251
|
-
if (!this.actor.slack?.channelId || !roleConfig.slack_channels.includes(this.actor.slack.channelId)) {
|
|
57252
|
-
continue;
|
|
57253
|
-
}
|
|
57254
|
-
}
|
|
57255
|
-
matched.push(roleName);
|
|
57256
|
-
}
|
|
57257
|
-
return matched;
|
|
57258
|
-
}
|
|
57259
|
-
buildActor() {
|
|
57260
|
-
return {
|
|
57261
|
-
authorAssociation: this.actor.authorAssociation,
|
|
57262
|
-
login: this.actor.login,
|
|
57263
|
-
roles: this.resolveRoles(),
|
|
57264
|
-
isLocalMode: this.actor.isLocalMode,
|
|
57265
|
-
...this.actor.slack && { slack: this.actor.slack }
|
|
57266
|
-
};
|
|
57267
|
-
}
|
|
57268
|
-
forCheckExecution(check) {
|
|
57269
|
-
return {
|
|
57270
|
-
scope: "check.execute",
|
|
57271
|
-
check: {
|
|
57272
|
-
id: check.id,
|
|
57273
|
-
type: check.type,
|
|
57274
|
-
group: check.group,
|
|
57275
|
-
tags: check.tags,
|
|
57276
|
-
criticality: check.criticality,
|
|
57277
|
-
sandbox: check.sandbox,
|
|
57278
|
-
policy: check.policy
|
|
57279
|
-
},
|
|
57280
|
-
actor: this.buildActor(),
|
|
57281
|
-
repository: this.repository,
|
|
57282
|
-
pullRequest: this.pullRequest
|
|
57283
|
-
};
|
|
57284
|
-
}
|
|
57285
|
-
forToolInvocation(serverName, methodName, transport) {
|
|
57286
|
-
return {
|
|
57287
|
-
scope: "tool.invoke",
|
|
57288
|
-
tool: { serverName, methodName, transport },
|
|
57289
|
-
actor: this.buildActor(),
|
|
57290
|
-
repository: this.repository,
|
|
57291
|
-
pullRequest: this.pullRequest
|
|
57292
|
-
};
|
|
57293
|
-
}
|
|
57294
|
-
forCapabilityResolve(checkId, capabilities) {
|
|
57295
|
-
return {
|
|
57296
|
-
scope: "capability.resolve",
|
|
57297
|
-
check: { id: checkId, type: "ai" },
|
|
57298
|
-
capability: capabilities,
|
|
57299
|
-
actor: this.buildActor(),
|
|
57300
|
-
repository: this.repository,
|
|
57301
|
-
pullRequest: this.pullRequest
|
|
57302
|
-
};
|
|
57303
|
-
}
|
|
57304
|
-
};
|
|
57305
|
-
}
|
|
57306
|
-
});
|
|
57307
|
-
|
|
57308
|
-
// src/enterprise/policy/opa-policy-engine.ts
|
|
57309
|
-
var opa_policy_engine_exports = {};
|
|
57310
|
-
__export(opa_policy_engine_exports, {
|
|
57311
|
-
OpaPolicyEngine: () => OpaPolicyEngine
|
|
57312
|
-
});
|
|
57313
|
-
var OpaPolicyEngine;
|
|
57314
|
-
var init_opa_policy_engine = __esm({
|
|
57315
|
-
"src/enterprise/policy/opa-policy-engine.ts"() {
|
|
57316
|
-
"use strict";
|
|
57317
|
-
init_opa_wasm_evaluator();
|
|
57318
|
-
init_opa_http_evaluator();
|
|
57319
|
-
init_policy_input_builder();
|
|
57320
|
-
OpaPolicyEngine = class {
|
|
57321
|
-
evaluator = null;
|
|
57322
|
-
fallback;
|
|
57323
|
-
timeout;
|
|
57324
|
-
config;
|
|
57325
|
-
inputBuilder = null;
|
|
57326
|
-
logger = null;
|
|
57327
|
-
constructor(config) {
|
|
57328
|
-
this.config = config;
|
|
57329
|
-
this.fallback = config.fallback || "deny";
|
|
57330
|
-
this.timeout = config.timeout || 5e3;
|
|
57331
|
-
}
|
|
57332
|
-
async initialize(config) {
|
|
57333
|
-
try {
|
|
57334
|
-
this.logger = (init_logger(), __toCommonJS(logger_exports)).logger;
|
|
57335
|
-
} catch {
|
|
57336
|
-
}
|
|
57337
|
-
const actor = {
|
|
57338
|
-
authorAssociation: process.env.VISOR_AUTHOR_ASSOCIATION,
|
|
57339
|
-
login: process.env.VISOR_AUTHOR_LOGIN || process.env.GITHUB_ACTOR,
|
|
57340
|
-
isLocalMode: !process.env.GITHUB_ACTIONS
|
|
57341
|
-
};
|
|
57342
|
-
const repo = {
|
|
57343
|
-
owner: process.env.GITHUB_REPOSITORY_OWNER,
|
|
57344
|
-
name: process.env.GITHUB_REPOSITORY?.split("/")[1],
|
|
57345
|
-
branch: process.env.GITHUB_HEAD_REF,
|
|
57346
|
-
baseBranch: process.env.GITHUB_BASE_REF,
|
|
57347
|
-
event: process.env.GITHUB_EVENT_NAME
|
|
57348
|
-
};
|
|
57349
|
-
const prNum = process.env.GITHUB_PR_NUMBER ? parseInt(process.env.GITHUB_PR_NUMBER, 10) : void 0;
|
|
57350
|
-
const pullRequest = {
|
|
57351
|
-
number: prNum !== void 0 && Number.isFinite(prNum) ? prNum : void 0
|
|
57352
|
-
};
|
|
57353
|
-
this.inputBuilder = new PolicyInputBuilder(config, actor, repo, pullRequest);
|
|
57354
|
-
if (config.engine === "local") {
|
|
57355
|
-
if (!config.rules) {
|
|
57356
|
-
throw new Error("OPA local mode requires `policy.rules` path to .wasm or .rego files");
|
|
57357
|
-
}
|
|
57358
|
-
const wasm = new OpaWasmEvaluator();
|
|
57359
|
-
await wasm.initialize(config.rules);
|
|
57360
|
-
if (config.data) {
|
|
57361
|
-
wasm.loadData(config.data);
|
|
57362
|
-
}
|
|
57363
|
-
this.evaluator = wasm;
|
|
57364
|
-
} else if (config.engine === "remote") {
|
|
57365
|
-
if (!config.url) {
|
|
57366
|
-
throw new Error("OPA remote mode requires `policy.url` pointing to OPA server");
|
|
57367
|
-
}
|
|
57368
|
-
this.evaluator = new OpaHttpEvaluator(config.url, this.timeout);
|
|
57369
|
-
} else {
|
|
57370
|
-
this.evaluator = null;
|
|
57371
|
-
}
|
|
57372
|
-
}
|
|
57373
|
-
/**
|
|
57374
|
-
* Update actor/repo/PR context (e.g., after PR info becomes available).
|
|
57375
|
-
* Called by the enterprise loader when engine context is enriched.
|
|
57376
|
-
*/
|
|
57377
|
-
setActorContext(actor, repo, pullRequest) {
|
|
57378
|
-
this.inputBuilder = new PolicyInputBuilder(this.config, actor, repo, pullRequest);
|
|
57379
|
-
}
|
|
57380
|
-
async evaluateCheckExecution(checkId, checkConfig) {
|
|
57381
|
-
if (!this.evaluator || !this.inputBuilder) return { allowed: true };
|
|
57382
|
-
const cfg = checkConfig && typeof checkConfig === "object" ? checkConfig : {};
|
|
57383
|
-
const policyOverride = cfg.policy;
|
|
57384
|
-
const input = this.inputBuilder.forCheckExecution({
|
|
57385
|
-
id: checkId,
|
|
57386
|
-
type: cfg.type || "ai",
|
|
57387
|
-
group: cfg.group,
|
|
57388
|
-
tags: cfg.tags,
|
|
57389
|
-
criticality: cfg.criticality,
|
|
57390
|
-
sandbox: cfg.sandbox,
|
|
57391
|
-
policy: policyOverride
|
|
57392
|
-
});
|
|
57393
|
-
return this.doEvaluate(input, this.resolveRulePath("check.execute", policyOverride?.rule));
|
|
57394
|
-
}
|
|
57395
|
-
async evaluateToolInvocation(serverName, methodName, transport) {
|
|
57396
|
-
if (!this.evaluator || !this.inputBuilder) return { allowed: true };
|
|
57397
|
-
const input = this.inputBuilder.forToolInvocation(serverName, methodName, transport);
|
|
57398
|
-
return this.doEvaluate(input, "visor/tool/invoke");
|
|
57399
|
-
}
|
|
57400
|
-
async evaluateCapabilities(checkId, capabilities) {
|
|
57401
|
-
if (!this.evaluator || !this.inputBuilder) return { allowed: true };
|
|
57402
|
-
const input = this.inputBuilder.forCapabilityResolve(checkId, capabilities);
|
|
57403
|
-
return this.doEvaluate(input, "visor/capability/resolve");
|
|
57404
|
-
}
|
|
57405
|
-
async shutdown() {
|
|
57406
|
-
if (this.evaluator && "shutdown" in this.evaluator) {
|
|
57407
|
-
await this.evaluator.shutdown();
|
|
57408
|
-
}
|
|
57409
|
-
this.evaluator = null;
|
|
57410
|
-
this.inputBuilder = null;
|
|
57411
|
-
}
|
|
57412
|
-
resolveRulePath(defaultScope, override) {
|
|
57413
|
-
if (override) {
|
|
57414
|
-
return override.startsWith("visor/") ? override : `visor/${override}`;
|
|
57415
|
-
}
|
|
57416
|
-
return `visor/${defaultScope.replace(/\./g, "/")}`;
|
|
57417
|
-
}
|
|
57418
|
-
async doEvaluate(input, rulePath) {
|
|
57419
|
-
try {
|
|
57420
|
-
this.logger?.debug(`[PolicyEngine] Evaluating ${rulePath}`, JSON.stringify(input));
|
|
57421
|
-
let timer;
|
|
57422
|
-
const timeoutPromise = new Promise((_resolve, reject) => {
|
|
57423
|
-
timer = setTimeout(() => reject(new Error("policy evaluation timeout")), this.timeout);
|
|
57424
|
-
});
|
|
57425
|
-
try {
|
|
57426
|
-
const result = await Promise.race([this.rawEvaluate(input, rulePath), timeoutPromise]);
|
|
57427
|
-
const decision = this.parseDecision(result);
|
|
57428
|
-
if (!decision.allowed && this.fallback === "warn") {
|
|
57429
|
-
decision.allowed = true;
|
|
57430
|
-
decision.warn = true;
|
|
57431
|
-
decision.reason = `audit: ${decision.reason || "policy denied"}`;
|
|
57432
|
-
}
|
|
57433
|
-
this.logger?.debug(
|
|
57434
|
-
`[PolicyEngine] Decision for ${rulePath}: allowed=${decision.allowed}, warn=${decision.warn || false}, reason=${decision.reason || "none"}`
|
|
57435
|
-
);
|
|
57436
|
-
return decision;
|
|
57437
|
-
} finally {
|
|
57438
|
-
if (timer) clearTimeout(timer);
|
|
57439
|
-
}
|
|
57440
|
-
} catch (err) {
|
|
57441
|
-
const msg = err instanceof Error ? err.message : String(err);
|
|
57442
|
-
this.logger?.warn(`[PolicyEngine] Evaluation failed for ${rulePath}: ${msg}`);
|
|
57443
|
-
return {
|
|
57444
|
-
allowed: this.fallback === "allow" || this.fallback === "warn",
|
|
57445
|
-
warn: this.fallback === "warn" ? true : void 0,
|
|
57446
|
-
reason: `policy evaluation failed, fallback=${this.fallback}`
|
|
57447
|
-
};
|
|
57448
|
-
}
|
|
57449
|
-
}
|
|
57450
|
-
async rawEvaluate(input, rulePath) {
|
|
57451
|
-
if (this.evaluator instanceof OpaWasmEvaluator) {
|
|
57452
|
-
const result = await this.evaluator.evaluate(input);
|
|
57453
|
-
return this.navigateWasmResult(result, rulePath);
|
|
57454
|
-
}
|
|
57455
|
-
return this.evaluator.evaluate(input, rulePath);
|
|
57456
|
-
}
|
|
57457
|
-
/**
|
|
57458
|
-
* Navigate nested OPA WASM result tree to reach the specific rule's output.
|
|
57459
|
-
* The WASM entrypoint `-e visor` means the result root IS the visor package,
|
|
57460
|
-
* so we strip the `visor/` prefix and walk the remaining segments.
|
|
57461
|
-
*/
|
|
57462
|
-
navigateWasmResult(result, rulePath) {
|
|
57463
|
-
if (!result || typeof result !== "object") return result;
|
|
57464
|
-
const segments = rulePath.replace(/^visor\//, "").split("/");
|
|
57465
|
-
let current = result;
|
|
57466
|
-
for (const seg of segments) {
|
|
57467
|
-
if (current && typeof current === "object" && seg in current) {
|
|
57468
|
-
current = current[seg];
|
|
57469
|
-
} else {
|
|
57470
|
-
return void 0;
|
|
57471
|
-
}
|
|
57472
|
-
}
|
|
57473
|
-
return current;
|
|
57474
|
-
}
|
|
57475
|
-
parseDecision(result) {
|
|
57476
|
-
if (result === void 0 || result === null) {
|
|
57477
|
-
return {
|
|
57478
|
-
allowed: this.fallback === "allow" || this.fallback === "warn",
|
|
57479
|
-
warn: this.fallback === "warn" ? true : void 0,
|
|
57480
|
-
reason: this.fallback === "warn" ? "audit: no policy result" : "no policy result"
|
|
57481
|
-
};
|
|
57482
|
-
}
|
|
57483
|
-
const allowed = result.allowed !== false;
|
|
57484
|
-
const decision = {
|
|
57485
|
-
allowed,
|
|
57486
|
-
reason: result.reason
|
|
57487
|
-
};
|
|
57488
|
-
if (result.capabilities) {
|
|
57489
|
-
decision.capabilities = result.capabilities;
|
|
57490
|
-
}
|
|
57491
|
-
return decision;
|
|
57492
|
-
}
|
|
57493
|
-
};
|
|
57494
|
-
}
|
|
57495
|
-
});
|
|
57496
|
-
|
|
57497
|
-
// src/enterprise/scheduler/knex-store.ts
|
|
57498
|
-
var knex_store_exports = {};
|
|
57499
|
-
__export(knex_store_exports, {
|
|
57500
|
-
KnexStoreBackend: () => KnexStoreBackend
|
|
57501
|
-
});
|
|
57502
|
-
function toNum(val) {
|
|
57503
|
-
if (val === null || val === void 0) return void 0;
|
|
57504
|
-
return typeof val === "string" ? parseInt(val, 10) : val;
|
|
57505
|
-
}
|
|
57506
|
-
function safeJsonParse2(value) {
|
|
57507
|
-
if (!value) return void 0;
|
|
57508
|
-
try {
|
|
57509
|
-
return JSON.parse(value);
|
|
57510
|
-
} catch {
|
|
57511
|
-
return void 0;
|
|
57512
|
-
}
|
|
57513
|
-
}
|
|
57514
|
-
function fromTriggerRow2(row) {
|
|
57515
|
-
return {
|
|
57516
|
-
id: row.id,
|
|
57517
|
-
creatorId: row.creator_id,
|
|
57518
|
-
creatorContext: row.creator_context ?? void 0,
|
|
57519
|
-
creatorName: row.creator_name ?? void 0,
|
|
57520
|
-
description: row.description ?? void 0,
|
|
57521
|
-
channels: safeJsonParse2(row.channels),
|
|
57522
|
-
fromUsers: safeJsonParse2(row.from_users),
|
|
57523
|
-
fromBots: row.from_bots === true || row.from_bots === 1,
|
|
57524
|
-
contains: safeJsonParse2(row.contains),
|
|
57525
|
-
matchPattern: row.match_pattern ?? void 0,
|
|
57526
|
-
threads: row.threads,
|
|
57527
|
-
workflow: row.workflow,
|
|
57528
|
-
inputs: safeJsonParse2(row.inputs),
|
|
57529
|
-
outputContext: safeJsonParse2(row.output_context),
|
|
57530
|
-
status: row.status,
|
|
57531
|
-
enabled: row.enabled === true || row.enabled === 1,
|
|
57532
|
-
createdAt: toNum(row.created_at)
|
|
57533
|
-
};
|
|
57534
|
-
}
|
|
57535
|
-
function toTriggerInsertRow(trigger) {
|
|
57536
|
-
return {
|
|
57537
|
-
id: trigger.id,
|
|
57538
|
-
creator_id: trigger.creatorId,
|
|
57539
|
-
creator_context: trigger.creatorContext ?? null,
|
|
57540
|
-
creator_name: trigger.creatorName ?? null,
|
|
57541
|
-
description: trigger.description ?? null,
|
|
57542
|
-
channels: trigger.channels ? JSON.stringify(trigger.channels) : null,
|
|
57543
|
-
from_users: trigger.fromUsers ? JSON.stringify(trigger.fromUsers) : null,
|
|
57544
|
-
from_bots: trigger.fromBots,
|
|
57545
|
-
contains: trigger.contains ? JSON.stringify(trigger.contains) : null,
|
|
57546
|
-
match_pattern: trigger.matchPattern ?? null,
|
|
57547
|
-
threads: trigger.threads,
|
|
57548
|
-
workflow: trigger.workflow,
|
|
57549
|
-
inputs: trigger.inputs ? JSON.stringify(trigger.inputs) : null,
|
|
57550
|
-
output_context: trigger.outputContext ? JSON.stringify(trigger.outputContext) : null,
|
|
57551
|
-
status: trigger.status,
|
|
57552
|
-
enabled: trigger.enabled,
|
|
57553
|
-
created_at: trigger.createdAt
|
|
57554
|
-
};
|
|
57555
|
-
}
|
|
57556
|
-
function fromDbRow2(row) {
|
|
57557
|
-
return {
|
|
57558
|
-
id: row.id,
|
|
57559
|
-
creatorId: row.creator_id,
|
|
57560
|
-
creatorContext: row.creator_context ?? void 0,
|
|
57561
|
-
creatorName: row.creator_name ?? void 0,
|
|
57562
|
-
timezone: row.timezone,
|
|
57563
|
-
schedule: row.schedule_expr,
|
|
57564
|
-
runAt: toNum(row.run_at),
|
|
57565
|
-
isRecurring: row.is_recurring === true || row.is_recurring === 1,
|
|
57566
|
-
originalExpression: row.original_expression,
|
|
57567
|
-
workflow: row.workflow ?? void 0,
|
|
57568
|
-
workflowInputs: safeJsonParse2(row.workflow_inputs),
|
|
57569
|
-
outputContext: safeJsonParse2(row.output_context),
|
|
57570
|
-
status: row.status,
|
|
57571
|
-
createdAt: toNum(row.created_at),
|
|
57572
|
-
lastRunAt: toNum(row.last_run_at),
|
|
57573
|
-
nextRunAt: toNum(row.next_run_at),
|
|
57574
|
-
runCount: row.run_count,
|
|
57575
|
-
failureCount: row.failure_count,
|
|
57576
|
-
lastError: row.last_error ?? void 0,
|
|
57577
|
-
previousResponse: row.previous_response ?? void 0
|
|
57578
|
-
};
|
|
57579
|
-
}
|
|
57580
|
-
function toInsertRow(schedule) {
|
|
57581
|
-
return {
|
|
57582
|
-
id: schedule.id,
|
|
57583
|
-
creator_id: schedule.creatorId,
|
|
57584
|
-
creator_context: schedule.creatorContext ?? null,
|
|
57585
|
-
creator_name: schedule.creatorName ?? null,
|
|
57586
|
-
timezone: schedule.timezone,
|
|
57587
|
-
schedule_expr: schedule.schedule,
|
|
57588
|
-
run_at: schedule.runAt ?? null,
|
|
57589
|
-
is_recurring: schedule.isRecurring,
|
|
57590
|
-
original_expression: schedule.originalExpression,
|
|
57591
|
-
workflow: schedule.workflow ?? null,
|
|
57592
|
-
workflow_inputs: schedule.workflowInputs ? JSON.stringify(schedule.workflowInputs) : null,
|
|
57593
|
-
output_context: schedule.outputContext ? JSON.stringify(schedule.outputContext) : null,
|
|
57594
|
-
status: schedule.status,
|
|
57595
|
-
created_at: schedule.createdAt,
|
|
57596
|
-
last_run_at: schedule.lastRunAt ?? null,
|
|
57597
|
-
next_run_at: schedule.nextRunAt ?? null,
|
|
57598
|
-
run_count: schedule.runCount,
|
|
57599
|
-
failure_count: schedule.failureCount,
|
|
57600
|
-
last_error: schedule.lastError ?? null,
|
|
57601
|
-
previous_response: schedule.previousResponse ?? null
|
|
57602
|
-
};
|
|
57603
|
-
}
|
|
57604
|
-
var fs24, path29, import_uuid2, KnexStoreBackend;
|
|
57605
|
-
var init_knex_store = __esm({
|
|
57606
|
-
"src/enterprise/scheduler/knex-store.ts"() {
|
|
57607
|
-
"use strict";
|
|
57608
|
-
fs24 = __toESM(require("fs"));
|
|
57609
|
-
path29 = __toESM(require("path"));
|
|
57610
|
-
import_uuid2 = require("uuid");
|
|
57611
|
-
init_logger();
|
|
57612
|
-
KnexStoreBackend = class {
|
|
57613
|
-
knex = null;
|
|
57614
|
-
driver;
|
|
57615
|
-
connection;
|
|
57616
|
-
constructor(driver, storageConfig, _haConfig) {
|
|
57617
|
-
this.driver = driver;
|
|
57618
|
-
this.connection = storageConfig.connection || {};
|
|
57619
|
-
}
|
|
57620
|
-
async initialize() {
|
|
57621
|
-
const { createRequire } = require("module");
|
|
57622
|
-
const runtimeRequire = createRequire(__filename);
|
|
57623
|
-
let knexFactory;
|
|
57624
|
-
try {
|
|
57625
|
-
knexFactory = runtimeRequire("knex");
|
|
57626
|
-
} catch (err) {
|
|
57627
|
-
const code = err?.code;
|
|
57628
|
-
if (code === "MODULE_NOT_FOUND" || code === "ERR_MODULE_NOT_FOUND") {
|
|
57629
|
-
throw new Error(
|
|
57630
|
-
"knex is required for PostgreSQL/MySQL/MSSQL schedule storage. Install it with: npm install knex"
|
|
57631
|
-
);
|
|
57632
|
-
}
|
|
57633
|
-
throw err;
|
|
57634
|
-
}
|
|
57635
|
-
const clientMap = {
|
|
57636
|
-
postgresql: "pg",
|
|
57637
|
-
mysql: "mysql2",
|
|
57638
|
-
mssql: "tedious"
|
|
57639
|
-
};
|
|
57640
|
-
const client = clientMap[this.driver];
|
|
57641
|
-
let connection;
|
|
57642
|
-
if (this.connection.connection_string) {
|
|
57643
|
-
connection = this.connection.connection_string;
|
|
57644
|
-
} else if (this.driver === "mssql") {
|
|
57645
|
-
connection = this.buildMssqlConnection();
|
|
57646
|
-
} else {
|
|
57647
|
-
connection = this.buildStandardConnection();
|
|
57648
|
-
}
|
|
57649
|
-
this.knex = knexFactory({
|
|
57650
|
-
client,
|
|
57651
|
-
connection,
|
|
57652
|
-
pool: {
|
|
57653
|
-
min: this.connection.pool?.min ?? 0,
|
|
57654
|
-
max: this.connection.pool?.max ?? 10
|
|
57655
|
-
}
|
|
57656
|
-
});
|
|
57657
|
-
await this.migrateSchema();
|
|
57658
|
-
logger.info(`[KnexStore] Initialized (${this.driver})`);
|
|
57659
|
-
}
|
|
57660
|
-
buildStandardConnection() {
|
|
57661
|
-
return {
|
|
57662
|
-
host: this.connection.host || "localhost",
|
|
57663
|
-
port: this.connection.port,
|
|
57664
|
-
database: this.connection.database || "visor",
|
|
57665
|
-
user: this.connection.user,
|
|
57666
|
-
password: this.connection.password,
|
|
57667
|
-
ssl: this.resolveSslConfig()
|
|
57668
|
-
};
|
|
57669
|
-
}
|
|
57670
|
-
buildMssqlConnection() {
|
|
57671
|
-
const ssl = this.connection.ssl;
|
|
57672
|
-
const sslEnabled = ssl === true || typeof ssl === "object" && ssl.enabled !== false;
|
|
57673
|
-
return {
|
|
57674
|
-
server: this.connection.host || "localhost",
|
|
57675
|
-
port: this.connection.port,
|
|
57676
|
-
database: this.connection.database || "visor",
|
|
57677
|
-
user: this.connection.user,
|
|
57678
|
-
password: this.connection.password,
|
|
57679
|
-
options: {
|
|
57680
|
-
encrypt: sslEnabled,
|
|
57681
|
-
trustServerCertificate: typeof ssl === "object" ? ssl.reject_unauthorized === false : !sslEnabled
|
|
57682
|
-
}
|
|
57683
|
-
};
|
|
57684
|
-
}
|
|
57685
|
-
resolveSslConfig() {
|
|
57686
|
-
const ssl = this.connection.ssl;
|
|
57687
|
-
if (ssl === false || ssl === void 0) return false;
|
|
57688
|
-
if (ssl === true) return { rejectUnauthorized: true };
|
|
57689
|
-
if (ssl.enabled === false) return false;
|
|
57690
|
-
const result = {
|
|
57691
|
-
rejectUnauthorized: ssl.reject_unauthorized !== false
|
|
57692
|
-
};
|
|
57693
|
-
if (ssl.ca) {
|
|
57694
|
-
const caPath = this.validateSslPath(ssl.ca, "CA certificate");
|
|
57695
|
-
result.ca = fs24.readFileSync(caPath, "utf8");
|
|
57696
|
-
}
|
|
57697
|
-
if (ssl.cert) {
|
|
57698
|
-
const certPath = this.validateSslPath(ssl.cert, "client certificate");
|
|
57699
|
-
result.cert = fs24.readFileSync(certPath, "utf8");
|
|
57700
|
-
}
|
|
57701
|
-
if (ssl.key) {
|
|
57702
|
-
const keyPath = this.validateSslPath(ssl.key, "client key");
|
|
57703
|
-
result.key = fs24.readFileSync(keyPath, "utf8");
|
|
57704
|
-
}
|
|
57705
|
-
return result;
|
|
57706
|
-
}
|
|
57707
|
-
validateSslPath(filePath, label) {
|
|
57708
|
-
const resolved = path29.resolve(filePath);
|
|
57709
|
-
if (resolved !== path29.normalize(resolved)) {
|
|
57710
|
-
throw new Error(`SSL ${label} path contains invalid sequences: ${filePath}`);
|
|
57711
|
-
}
|
|
57712
|
-
if (!fs24.existsSync(resolved)) {
|
|
57713
|
-
throw new Error(`SSL ${label} not found: ${filePath}`);
|
|
57714
|
-
}
|
|
57715
|
-
return resolved;
|
|
57716
|
-
}
|
|
57717
|
-
async shutdown() {
|
|
57718
|
-
if (this.knex) {
|
|
57719
|
-
await this.knex.destroy();
|
|
57720
|
-
this.knex = null;
|
|
57721
|
-
}
|
|
57722
|
-
}
|
|
57723
|
-
async migrateSchema() {
|
|
57724
|
-
const knex = this.getKnex();
|
|
57725
|
-
const exists = await knex.schema.hasTable("schedules");
|
|
57726
|
-
if (!exists) {
|
|
57727
|
-
await knex.schema.createTable("schedules", (table) => {
|
|
57728
|
-
table.string("id", 36).primary();
|
|
57729
|
-
table.string("creator_id", 255).notNullable().index();
|
|
57730
|
-
table.string("creator_context", 255);
|
|
57731
|
-
table.string("creator_name", 255);
|
|
57732
|
-
table.string("timezone", 64).notNullable().defaultTo("UTC");
|
|
57733
|
-
table.string("schedule_expr", 255);
|
|
57734
|
-
table.bigInteger("run_at");
|
|
57735
|
-
table.boolean("is_recurring").notNullable();
|
|
57736
|
-
table.text("original_expression");
|
|
57737
|
-
table.string("workflow", 255);
|
|
57738
|
-
table.text("workflow_inputs");
|
|
57739
|
-
table.text("output_context");
|
|
57740
|
-
table.string("status", 20).notNullable().index();
|
|
57741
|
-
table.bigInteger("created_at").notNullable();
|
|
57742
|
-
table.bigInteger("last_run_at");
|
|
57743
|
-
table.bigInteger("next_run_at");
|
|
57744
|
-
table.integer("run_count").notNullable().defaultTo(0);
|
|
57745
|
-
table.integer("failure_count").notNullable().defaultTo(0);
|
|
57746
|
-
table.text("last_error");
|
|
57747
|
-
table.text("previous_response");
|
|
57748
|
-
table.index(["status", "next_run_at"]);
|
|
57749
|
-
});
|
|
57750
|
-
}
|
|
57751
|
-
const triggersExist = await knex.schema.hasTable("message_triggers");
|
|
57752
|
-
if (!triggersExist) {
|
|
57753
|
-
await knex.schema.createTable("message_triggers", (table) => {
|
|
57754
|
-
table.string("id", 36).primary();
|
|
57755
|
-
table.string("creator_id", 255).notNullable().index();
|
|
57756
|
-
table.string("creator_context", 255);
|
|
57757
|
-
table.string("creator_name", 255);
|
|
57758
|
-
table.text("description");
|
|
57759
|
-
table.text("channels");
|
|
57760
|
-
table.text("from_users");
|
|
57761
|
-
table.boolean("from_bots").notNullable().defaultTo(false);
|
|
57762
|
-
table.text("contains");
|
|
57763
|
-
table.text("match_pattern");
|
|
57764
|
-
table.string("threads", 20).notNullable().defaultTo("any");
|
|
57765
|
-
table.string("workflow", 255).notNullable();
|
|
57766
|
-
table.text("inputs");
|
|
57767
|
-
table.text("output_context");
|
|
57768
|
-
table.string("status", 20).notNullable().defaultTo("active").index();
|
|
57769
|
-
table.boolean("enabled").notNullable().defaultTo(true);
|
|
57770
|
-
table.bigInteger("created_at").notNullable();
|
|
57771
|
-
});
|
|
57772
|
-
}
|
|
57773
|
-
const locksExist = await knex.schema.hasTable("scheduler_locks");
|
|
57774
|
-
if (!locksExist) {
|
|
57775
|
-
await knex.schema.createTable("scheduler_locks", (table) => {
|
|
57776
|
-
table.string("lock_id", 255).primary();
|
|
57777
|
-
table.string("node_id", 255).notNullable();
|
|
57778
|
-
table.string("lock_token", 36).notNullable();
|
|
57779
|
-
table.bigInteger("acquired_at").notNullable();
|
|
57780
|
-
table.bigInteger("expires_at").notNullable();
|
|
57781
|
-
});
|
|
57782
|
-
}
|
|
57783
|
-
}
|
|
57784
|
-
getKnex() {
|
|
57785
|
-
if (!this.knex) {
|
|
57786
|
-
throw new Error("[KnexStore] Not initialized. Call initialize() first.");
|
|
57787
|
-
}
|
|
57788
|
-
return this.knex;
|
|
57789
|
-
}
|
|
57790
|
-
// --- CRUD ---
|
|
57791
|
-
async create(schedule) {
|
|
57792
|
-
const knex = this.getKnex();
|
|
57793
|
-
const newSchedule = {
|
|
57794
|
-
...schedule,
|
|
57795
|
-
id: (0, import_uuid2.v4)(),
|
|
57796
|
-
createdAt: Date.now(),
|
|
57797
|
-
runCount: 0,
|
|
57798
|
-
failureCount: 0,
|
|
57799
|
-
status: "active"
|
|
57800
|
-
};
|
|
57801
|
-
await knex("schedules").insert(toInsertRow(newSchedule));
|
|
57802
|
-
logger.info(`[KnexStore] Created schedule ${newSchedule.id} for user ${newSchedule.creatorId}`);
|
|
57803
|
-
return newSchedule;
|
|
57804
|
-
}
|
|
57805
|
-
async importSchedule(schedule) {
|
|
57806
|
-
const knex = this.getKnex();
|
|
57807
|
-
const existing = await knex("schedules").where("id", schedule.id).first();
|
|
57808
|
-
if (existing) return;
|
|
57809
|
-
await knex("schedules").insert(toInsertRow(schedule));
|
|
57810
|
-
}
|
|
57811
|
-
async get(id) {
|
|
57812
|
-
const knex = this.getKnex();
|
|
57813
|
-
const row = await knex("schedules").where("id", id).first();
|
|
57814
|
-
return row ? fromDbRow2(row) : void 0;
|
|
57815
|
-
}
|
|
57816
|
-
async update(id, patch) {
|
|
57817
|
-
const knex = this.getKnex();
|
|
57818
|
-
const existing = await knex("schedules").where("id", id).first();
|
|
57819
|
-
if (!existing) return void 0;
|
|
57820
|
-
const current = fromDbRow2(existing);
|
|
57821
|
-
const updated = { ...current, ...patch, id: current.id };
|
|
57822
|
-
const row = toInsertRow(updated);
|
|
57823
|
-
delete row.id;
|
|
57824
|
-
await knex("schedules").where("id", id).update(row);
|
|
57825
|
-
return updated;
|
|
57826
|
-
}
|
|
57827
|
-
async delete(id) {
|
|
57828
|
-
const knex = this.getKnex();
|
|
57829
|
-
const deleted = await knex("schedules").where("id", id).del();
|
|
57830
|
-
if (deleted > 0) {
|
|
57831
|
-
logger.info(`[KnexStore] Deleted schedule ${id}`);
|
|
57832
|
-
return true;
|
|
57833
|
-
}
|
|
57834
|
-
return false;
|
|
57835
|
-
}
|
|
57836
|
-
// --- Queries ---
|
|
57837
|
-
async getByCreator(creatorId) {
|
|
57838
|
-
const knex = this.getKnex();
|
|
57839
|
-
const rows = await knex("schedules").where("creator_id", creatorId);
|
|
57840
|
-
return rows.map((r) => fromDbRow2(r));
|
|
57841
|
-
}
|
|
57842
|
-
async getActiveSchedules() {
|
|
57843
|
-
const knex = this.getKnex();
|
|
57844
|
-
const rows = await knex("schedules").where("status", "active");
|
|
57845
|
-
return rows.map((r) => fromDbRow2(r));
|
|
57846
|
-
}
|
|
57847
|
-
async getDueSchedules(now) {
|
|
57848
|
-
const ts = now ?? Date.now();
|
|
57849
|
-
const knex = this.getKnex();
|
|
57850
|
-
const bFalse = this.driver === "mssql" ? 0 : false;
|
|
57851
|
-
const bTrue = this.driver === "mssql" ? 1 : true;
|
|
57852
|
-
const rows = await knex("schedules").where("status", "active").andWhere(function() {
|
|
57853
|
-
this.where(function() {
|
|
57854
|
-
this.where("is_recurring", bFalse).whereNotNull("run_at").where("run_at", "<=", ts);
|
|
57855
|
-
}).orWhere(function() {
|
|
57856
|
-
this.where("is_recurring", bTrue).whereNotNull("next_run_at").where("next_run_at", "<=", ts);
|
|
57857
|
-
});
|
|
57858
|
-
});
|
|
57859
|
-
return rows.map((r) => fromDbRow2(r));
|
|
57860
|
-
}
|
|
57861
|
-
async findByWorkflow(creatorId, workflowName) {
|
|
57862
|
-
const knex = this.getKnex();
|
|
57863
|
-
const escaped = workflowName.toLowerCase().replace(/[%_\\]/g, "\\$&");
|
|
57864
|
-
const pattern = `%${escaped}%`;
|
|
57865
|
-
const rows = await knex("schedules").where("creator_id", creatorId).where("status", "active").whereRaw("LOWER(workflow) LIKE ? ESCAPE '\\'", [pattern]);
|
|
57866
|
-
return rows.map((r) => fromDbRow2(r));
|
|
57867
|
-
}
|
|
57868
|
-
async getAll() {
|
|
57869
|
-
const knex = this.getKnex();
|
|
57870
|
-
const rows = await knex("schedules");
|
|
57871
|
-
return rows.map((r) => fromDbRow2(r));
|
|
57872
|
-
}
|
|
57873
|
-
async getStats() {
|
|
57874
|
-
const knex = this.getKnex();
|
|
57875
|
-
const boolTrue = this.driver === "mssql" ? "1" : "true";
|
|
57876
|
-
const boolFalse = this.driver === "mssql" ? "0" : "false";
|
|
57877
|
-
const result = await knex("schedules").select(
|
|
57878
|
-
knex.raw("COUNT(*) as total"),
|
|
57879
|
-
knex.raw("SUM(CASE WHEN status = 'active' THEN 1 ELSE 0 END) as active"),
|
|
57880
|
-
knex.raw("SUM(CASE WHEN status = 'paused' THEN 1 ELSE 0 END) as paused"),
|
|
57881
|
-
knex.raw("SUM(CASE WHEN status = 'completed' THEN 1 ELSE 0 END) as completed"),
|
|
57882
|
-
knex.raw("SUM(CASE WHEN status = 'failed' THEN 1 ELSE 0 END) as failed"),
|
|
57883
|
-
knex.raw(`SUM(CASE WHEN is_recurring = ${boolTrue} THEN 1 ELSE 0 END) as recurring`),
|
|
57884
|
-
knex.raw(`SUM(CASE WHEN is_recurring = ${boolFalse} THEN 1 ELSE 0 END) as one_time`)
|
|
57885
|
-
).first();
|
|
57886
|
-
return {
|
|
57887
|
-
total: Number(result.total) || 0,
|
|
57888
|
-
active: Number(result.active) || 0,
|
|
57889
|
-
paused: Number(result.paused) || 0,
|
|
57890
|
-
completed: Number(result.completed) || 0,
|
|
57891
|
-
failed: Number(result.failed) || 0,
|
|
57892
|
-
recurring: Number(result.recurring) || 0,
|
|
57893
|
-
oneTime: Number(result.one_time) || 0
|
|
57894
|
-
};
|
|
57895
|
-
}
|
|
57896
|
-
async validateLimits(creatorId, isRecurring, limits) {
|
|
57897
|
-
const knex = this.getKnex();
|
|
57898
|
-
if (limits.maxGlobal) {
|
|
57899
|
-
const result = await knex("schedules").count("* as cnt").first();
|
|
57900
|
-
if (Number(result?.cnt) >= limits.maxGlobal) {
|
|
57901
|
-
throw new Error(`Global schedule limit reached (${limits.maxGlobal})`);
|
|
57902
|
-
}
|
|
57903
|
-
}
|
|
57904
|
-
if (limits.maxPerUser) {
|
|
57905
|
-
const result = await knex("schedules").where("creator_id", creatorId).count("* as cnt").first();
|
|
57906
|
-
if (Number(result?.cnt) >= limits.maxPerUser) {
|
|
57907
|
-
throw new Error(`You have reached the maximum number of schedules (${limits.maxPerUser})`);
|
|
57908
|
-
}
|
|
57909
|
-
}
|
|
57910
|
-
if (isRecurring && limits.maxRecurringPerUser) {
|
|
57911
|
-
const bTrue = this.driver === "mssql" ? 1 : true;
|
|
57912
|
-
const result = await knex("schedules").where("creator_id", creatorId).where("is_recurring", bTrue).count("* as cnt").first();
|
|
57913
|
-
if (Number(result?.cnt) >= limits.maxRecurringPerUser) {
|
|
57914
|
-
throw new Error(
|
|
57915
|
-
`You have reached the maximum number of recurring schedules (${limits.maxRecurringPerUser})`
|
|
57916
|
-
);
|
|
57917
|
-
}
|
|
57918
|
-
}
|
|
57919
|
-
}
|
|
57920
|
-
// --- HA Distributed Locking (via scheduler_locks table) ---
|
|
57921
|
-
async tryAcquireLock(lockId, nodeId, ttlSeconds) {
|
|
57922
|
-
const knex = this.getKnex();
|
|
57923
|
-
const now = Date.now();
|
|
57924
|
-
const expiresAt = now + ttlSeconds * 1e3;
|
|
57925
|
-
const token = (0, import_uuid2.v4)();
|
|
57926
|
-
const updated = await knex("scheduler_locks").where("lock_id", lockId).where("expires_at", "<", now).update({
|
|
57927
|
-
node_id: nodeId,
|
|
57928
|
-
lock_token: token,
|
|
57929
|
-
acquired_at: now,
|
|
57930
|
-
expires_at: expiresAt
|
|
57931
|
-
});
|
|
57932
|
-
if (updated > 0) return token;
|
|
57933
|
-
try {
|
|
57934
|
-
await knex("scheduler_locks").insert({
|
|
57935
|
-
lock_id: lockId,
|
|
57936
|
-
node_id: nodeId,
|
|
57937
|
-
lock_token: token,
|
|
57938
|
-
acquired_at: now,
|
|
57939
|
-
expires_at: expiresAt
|
|
57940
|
-
});
|
|
57941
|
-
return token;
|
|
57942
|
-
} catch {
|
|
57943
|
-
return null;
|
|
57944
|
-
}
|
|
57945
|
-
}
|
|
57946
|
-
async releaseLock(lockId, lockToken) {
|
|
57947
|
-
const knex = this.getKnex();
|
|
57948
|
-
await knex("scheduler_locks").where("lock_id", lockId).where("lock_token", lockToken).del();
|
|
57949
|
-
}
|
|
57950
|
-
async renewLock(lockId, lockToken, ttlSeconds) {
|
|
57951
|
-
const knex = this.getKnex();
|
|
57952
|
-
const now = Date.now();
|
|
57953
|
-
const expiresAt = now + ttlSeconds * 1e3;
|
|
57954
|
-
const updated = await knex("scheduler_locks").where("lock_id", lockId).where("lock_token", lockToken).update({ acquired_at: now, expires_at: expiresAt });
|
|
57955
|
-
return updated > 0;
|
|
57956
|
-
}
|
|
57957
|
-
async flush() {
|
|
57958
|
-
}
|
|
57959
|
-
// --- Message Trigger CRUD ---
|
|
57960
|
-
async createTrigger(trigger) {
|
|
57961
|
-
const knex = this.getKnex();
|
|
57962
|
-
const newTrigger = {
|
|
57963
|
-
...trigger,
|
|
57964
|
-
id: (0, import_uuid2.v4)(),
|
|
57965
|
-
createdAt: Date.now()
|
|
57966
|
-
};
|
|
57967
|
-
await knex("message_triggers").insert(toTriggerInsertRow(newTrigger));
|
|
57968
|
-
logger.info(`[KnexStore] Created trigger ${newTrigger.id} for user ${newTrigger.creatorId}`);
|
|
57969
|
-
return newTrigger;
|
|
57970
|
-
}
|
|
57971
|
-
async getTrigger(id) {
|
|
57972
|
-
const knex = this.getKnex();
|
|
57973
|
-
const row = await knex("message_triggers").where("id", id).first();
|
|
57974
|
-
return row ? fromTriggerRow2(row) : void 0;
|
|
57975
|
-
}
|
|
57976
|
-
async updateTrigger(id, patch) {
|
|
57977
|
-
const knex = this.getKnex();
|
|
57978
|
-
const existing = await knex("message_triggers").where("id", id).first();
|
|
57979
|
-
if (!existing) return void 0;
|
|
57980
|
-
const current = fromTriggerRow2(existing);
|
|
57981
|
-
const updated = {
|
|
57982
|
-
...current,
|
|
57983
|
-
...patch,
|
|
57984
|
-
id: current.id,
|
|
57985
|
-
createdAt: current.createdAt
|
|
57986
|
-
};
|
|
57987
|
-
const row = toTriggerInsertRow(updated);
|
|
57988
|
-
delete row.id;
|
|
57989
|
-
await knex("message_triggers").where("id", id).update(row);
|
|
57990
|
-
return updated;
|
|
57991
|
-
}
|
|
57992
|
-
async deleteTrigger(id) {
|
|
57993
|
-
const knex = this.getKnex();
|
|
57994
|
-
const deleted = await knex("message_triggers").where("id", id).del();
|
|
57995
|
-
if (deleted > 0) {
|
|
57996
|
-
logger.info(`[KnexStore] Deleted trigger ${id}`);
|
|
57997
|
-
return true;
|
|
57998
|
-
}
|
|
57999
|
-
return false;
|
|
58000
|
-
}
|
|
58001
|
-
async getTriggersByCreator(creatorId) {
|
|
58002
|
-
const knex = this.getKnex();
|
|
58003
|
-
const rows = await knex("message_triggers").where("creator_id", creatorId);
|
|
58004
|
-
return rows.map((r) => fromTriggerRow2(r));
|
|
58005
|
-
}
|
|
58006
|
-
async getActiveTriggers() {
|
|
58007
|
-
const knex = this.getKnex();
|
|
58008
|
-
const rows = await knex("message_triggers").where("status", "active").where("enabled", this.driver === "mssql" ? 1 : true);
|
|
58009
|
-
return rows.map((r) => fromTriggerRow2(r));
|
|
58010
|
-
}
|
|
58011
|
-
};
|
|
58012
|
-
}
|
|
58013
|
-
});
|
|
58014
|
-
|
|
58015
|
-
// src/enterprise/loader.ts
|
|
58016
|
-
var loader_exports = {};
|
|
58017
|
-
__export(loader_exports, {
|
|
58018
|
-
loadEnterprisePolicyEngine: () => loadEnterprisePolicyEngine,
|
|
58019
|
-
loadEnterpriseStoreBackend: () => loadEnterpriseStoreBackend
|
|
58020
|
-
});
|
|
58021
|
-
async function loadEnterprisePolicyEngine(config) {
|
|
58022
|
-
try {
|
|
58023
|
-
const { LicenseValidator: LicenseValidator2 } = await Promise.resolve().then(() => (init_validator(), validator_exports));
|
|
58024
|
-
const validator = new LicenseValidator2();
|
|
58025
|
-
const license = await validator.loadAndValidate();
|
|
58026
|
-
if (!license || !validator.hasFeature("policy")) {
|
|
58027
|
-
return new DefaultPolicyEngine();
|
|
58028
|
-
}
|
|
58029
|
-
if (validator.isInGracePeriod()) {
|
|
58030
|
-
console.warn(
|
|
58031
|
-
"[visor:enterprise] License has expired but is within the 72-hour grace period. Please renew your license."
|
|
58032
|
-
);
|
|
58033
|
-
}
|
|
58034
|
-
const { OpaPolicyEngine: OpaPolicyEngine2 } = await Promise.resolve().then(() => (init_opa_policy_engine(), opa_policy_engine_exports));
|
|
58035
|
-
const engine = new OpaPolicyEngine2(config);
|
|
58036
|
-
await engine.initialize(config);
|
|
58037
|
-
return engine;
|
|
58038
|
-
} catch (err) {
|
|
58039
|
-
const msg = err instanceof Error ? err.message : String(err);
|
|
58040
|
-
try {
|
|
58041
|
-
const { logger: logger2 } = (init_logger(), __toCommonJS(logger_exports));
|
|
58042
|
-
logger2.warn(`[PolicyEngine] Enterprise policy init failed, falling back to default: ${msg}`);
|
|
58043
|
-
} catch {
|
|
58044
|
-
}
|
|
58045
|
-
return new DefaultPolicyEngine();
|
|
58046
|
-
}
|
|
58047
|
-
}
|
|
58048
|
-
async function loadEnterpriseStoreBackend(driver, storageConfig, haConfig) {
|
|
58049
|
-
const { LicenseValidator: LicenseValidator2 } = await Promise.resolve().then(() => (init_validator(), validator_exports));
|
|
58050
|
-
const validator = new LicenseValidator2();
|
|
58051
|
-
const license = await validator.loadAndValidate();
|
|
58052
|
-
if (!license || !validator.hasFeature("scheduler-sql")) {
|
|
58053
|
-
throw new Error(
|
|
58054
|
-
`The ${driver} schedule storage driver requires a Visor Enterprise license with the 'scheduler-sql' feature. Please upgrade or use driver: 'sqlite' (default).`
|
|
58055
|
-
);
|
|
58056
|
-
}
|
|
58057
|
-
if (validator.isInGracePeriod()) {
|
|
58058
|
-
console.warn(
|
|
58059
|
-
"[visor:enterprise] License has expired but is within the 72-hour grace period. Please renew your license."
|
|
58060
|
-
);
|
|
58061
|
-
}
|
|
58062
|
-
const { KnexStoreBackend: KnexStoreBackend2 } = await Promise.resolve().then(() => (init_knex_store(), knex_store_exports));
|
|
58063
|
-
return new KnexStoreBackend2(driver, storageConfig, haConfig);
|
|
58064
|
-
}
|
|
58065
|
-
var init_loader = __esm({
|
|
58066
|
-
"src/enterprise/loader.ts"() {
|
|
58067
|
-
"use strict";
|
|
58068
|
-
init_default_engine();
|
|
58069
|
-
}
|
|
58070
|
-
});
|
|
58071
|
-
|
|
58072
56698
|
// src/event-bus/event-bus.ts
|
|
58073
56699
|
var event_bus_exports = {};
|
|
58074
56700
|
__export(event_bus_exports, {
|
|
@@ -58975,8 +57601,8 @@ ${content}
|
|
|
58975
57601
|
* Sleep utility
|
|
58976
57602
|
*/
|
|
58977
57603
|
sleep(ms) {
|
|
58978
|
-
return new Promise((
|
|
58979
|
-
const t = setTimeout(
|
|
57604
|
+
return new Promise((resolve15) => {
|
|
57605
|
+
const t = setTimeout(resolve15, ms);
|
|
58980
57606
|
if (typeof t.unref === "function") {
|
|
58981
57607
|
try {
|
|
58982
57608
|
t.unref();
|
|
@@ -59261,8 +57887,8 @@ ${end}`);
|
|
|
59261
57887
|
async updateGroupedComment(ctx, comments, group, changedIds) {
|
|
59262
57888
|
const existingLock = this.updateLocks.get(group);
|
|
59263
57889
|
let resolveLock;
|
|
59264
|
-
const ourLock = new Promise((
|
|
59265
|
-
resolveLock =
|
|
57890
|
+
const ourLock = new Promise((resolve15) => {
|
|
57891
|
+
resolveLock = resolve15;
|
|
59266
57892
|
});
|
|
59267
57893
|
this.updateLocks.set(group, ourLock);
|
|
59268
57894
|
try {
|
|
@@ -59593,7 +58219,7 @@ ${blocks}
|
|
|
59593
58219
|
* Sleep utility for enforcing delays
|
|
59594
58220
|
*/
|
|
59595
58221
|
sleep(ms) {
|
|
59596
|
-
return new Promise((
|
|
58222
|
+
return new Promise((resolve15) => setTimeout(resolve15, ms));
|
|
59597
58223
|
}
|
|
59598
58224
|
};
|
|
59599
58225
|
}
|
|
@@ -61440,11 +60066,11 @@ var require_request3 = __commonJS({
|
|
|
61440
60066
|
"use strict";
|
|
61441
60067
|
var __awaiter = exports2 && exports2.__awaiter || function(thisArg, _arguments, P, generator) {
|
|
61442
60068
|
function adopt(value) {
|
|
61443
|
-
return value instanceof P ? value : new P(function(
|
|
61444
|
-
|
|
60069
|
+
return value instanceof P ? value : new P(function(resolve15) {
|
|
60070
|
+
resolve15(value);
|
|
61445
60071
|
});
|
|
61446
60072
|
}
|
|
61447
|
-
return new (P || (P = Promise))(function(
|
|
60073
|
+
return new (P || (P = Promise))(function(resolve15, reject) {
|
|
61448
60074
|
function fulfilled(value) {
|
|
61449
60075
|
try {
|
|
61450
60076
|
step(generator.next(value));
|
|
@@ -61460,7 +60086,7 @@ var require_request3 = __commonJS({
|
|
|
61460
60086
|
}
|
|
61461
60087
|
}
|
|
61462
60088
|
function step(result) {
|
|
61463
|
-
result.done ?
|
|
60089
|
+
result.done ? resolve15(result.value) : adopt(result.value).then(fulfilled, rejected);
|
|
61464
60090
|
}
|
|
61465
60091
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
61466
60092
|
});
|
|
@@ -61484,9 +60110,9 @@ var require_request3 = __commonJS({
|
|
|
61484
60110
|
HttpMethod2["PATCH"] = "PATCH";
|
|
61485
60111
|
})(HttpMethod = exports2.HttpMethod || (exports2.HttpMethod = {}));
|
|
61486
60112
|
var SvixRequest = class {
|
|
61487
|
-
constructor(method,
|
|
60113
|
+
constructor(method, path29) {
|
|
61488
60114
|
this.method = method;
|
|
61489
|
-
this.path =
|
|
60115
|
+
this.path = path29;
|
|
61490
60116
|
this.queryParams = {};
|
|
61491
60117
|
this.headerParams = {};
|
|
61492
60118
|
}
|
|
@@ -61589,7 +60215,7 @@ var require_request3 = __commonJS({
|
|
|
61589
60215
|
}
|
|
61590
60216
|
function sendWithRetry(url, init, retryScheduleInMs, nextInterval = 50, triesLeft = 2, fetchImpl = fetch, retryCount = 1) {
|
|
61591
60217
|
return __awaiter(this, void 0, void 0, function* () {
|
|
61592
|
-
const sleep = (interval) => new Promise((
|
|
60218
|
+
const sleep = (interval) => new Promise((resolve15) => setTimeout(resolve15, interval));
|
|
61593
60219
|
try {
|
|
61594
60220
|
const response = yield fetchImpl(url, init);
|
|
61595
60221
|
if (triesLeft <= 0 || response.status < 500) {
|
|
@@ -70663,7 +69289,7 @@ ${message}`;
|
|
|
70663
69289
|
});
|
|
70664
69290
|
|
|
70665
69291
|
// src/agent-protocol/task-store.ts
|
|
70666
|
-
function
|
|
69292
|
+
function safeJsonParse2(value) {
|
|
70667
69293
|
if (!value) return void 0;
|
|
70668
69294
|
try {
|
|
70669
69295
|
return JSON.parse(value);
|
|
@@ -70680,12 +69306,12 @@ function taskRowToAgentTask(row) {
|
|
|
70680
69306
|
context_id: row.context_id,
|
|
70681
69307
|
status: {
|
|
70682
69308
|
state: row.state,
|
|
70683
|
-
message:
|
|
69309
|
+
message: safeJsonParse2(row.status_message),
|
|
70684
69310
|
timestamp: row.updated_at
|
|
70685
69311
|
},
|
|
70686
|
-
artifacts:
|
|
70687
|
-
history:
|
|
70688
|
-
metadata:
|
|
69312
|
+
artifacts: safeJsonParse2(row.artifacts) ?? [],
|
|
69313
|
+
history: safeJsonParse2(row.history) ?? [],
|
|
69314
|
+
metadata: safeJsonParse2(row.request_metadata),
|
|
70689
69315
|
workflow_id: row.workflow_id ?? void 0
|
|
70690
69316
|
};
|
|
70691
69317
|
}
|
|
@@ -70922,7 +69548,7 @@ var init_task_store = __esm({
|
|
|
70922
69548
|
const db = this.getDb();
|
|
70923
69549
|
const row = db.prepare("SELECT artifacts FROM agent_tasks WHERE id = ?").get(taskId);
|
|
70924
69550
|
if (!row) throw new TaskNotFoundError(taskId);
|
|
70925
|
-
const artifacts =
|
|
69551
|
+
const artifacts = safeJsonParse2(row.artifacts) ?? [];
|
|
70926
69552
|
artifacts.push(artifact);
|
|
70927
69553
|
db.prepare("UPDATE agent_tasks SET artifacts = ?, updated_at = ? WHERE id = ?").run(
|
|
70928
69554
|
JSON.stringify(artifacts),
|
|
@@ -70934,7 +69560,7 @@ var init_task_store = __esm({
|
|
|
70934
69560
|
const db = this.getDb();
|
|
70935
69561
|
const row = db.prepare("SELECT history FROM agent_tasks WHERE id = ?").get(taskId);
|
|
70936
69562
|
if (!row) throw new TaskNotFoundError(taskId);
|
|
70937
|
-
const history =
|
|
69563
|
+
const history = safeJsonParse2(row.history) ?? [];
|
|
70938
69564
|
history.push(message);
|
|
70939
69565
|
db.prepare("UPDATE agent_tasks SET history = ?, updated_at = ? WHERE id = ?").run(
|
|
70940
69566
|
JSON.stringify(history),
|
|
@@ -71446,13 +70072,13 @@ __export(a2a_frontend_exports, {
|
|
|
71446
70072
|
resultToArtifacts: () => resultToArtifacts
|
|
71447
70073
|
});
|
|
71448
70074
|
function readJsonBody(req) {
|
|
71449
|
-
return new Promise((
|
|
70075
|
+
return new Promise((resolve15, reject) => {
|
|
71450
70076
|
const chunks = [];
|
|
71451
70077
|
req.on("data", (chunk) => chunks.push(chunk));
|
|
71452
70078
|
req.on("end", () => {
|
|
71453
70079
|
try {
|
|
71454
70080
|
const body = Buffer.concat(chunks).toString("utf8");
|
|
71455
|
-
|
|
70081
|
+
resolve15(body ? JSON.parse(body) : {});
|
|
71456
70082
|
} catch {
|
|
71457
70083
|
reject(new ParseError("Malformed JSON body"));
|
|
71458
70084
|
}
|
|
@@ -71695,12 +70321,12 @@ var init_a2a_frontend = __esm({
|
|
|
71695
70321
|
}
|
|
71696
70322
|
const port = this.config.port ?? 9e3;
|
|
71697
70323
|
const host = this.config.host ?? "0.0.0.0";
|
|
71698
|
-
await new Promise((
|
|
70324
|
+
await new Promise((resolve15) => {
|
|
71699
70325
|
this.server.listen(port, host, () => {
|
|
71700
70326
|
const addr = this.server.address();
|
|
71701
70327
|
this._boundPort = typeof addr === "object" && addr ? addr.port : port;
|
|
71702
70328
|
logger.info(`A2A server listening on ${host}:${this._boundPort}`);
|
|
71703
|
-
|
|
70329
|
+
resolve15();
|
|
71704
70330
|
});
|
|
71705
70331
|
});
|
|
71706
70332
|
if (this.agentCard) {
|
|
@@ -71724,8 +70350,8 @@ var init_a2a_frontend = __esm({
|
|
|
71724
70350
|
}
|
|
71725
70351
|
this.streamManager.shutdown();
|
|
71726
70352
|
if (this.server) {
|
|
71727
|
-
await new Promise((
|
|
71728
|
-
this.server.close((err) => err ? reject(err) :
|
|
70353
|
+
await new Promise((resolve15, reject) => {
|
|
70354
|
+
this.server.close((err) => err ? reject(err) : resolve15());
|
|
71729
70355
|
});
|
|
71730
70356
|
this.server = null;
|
|
71731
70357
|
}
|
|
@@ -72442,15 +71068,15 @@ function serializeRunState(state) {
|
|
|
72442
71068
|
])
|
|
72443
71069
|
};
|
|
72444
71070
|
}
|
|
72445
|
-
var
|
|
71071
|
+
var path28, fs24, StateMachineExecutionEngine;
|
|
72446
71072
|
var init_state_machine_execution_engine = __esm({
|
|
72447
71073
|
"src/state-machine-execution-engine.ts"() {
|
|
72448
71074
|
"use strict";
|
|
72449
71075
|
init_runner();
|
|
72450
71076
|
init_logger();
|
|
72451
71077
|
init_sandbox_manager();
|
|
72452
|
-
|
|
72453
|
-
|
|
71078
|
+
path28 = __toESM(require("path"));
|
|
71079
|
+
fs24 = __toESM(require("fs"));
|
|
72454
71080
|
StateMachineExecutionEngine = class _StateMachineExecutionEngine {
|
|
72455
71081
|
workingDirectory;
|
|
72456
71082
|
executionContext;
|
|
@@ -72682,8 +71308,8 @@ var init_state_machine_execution_engine = __esm({
|
|
|
72682
71308
|
logger.debug(
|
|
72683
71309
|
`[PolicyEngine] Loading enterprise policy engine (engine=${configWithTagFilter.policy.engine})`
|
|
72684
71310
|
);
|
|
72685
|
-
const { loadEnterprisePolicyEngine
|
|
72686
|
-
context2.policyEngine = await
|
|
71311
|
+
const { loadEnterprisePolicyEngine } = await import("./enterprise/loader");
|
|
71312
|
+
context2.policyEngine = await loadEnterprisePolicyEngine(configWithTagFilter.policy);
|
|
72687
71313
|
logger.debug(
|
|
72688
71314
|
`[PolicyEngine] Initialized: ${context2.policyEngine?.constructor?.name || "unknown"}`
|
|
72689
71315
|
);
|
|
@@ -72837,9 +71463,9 @@ var init_state_machine_execution_engine = __esm({
|
|
|
72837
71463
|
}
|
|
72838
71464
|
const checkId = String(ev?.checkId || "unknown");
|
|
72839
71465
|
const threadKey = ev?.threadKey || (channel && threadTs ? `${channel}:${threadTs}` : "session");
|
|
72840
|
-
const baseDir = process.env.VISOR_SNAPSHOT_DIR ||
|
|
72841
|
-
|
|
72842
|
-
const filePath =
|
|
71466
|
+
const baseDir = process.env.VISOR_SNAPSHOT_DIR || path28.resolve(process.cwd(), ".visor", "snapshots");
|
|
71467
|
+
fs24.mkdirSync(baseDir, { recursive: true });
|
|
71468
|
+
const filePath = path28.join(baseDir, `${threadKey}-${checkId}.json`);
|
|
72843
71469
|
await this.saveSnapshotToFile(filePath);
|
|
72844
71470
|
logger.info(`[Snapshot] Saved run snapshot: ${filePath}`);
|
|
72845
71471
|
try {
|
|
@@ -72980,7 +71606,7 @@ var init_state_machine_execution_engine = __esm({
|
|
|
72980
71606
|
* Does not include secrets. Intended for debugging and future resume support.
|
|
72981
71607
|
*/
|
|
72982
71608
|
async saveSnapshotToFile(filePath) {
|
|
72983
|
-
const
|
|
71609
|
+
const fs25 = await import("fs/promises");
|
|
72984
71610
|
const ctx = this._lastContext;
|
|
72985
71611
|
const runner = this._lastRunner;
|
|
72986
71612
|
if (!ctx || !runner) {
|
|
@@ -73000,14 +71626,14 @@ var init_state_machine_execution_engine = __esm({
|
|
|
73000
71626
|
journal: entries,
|
|
73001
71627
|
requestedChecks: ctx.requestedChecks || []
|
|
73002
71628
|
};
|
|
73003
|
-
await
|
|
71629
|
+
await fs25.writeFile(filePath, JSON.stringify(payload, null, 2), "utf8");
|
|
73004
71630
|
}
|
|
73005
71631
|
/**
|
|
73006
71632
|
* Load a snapshot JSON from file and return it. Resume support can build on this.
|
|
73007
71633
|
*/
|
|
73008
71634
|
async loadSnapshotFromFile(filePath) {
|
|
73009
|
-
const
|
|
73010
|
-
const raw = await
|
|
71635
|
+
const fs25 = await import("fs/promises");
|
|
71636
|
+
const raw = await fs25.readFile(filePath, "utf8");
|
|
73011
71637
|
return JSON.parse(raw);
|
|
73012
71638
|
}
|
|
73013
71639
|
/**
|