@xdsjs/dossierx-daemon 0.1.16 → 0.1.17
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 +114 -12
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -2290,7 +2290,7 @@ function createTaskArchive(options) {
|
|
|
2290
2290
|
|
|
2291
2291
|
// src/version.ts
|
|
2292
2292
|
var DAEMON_PACKAGE_NAME = "@xdsjs/dossierx-daemon";
|
|
2293
|
-
var DAEMON_VERSION = "0.1.
|
|
2293
|
+
var DAEMON_VERSION = "0.1.17";
|
|
2294
2294
|
|
|
2295
2295
|
// src/local-api/server.ts
|
|
2296
2296
|
var DEFAULT_MAX_FILE_BYTES = 5 * 1024 * 1024;
|
|
@@ -2307,12 +2307,51 @@ function json(response, status, body, origin) {
|
|
|
2307
2307
|
});
|
|
2308
2308
|
response.end(JSON.stringify(body));
|
|
2309
2309
|
}
|
|
2310
|
+
function vercelProjectNameFromAllowedOrigin(origin) {
|
|
2311
|
+
try {
|
|
2312
|
+
const url = new URL(origin);
|
|
2313
|
+
if (url.protocol !== "https:" || !url.hostname.endsWith(".vercel.app")) {
|
|
2314
|
+
return null;
|
|
2315
|
+
}
|
|
2316
|
+
const label = url.hostname.slice(0, -".vercel.app".length);
|
|
2317
|
+
for (const suffix of ["-beta", "-production", "-prod", "-preview", "-staging"]) {
|
|
2318
|
+
if (label.endsWith(suffix) && label.length > suffix.length) {
|
|
2319
|
+
return label.slice(0, -suffix.length);
|
|
2320
|
+
}
|
|
2321
|
+
}
|
|
2322
|
+
return label;
|
|
2323
|
+
} catch {
|
|
2324
|
+
return null;
|
|
2325
|
+
}
|
|
2326
|
+
}
|
|
2327
|
+
function isVercelDeploymentOriginAllowed(origin, allowedOrigins) {
|
|
2328
|
+
let requested;
|
|
2329
|
+
try {
|
|
2330
|
+
requested = new URL(origin);
|
|
2331
|
+
} catch {
|
|
2332
|
+
return false;
|
|
2333
|
+
}
|
|
2334
|
+
if (requested.protocol !== "https:" || !requested.hostname.endsWith(".vercel.app")) {
|
|
2335
|
+
return false;
|
|
2336
|
+
}
|
|
2337
|
+
const requestedLabel = requested.hostname.slice(0, -".vercel.app".length);
|
|
2338
|
+
return allowedOrigins.some((allowedOriginValue) => {
|
|
2339
|
+
const projectName = vercelProjectNameFromAllowedOrigin(allowedOriginValue);
|
|
2340
|
+
if (!projectName) {
|
|
2341
|
+
return false;
|
|
2342
|
+
}
|
|
2343
|
+
const deploymentPattern = new RegExp(
|
|
2344
|
+
`^${projectName.replace(/[.*+?^${}()|[\]\\]/g, "\\$&")}-[a-z0-9]+-[a-z0-9-]+$`
|
|
2345
|
+
);
|
|
2346
|
+
return requestedLabel === projectName || deploymentPattern.test(requestedLabel);
|
|
2347
|
+
});
|
|
2348
|
+
}
|
|
2310
2349
|
function allowedOrigin(request, allowedOrigins) {
|
|
2311
2350
|
const origin = request.headers.origin;
|
|
2312
2351
|
if (!origin) {
|
|
2313
2352
|
return "";
|
|
2314
2353
|
}
|
|
2315
|
-
return allowedOrigins.includes(origin) ? origin : null;
|
|
2354
|
+
return allowedOrigins.includes(origin) || isVercelDeploymentOriginAllowed(origin, allowedOrigins) ? origin : null;
|
|
2316
2355
|
}
|
|
2317
2356
|
function requestUrl(request) {
|
|
2318
2357
|
return new URL(request.url ?? "/", "http://127.0.0.1");
|
|
@@ -2545,16 +2584,40 @@ async function startWorkspaceReadServer(options) {
|
|
|
2545
2584
|
const taskArchive = options.taskArchive ?? createTaskArchive({ workspaceRoot: options.workspaceRoot });
|
|
2546
2585
|
const server = createServer((request, response) => {
|
|
2547
2586
|
void (async () => {
|
|
2587
|
+
const url = requestUrl(request);
|
|
2548
2588
|
const origin = allowedOrigin(request, options.allowedOrigins);
|
|
2549
2589
|
if (origin === null) {
|
|
2590
|
+
if (url.pathname === "/workspace/manifest") {
|
|
2591
|
+
console.warn(
|
|
2592
|
+
JSON.stringify({
|
|
2593
|
+
msg: "workspace manifest cors rejected",
|
|
2594
|
+
origin: request.headers.origin ?? null,
|
|
2595
|
+
requestedMethod: request.headers["access-control-request-method"] ?? null,
|
|
2596
|
+
requestedPrivateNetwork: request.headers["access-control-request-private-network"] ?? null,
|
|
2597
|
+
status: 403,
|
|
2598
|
+
error: "Origin not allowed"
|
|
2599
|
+
})
|
|
2600
|
+
);
|
|
2601
|
+
}
|
|
2550
2602
|
json(response, 403, { error: "Origin not allowed" });
|
|
2551
2603
|
return;
|
|
2552
2604
|
}
|
|
2553
2605
|
if (request.method === "OPTIONS") {
|
|
2606
|
+
if (url.pathname === "/workspace/manifest") {
|
|
2607
|
+
console.info(
|
|
2608
|
+
JSON.stringify({
|
|
2609
|
+
msg: "workspace manifest preflight served",
|
|
2610
|
+
origin,
|
|
2611
|
+
requestedMethod: request.headers["access-control-request-method"] ?? null,
|
|
2612
|
+
requestedPrivateNetwork: request.headers["access-control-request-private-network"] ?? null,
|
|
2613
|
+
status: 204,
|
|
2614
|
+
allowPrivateNetwork: true
|
|
2615
|
+
})
|
|
2616
|
+
);
|
|
2617
|
+
}
|
|
2554
2618
|
json(response, 204, {}, origin);
|
|
2555
2619
|
return;
|
|
2556
2620
|
}
|
|
2557
|
-
const url = requestUrl(request);
|
|
2558
2621
|
if (request.method === "GET" && url.pathname === "/runtime/codex") {
|
|
2559
2622
|
json(
|
|
2560
2623
|
response,
|
|
@@ -2614,26 +2677,65 @@ async function startWorkspaceReadServer(options) {
|
|
|
2614
2677
|
const ticker = url.searchParams.get("ticker");
|
|
2615
2678
|
const market = url.searchParams.get("market");
|
|
2616
2679
|
if (!ticker || !market) {
|
|
2680
|
+
console.warn(
|
|
2681
|
+
JSON.stringify({
|
|
2682
|
+
msg: "workspace manifest request rejected",
|
|
2683
|
+
origin,
|
|
2684
|
+
ticker,
|
|
2685
|
+
market,
|
|
2686
|
+
status: 400,
|
|
2687
|
+
error: "Missing ticker or market"
|
|
2688
|
+
})
|
|
2689
|
+
);
|
|
2617
2690
|
json(response, 400, { error: "Missing ticker or market" }, origin);
|
|
2618
2691
|
return;
|
|
2619
2692
|
}
|
|
2620
2693
|
try {
|
|
2621
|
-
|
|
2622
|
-
|
|
2623
|
-
|
|
2624
|
-
|
|
2625
|
-
|
|
2694
|
+
const body = await readCompanyManifest({
|
|
2695
|
+
workspaceRoot: options.workspaceRoot,
|
|
2696
|
+
ticker,
|
|
2697
|
+
market
|
|
2698
|
+
});
|
|
2699
|
+
const paths = body.manifest.pages.map((page) => page.path);
|
|
2700
|
+
console.info(
|
|
2701
|
+
JSON.stringify({
|
|
2702
|
+
msg: "workspace manifest served",
|
|
2703
|
+
origin,
|
|
2626
2704
|
ticker,
|
|
2627
|
-
market
|
|
2628
|
-
|
|
2629
|
-
|
|
2705
|
+
market,
|
|
2706
|
+
status: 200,
|
|
2707
|
+
pageCount: paths.length,
|
|
2708
|
+
hasNotebook: paths.some(
|
|
2709
|
+
(item) => item.endsWith("/financial-reports/notebooklm/notebook.json")
|
|
2710
|
+
),
|
|
2711
|
+
hasFactsBundle: paths.some(
|
|
2712
|
+
(item) => item.endsWith("/financial-reports/ingest/facts-bundle.json")
|
|
2713
|
+
),
|
|
2714
|
+
hasFinancialWiki: paths.some(
|
|
2715
|
+
(item) => item.endsWith(
|
|
2716
|
+
"/financial-reports/wiki/financial-report-analysis.md"
|
|
2717
|
+
)
|
|
2718
|
+
)
|
|
2719
|
+
})
|
|
2630
2720
|
);
|
|
2721
|
+
json(response, 200, body, origin);
|
|
2631
2722
|
} catch (error) {
|
|
2723
|
+
const message = error instanceof Error ? error.message : "Workspace manifest failed";
|
|
2724
|
+
console.warn(
|
|
2725
|
+
JSON.stringify({
|
|
2726
|
+
msg: "workspace manifest request failed",
|
|
2727
|
+
origin,
|
|
2728
|
+
ticker,
|
|
2729
|
+
market,
|
|
2730
|
+
status: 400,
|
|
2731
|
+
error: message
|
|
2732
|
+
})
|
|
2733
|
+
);
|
|
2632
2734
|
json(
|
|
2633
2735
|
response,
|
|
2634
2736
|
400,
|
|
2635
2737
|
{
|
|
2636
|
-
error:
|
|
2738
|
+
error: message
|
|
2637
2739
|
},
|
|
2638
2740
|
origin
|
|
2639
2741
|
);
|