siteplane 0.1.64 → 0.1.66
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +13 -0
- package/dist/bin/siteplane.js +214 -258
- package/dist/index.js +134 -178
- package/dist/next.d.ts +10 -0
- package/dist/next.js +175 -108
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -631,6 +631,7 @@ var bookingPublicConfigSchema = z9.object({
|
|
|
631
631
|
settings: z9.object({
|
|
632
632
|
slotIntervalMinutes: z9.number().int().positive(),
|
|
633
633
|
minLeadMinutes: z9.number().int().min(0),
|
|
634
|
+
minCancelLeadMinutes: z9.number().int().min(0),
|
|
634
635
|
maxAdvanceDays: z9.number().int().min(1),
|
|
635
636
|
requirePhone: z9.boolean(),
|
|
636
637
|
collectNote: z9.boolean(),
|
|
@@ -839,7 +840,7 @@ var bookingManifestSchema = z9.object({
|
|
|
839
840
|
siteId: z9.string().trim().min(1),
|
|
840
841
|
siteKeyPrefix: z9.string().startsWith("bk_pub_"),
|
|
841
842
|
bookingPageSlug: z9.string().regex(/^[a-z0-9]+(?:-[a-z0-9]+)*$/).min(2).max(64),
|
|
842
|
-
|
|
843
|
+
integration: z9.literal("rewrite").optional(),
|
|
843
844
|
productionOrigin: z9.string().url().optional()
|
|
844
845
|
}).passthrough();
|
|
845
846
|
var secretManifestKeys = /* @__PURE__ */ new Set([
|
|
@@ -2242,117 +2243,63 @@ function collectRedactedBookingKeys(input, prefix = "") {
|
|
|
2242
2243
|
}
|
|
2243
2244
|
|
|
2244
2245
|
// ../cli/dist/booking/static-scan.js
|
|
2246
|
+
import ts2 from "typescript";
|
|
2245
2247
|
function scanBookingSourceFiles(files, input) {
|
|
2246
|
-
const
|
|
2247
|
-
const
|
|
2248
|
-
const
|
|
2249
|
-
|
|
2250
|
-
|
|
2251
|
-
|
|
2248
|
+
const findings = [];
|
|
2249
|
+
const hardErrors = [];
|
|
2250
|
+
const warnings = [];
|
|
2251
|
+
for (const file of files) {
|
|
2252
|
+
let visit2 = function(node) {
|
|
2253
|
+
if (ts2.isCallExpression(node) && ts2.isIdentifier(node.expression) && node.expression.text === "withSiteplane") {
|
|
2254
|
+
const options = node.arguments[1];
|
|
2255
|
+
const booking = options && property(options, "booking");
|
|
2256
|
+
const site = booking && property(booking, "site");
|
|
2257
|
+
if (site && ts2.isStringLiteralLike(site)) {
|
|
2258
|
+
const issue = {
|
|
2259
|
+
code: site.text === input.siteId ? "booking_scan.integration_found" : "booking_scan.site_mismatch",
|
|
2260
|
+
message: site.text === input.siteId ? "Booking /booking rewrite configured for this Site ID." : "The Booking wrapper uses a different Site ID; use the Site ID supplied by Siteplane.",
|
|
2261
|
+
filePath: file.filePath
|
|
2262
|
+
};
|
|
2263
|
+
(site.text === input.siteId ? findings : hardErrors).push(issue);
|
|
2264
|
+
}
|
|
2265
|
+
}
|
|
2266
|
+
ts2.forEachChild(node, visit2);
|
|
2267
|
+
};
|
|
2268
|
+
var visit = visit2;
|
|
2269
|
+
const source = ts2.createSourceFile(file.filePath, file.sourceText, ts2.ScriptTarget.Latest, true, ts2.ScriptKind.TSX);
|
|
2270
|
+
visit2(source);
|
|
2271
|
+
}
|
|
2272
|
+
if (!findings.length && !hardErrors.length)
|
|
2273
|
+
hardErrors.push({
|
|
2274
|
+
code: "booking_scan.integration_missing",
|
|
2275
|
+
message: "Could not verify withSiteplane(nextConfig, { booking: { site: <site-id> } }). Include next.config.ts in the scan and use a literal Site ID.",
|
|
2276
|
+
filePath: "next.config.ts"
|
|
2277
|
+
});
|
|
2278
|
+
if (input.productionOrigin && !files.some((file) => file.sourceText.includes(input.productionOrigin)))
|
|
2279
|
+
warnings.push({
|
|
2280
|
+
code: "booking_scan.origin_not_detected",
|
|
2281
|
+
message: "Verify the public booking address and its allowed origins in Siteplane settings.",
|
|
2252
2282
|
filePath: "siteplane.booking.json"
|
|
2253
|
-
}
|
|
2254
|
-
] : [];
|
|
2255
|
-
const warnings = [
|
|
2256
|
-
...createPageSlugWarnings(embeds, input.bookingPageSlug),
|
|
2257
|
-
...createOriginWarnings(files, input.productionOrigin)
|
|
2258
|
-
];
|
|
2259
|
-
const selectedEmbed = selectManifestEmbed(embeds);
|
|
2260
|
-
const manifest = bookingManifestSchema.parse({
|
|
2261
|
-
schemaVersion: 1,
|
|
2262
|
-
siteId: input.siteId,
|
|
2263
|
-
siteKeyPrefix: input.siteKeyPrefix,
|
|
2264
|
-
bookingPageSlug: selectedEmbed?.pageSlug ?? input.bookingPageSlug,
|
|
2265
|
-
...selectedEmbed ? { embedMode: selectedEmbed.embedMode } : {},
|
|
2266
|
-
...input.productionOrigin ? { productionOrigin: input.productionOrigin } : {}
|
|
2267
|
-
});
|
|
2283
|
+
});
|
|
2268
2284
|
return {
|
|
2269
|
-
manifest
|
|
2285
|
+
manifest: bookingManifestSchema.parse({
|
|
2286
|
+
schemaVersion: 1,
|
|
2287
|
+
...input,
|
|
2288
|
+
integration: "rewrite"
|
|
2289
|
+
}),
|
|
2270
2290
|
findings,
|
|
2271
2291
|
hardErrors,
|
|
2272
2292
|
warnings,
|
|
2273
2293
|
suggestions: []
|
|
2274
2294
|
};
|
|
2275
2295
|
}
|
|
2276
|
-
function
|
|
2277
|
-
|
|
2278
|
-
|
|
2279
|
-
|
|
2280
|
-
|
|
2281
|
-
|
|
2282
|
-
embedMode: "script"
|
|
2283
|
-
});
|
|
2296
|
+
function property(node, name2) {
|
|
2297
|
+
if (!ts2.isObjectLiteralExpression(node))
|
|
2298
|
+
return;
|
|
2299
|
+
for (const item of node.properties) {
|
|
2300
|
+
if (ts2.isPropertyAssignment(item) && (ts2.isIdentifier(item.name) || ts2.isStringLiteral(item.name)) && item.name.text === name2)
|
|
2301
|
+
return item.initializer;
|
|
2284
2302
|
}
|
|
2285
|
-
if (/<siteplane-booking\b/u.test(source)) {
|
|
2286
|
-
const pageSlug = readAttributeValue(source, "booking-page-slug");
|
|
2287
|
-
embeds.push({
|
|
2288
|
-
filePath: file.filePath,
|
|
2289
|
-
embedMode: "web_component",
|
|
2290
|
-
...pageSlug ? { pageSlug } : {}
|
|
2291
|
-
});
|
|
2292
|
-
}
|
|
2293
|
-
for (const match of source.matchAll(/<iframe\b[^>]*>/giu)) {
|
|
2294
|
-
const tag = match[0];
|
|
2295
|
-
const src = readAttributeValue(tag, "src");
|
|
2296
|
-
const pageSlug = src ? readBookingPageSlug(src) : void 0;
|
|
2297
|
-
if (/data-siteplane-booking/u.test(tag) || pageSlug !== void 0) {
|
|
2298
|
-
embeds.push({
|
|
2299
|
-
filePath: file.filePath,
|
|
2300
|
-
embedMode: "iframe",
|
|
2301
|
-
...pageSlug ? { pageSlug } : {}
|
|
2302
|
-
});
|
|
2303
|
-
}
|
|
2304
|
-
}
|
|
2305
|
-
return embeds;
|
|
2306
|
-
}
|
|
2307
|
-
function createEmbedFoundIssue(embed) {
|
|
2308
|
-
return {
|
|
2309
|
-
code: "booking_scan.embed_found",
|
|
2310
|
-
message: "Siteplane Booking embed was found.",
|
|
2311
|
-
filePath: embed.filePath,
|
|
2312
|
-
embedMode: embed.embedMode,
|
|
2313
|
-
...embed.pageSlug ? { pageSlug: embed.pageSlug } : {}
|
|
2314
|
-
};
|
|
2315
|
-
}
|
|
2316
|
-
function createPageSlugWarnings(embeds, expectedSlug) {
|
|
2317
|
-
return embeds.filter((embed) => embed.pageSlug && embed.pageSlug !== expectedSlug).map((embed) => {
|
|
2318
|
-
const pageSlug = embed.pageSlug;
|
|
2319
|
-
return {
|
|
2320
|
-
code: "booking_scan.page_slug_mismatch",
|
|
2321
|
-
message: `Booking embed references page slug ${pageSlug}, but the manifest is configured for ${expectedSlug}.`,
|
|
2322
|
-
filePath: embed.filePath,
|
|
2323
|
-
embedMode: embed.embedMode,
|
|
2324
|
-
...pageSlug ? { pageSlug } : {}
|
|
2325
|
-
};
|
|
2326
|
-
});
|
|
2327
|
-
}
|
|
2328
|
-
function createOriginWarnings(files, productionOrigin) {
|
|
2329
|
-
if (!productionOrigin) {
|
|
2330
|
-
return [];
|
|
2331
|
-
}
|
|
2332
|
-
if (files.some((file) => file.sourceText.includes(productionOrigin))) {
|
|
2333
|
-
return [];
|
|
2334
|
-
}
|
|
2335
|
-
return [
|
|
2336
|
-
{
|
|
2337
|
-
code: "booking_scan.origin_not_detected",
|
|
2338
|
-
message: "The configured production origin was not found statically; verify it is registered as an allowed Booking origin in Siteplane.",
|
|
2339
|
-
filePath: "siteplane.booking.json"
|
|
2340
|
-
}
|
|
2341
|
-
];
|
|
2342
|
-
}
|
|
2343
|
-
function selectManifestEmbed(embeds) {
|
|
2344
|
-
return embeds.find((embed) => embed.embedMode === "web_component") ?? embeds.find((embed) => embed.embedMode === "iframe") ?? embeds[0];
|
|
2345
|
-
}
|
|
2346
|
-
function readAttributeValue(source, attributeName) {
|
|
2347
|
-
const escapedName = escapeRegExp(attributeName);
|
|
2348
|
-
const match = new RegExp(`${escapedName}\\s*=\\s*["']([^"']+)["']`, "iu").exec(source);
|
|
2349
|
-
return match?.[1];
|
|
2350
|
-
}
|
|
2351
|
-
function readBookingPageSlug(value) {
|
|
2352
|
-
return /\/book\/([a-z0-9]+(?:-[a-z0-9]+)*)(?:[/?#]|$)/u.exec(value)?.[1];
|
|
2353
|
-
}
|
|
2354
|
-
function escapeRegExp(value) {
|
|
2355
|
-
return value.replace(/[.*+?^${}()|[\]\\]/gu, "\\$&");
|
|
2356
2303
|
}
|
|
2357
2304
|
|
|
2358
2305
|
// ../cli/dist/commands/analytics/check.js
|
|
@@ -2455,10 +2402,17 @@ var errorSchema = z30.object({
|
|
|
2455
2402
|
import { randomUUID } from "crypto";
|
|
2456
2403
|
|
|
2457
2404
|
// ../cli/dist/commands/booking/check.js
|
|
2458
|
-
import {
|
|
2405
|
+
import { dirname as dirname4, join as join2 } from "path";
|
|
2406
|
+
import { access, readFile as readFile4 } from "fs/promises";
|
|
2459
2407
|
async function bookingCheckCommand(input) {
|
|
2460
2408
|
const validatedManifest = await readBookingManifestFile(input.manifestPath);
|
|
2461
|
-
const
|
|
2409
|
+
const configs = (await Promise.all(["next.config.ts", "next.config.js", "next.config.mjs"].map(async (name2) => {
|
|
2410
|
+
const path = join2(dirname4(input.manifestPath), name2);
|
|
2411
|
+
return await access(path).then(() => path, () => null);
|
|
2412
|
+
}))).filter((path) => path !== null);
|
|
2413
|
+
const sourceFiles = await readSourceFiles([
|
|
2414
|
+
.../* @__PURE__ */ new Set([...input.sourceFilePaths, ...configs])
|
|
2415
|
+
]);
|
|
2462
2416
|
const scanInput = {
|
|
2463
2417
|
siteId: validatedManifest.manifest.siteId,
|
|
2464
2418
|
siteKeyPrefix: validatedManifest.manifest.siteKeyPrefix,
|
|
@@ -2499,7 +2453,7 @@ function createBoundaryErrors(validation) {
|
|
|
2499
2453
|
|
|
2500
2454
|
// ../cli/dist/commands/booking/init.js
|
|
2501
2455
|
import { mkdir as mkdir4, writeFile as writeFile4 } from "fs/promises";
|
|
2502
|
-
import { dirname as
|
|
2456
|
+
import { dirname as dirname5, join as join3 } from "path";
|
|
2503
2457
|
async function bookingInitCommand(input) {
|
|
2504
2458
|
const manifest = {
|
|
2505
2459
|
schemaVersion: 1,
|
|
@@ -2508,7 +2462,7 @@ async function bookingInitCommand(input) {
|
|
|
2508
2462
|
bookingPageSlug: input.bookingPageSlug,
|
|
2509
2463
|
...input.productionOrigin ? { productionOrigin: input.productionOrigin } : {}
|
|
2510
2464
|
};
|
|
2511
|
-
const manifestPath =
|
|
2465
|
+
const manifestPath = join3(input.projectDir, "siteplane.booking.json");
|
|
2512
2466
|
const artifacts = createBookingArtifacts(input.agentClient);
|
|
2513
2467
|
await writeBookingManifestFile(manifestPath, manifest);
|
|
2514
2468
|
for (const artifact of artifacts) {
|
|
@@ -2548,16 +2502,18 @@ function createBookingArtifacts(agentClient) {
|
|
|
2548
2502
|
return artifacts;
|
|
2549
2503
|
}
|
|
2550
2504
|
async function writeProjectFile(projectDir, relativePath, contents) {
|
|
2551
|
-
const path =
|
|
2552
|
-
await mkdir4(
|
|
2505
|
+
const path = join3(projectDir, relativePath);
|
|
2506
|
+
await mkdir4(dirname5(path), { recursive: true });
|
|
2553
2507
|
await writeFile4(path, contents, "utf8");
|
|
2554
2508
|
}
|
|
2555
2509
|
var bookingRulesTemplate = `# Siteplane Booking Rules
|
|
2556
2510
|
|
|
2557
2511
|
- Do not change layout, copy, styling, animation or business logic while adding Booking.
|
|
2558
|
-
-
|
|
2559
|
-
- Use
|
|
2560
|
-
-
|
|
2512
|
+
- Integrate /booking on the customer domain through withSiteplane(nextConfig, { booking: { site: "<site-id>" } }); use the immutable Site ID supplied by Siteplane.
|
|
2513
|
+
- Use a normal <a href="/booking"> link, not next/link, an iframe or an embed script.
|
|
2514
|
+
- Preserve existing rewrites. Booking-only must not require Editor setup or siteplane.config.json.
|
|
2515
|
+
- Configure the public booking address in Siteplane; register its origin and call https://siteplane.io/api/booking/* directly with CORS, without a raw public key.
|
|
2516
|
+
- Preserve customer CSP and middleware; explain required Siteplane/Stripe permissions and exclude /booking from customer middleware.
|
|
2561
2517
|
- Do not write setup tokens, project CLI tokens or private keys into source files.
|
|
2562
2518
|
- Run npx siteplane booking check, npx siteplane booking sync and npx siteplane booking test after setup.
|
|
2563
2519
|
- booking test stays in test_mode; live booking only starts after explicit dashboard activation.
|
|
@@ -2565,7 +2521,7 @@ var bookingRulesTemplate = `# Siteplane Booking Rules
|
|
|
2565
2521
|
function bookingSkillTemplate(agentName) {
|
|
2566
2522
|
return `# Siteplane Booking Skill
|
|
2567
2523
|
|
|
2568
|
-
Use this skill in ${agentName} before
|
|
2524
|
+
Use this skill in ${agentName} before integrating Siteplane Booking at /booking.
|
|
2569
2525
|
|
|
2570
2526
|
${bookingRulesTemplate}`;
|
|
2571
2527
|
}
|
|
@@ -2640,9 +2596,9 @@ function requireContentExportScope(scopes) {
|
|
|
2640
2596
|
}
|
|
2641
2597
|
|
|
2642
2598
|
// ../cli/dist/config/project-config.js
|
|
2643
|
-
import { access, chmod, open, readFile as readFile5, rename, rm } from "fs/promises";
|
|
2599
|
+
import { access as access2, chmod, open, readFile as readFile5, rename, rm } from "fs/promises";
|
|
2644
2600
|
import { randomUUID as randomUUID2 } from "crypto";
|
|
2645
|
-
import { join as
|
|
2601
|
+
import { join as join4 } from "path";
|
|
2646
2602
|
import { z as z31 } from "zod";
|
|
2647
2603
|
var siteplaneProjectConfigSchema = z31.object({
|
|
2648
2604
|
version: z31.literal(2),
|
|
@@ -2658,7 +2614,7 @@ var siteplaneProjectConfigSchema = z31.object({
|
|
|
2658
2614
|
fieldContractHash: z31.string().regex(/^sha256:[0-9a-f]{64}$/iu).optional()
|
|
2659
2615
|
}).strict();
|
|
2660
2616
|
async function readProjectPackageJson(projectDir) {
|
|
2661
|
-
return JSON.parse(await readFile5(
|
|
2617
|
+
return JSON.parse(await readFile5(join4(projectDir, "package.json"), "utf8"));
|
|
2662
2618
|
}
|
|
2663
2619
|
async function detectNextProject(projectDir) {
|
|
2664
2620
|
const packageJson = await readProjectPackageJson(projectDir).catch(() => null);
|
|
@@ -2671,7 +2627,7 @@ async function detectNextProject(projectDir) {
|
|
|
2671
2627
|
"next.config.ts"
|
|
2672
2628
|
]) {
|
|
2673
2629
|
try {
|
|
2674
|
-
await
|
|
2630
|
+
await access2(join4(projectDir, fileName));
|
|
2675
2631
|
return true;
|
|
2676
2632
|
} catch {
|
|
2677
2633
|
}
|
|
@@ -2679,13 +2635,13 @@ async function detectNextProject(projectDir) {
|
|
|
2679
2635
|
return false;
|
|
2680
2636
|
}
|
|
2681
2637
|
async function writeProjectConfig(projectDir, config) {
|
|
2682
|
-
const path =
|
|
2638
|
+
const path = join4(projectDir, "siteplane.config.json");
|
|
2683
2639
|
const parsed = siteplaneProjectConfigSchema.parse(config);
|
|
2684
2640
|
await writeJsonAtomically(path, parsed, 420);
|
|
2685
2641
|
return path;
|
|
2686
2642
|
}
|
|
2687
2643
|
async function readProjectConfig(projectDir) {
|
|
2688
|
-
return siteplaneProjectConfigSchema.parse(JSON.parse(await readFile5(
|
|
2644
|
+
return siteplaneProjectConfigSchema.parse(JSON.parse(await readFile5(join4(projectDir, "siteplane.config.json"), "utf8")));
|
|
2689
2645
|
}
|
|
2690
2646
|
async function writeJsonAtomically(path, value, mode) {
|
|
2691
2647
|
const temporaryPath = `${path}.${randomUUID2()}.tmp`;
|
|
@@ -2713,7 +2669,7 @@ async function writeJsonAtomically(path, value, mode) {
|
|
|
2713
2669
|
import { execFile } from "child_process";
|
|
2714
2670
|
import { randomUUID as randomUUID3 } from "crypto";
|
|
2715
2671
|
import { chmod as chmod2, lstat, mkdir as mkdir5, open as open2, readFile as readFile6, rename as rename2, rm as rm2 } from "fs/promises";
|
|
2716
|
-
import { dirname as
|
|
2672
|
+
import { dirname as dirname6, join as join5, relative } from "path";
|
|
2717
2673
|
import { promisify } from "util";
|
|
2718
2674
|
import { z as z32 } from "zod";
|
|
2719
2675
|
var localSetupInstallationSchema = z32.object({
|
|
@@ -2738,7 +2694,7 @@ var localSetupCredentialsSchema = z32.union([
|
|
|
2738
2694
|
z32.object({ installation: localSetupInstallationSchema }).strict()
|
|
2739
2695
|
]);
|
|
2740
2696
|
async function assertLocalCredentialsPathSafe(projectDir, options = {}) {
|
|
2741
|
-
const path =
|
|
2697
|
+
const path = join5(projectDir, ".siteplane/credentials.json");
|
|
2742
2698
|
await assertCredentialFilesystemSafe(projectDir);
|
|
2743
2699
|
const isTrackedFile = options.isTrackedFile ?? ((targetPath) => gitPathMatches(projectDir, targetPath, "ls-files"));
|
|
2744
2700
|
const isIgnoredFile = options.isIgnoredFile ?? ((targetPath) => gitPathMatches(projectDir, targetPath, "check-ignore"));
|
|
@@ -2753,8 +2709,8 @@ async function assertLocalCredentialsPathSafe(projectDir, options = {}) {
|
|
|
2753
2709
|
async function assertCredentialFilesystemSafe(projectDir) {
|
|
2754
2710
|
for (const [path, directory, mode] of [
|
|
2755
2711
|
[projectDir, true, null],
|
|
2756
|
-
[
|
|
2757
|
-
[
|
|
2712
|
+
[join5(projectDir, ".siteplane"), true, 448],
|
|
2713
|
+
[join5(projectDir, ".siteplane/credentials.json"), false, 384]
|
|
2758
2714
|
]) {
|
|
2759
2715
|
const stat = await lstat(path).catch((error) => {
|
|
2760
2716
|
if (error.code === "ENOENT")
|
|
@@ -2777,7 +2733,7 @@ async function writeLocalCredentials(projectDir, credentials, options = {}) {
|
|
|
2777
2733
|
async function writeLocalSetupCredentials(projectDir, credentials, options = {}) {
|
|
2778
2734
|
const path = await assertLocalCredentialsPathSafe(projectDir, options);
|
|
2779
2735
|
const parsed = localSetupCredentialsSchema.parse(credentials);
|
|
2780
|
-
await mkdir5(
|
|
2736
|
+
await mkdir5(dirname6(path), { recursive: true, mode: 448 });
|
|
2781
2737
|
await writeCredentialsAtomically(path, parsed);
|
|
2782
2738
|
return path;
|
|
2783
2739
|
}
|
|
@@ -2790,7 +2746,7 @@ async function readLocalCredentials(projectDir) {
|
|
|
2790
2746
|
}
|
|
2791
2747
|
async function readLocalSetupCredentials(projectDir) {
|
|
2792
2748
|
await assertCredentialFilesystemSafe(projectDir);
|
|
2793
|
-
return localSetupCredentialsSchema.parse(JSON.parse(await readFile6(
|
|
2749
|
+
return localSetupCredentialsSchema.parse(JSON.parse(await readFile6(join5(projectDir, ".siteplane/credentials.json"), "utf8")));
|
|
2794
2750
|
}
|
|
2795
2751
|
async function writeCredentialsAtomically(path, credentials) {
|
|
2796
2752
|
const temporaryPath = `${path}.${randomUUID3()}.tmp`;
|
|
@@ -2808,7 +2764,7 @@ async function writeCredentialsAtomically(path, credentials) {
|
|
|
2808
2764
|
try {
|
|
2809
2765
|
await rename2(temporaryPath, path);
|
|
2810
2766
|
await chmod2(path, 384);
|
|
2811
|
-
const directory = await open2(
|
|
2767
|
+
const directory = await open2(dirname6(path), "r");
|
|
2812
2768
|
try {
|
|
2813
2769
|
await directory.sync();
|
|
2814
2770
|
} finally {
|
|
@@ -2831,8 +2787,8 @@ async function gitPathMatches(projectDir, path, command) {
|
|
|
2831
2787
|
}
|
|
2832
2788
|
|
|
2833
2789
|
// ../cli/dist/commands/init.js
|
|
2834
|
-
import { access as
|
|
2835
|
-
import { join as
|
|
2790
|
+
import { access as access4 } from "fs/promises";
|
|
2791
|
+
import { join as join8, relative as relative3 } from "path";
|
|
2836
2792
|
import { z as z35 } from "zod";
|
|
2837
2793
|
|
|
2838
2794
|
// ../cli/dist/commands/setup-preflight.js
|
|
@@ -2844,7 +2800,7 @@ import { parse as parseYaml } from "yaml";
|
|
|
2844
2800
|
// ../cli/dist/config/installed-package.js
|
|
2845
2801
|
import { createRequire } from "module";
|
|
2846
2802
|
import { readFile as readFile7 } from "fs/promises";
|
|
2847
|
-
import { join as
|
|
2803
|
+
import { join as join6 } from "path";
|
|
2848
2804
|
import { z as z33 } from "zod";
|
|
2849
2805
|
var packageSchema = z33.object({
|
|
2850
2806
|
name: z33.string().optional(),
|
|
@@ -2852,10 +2808,10 @@ var packageSchema = z33.object({
|
|
|
2852
2808
|
peerDependencies: z33.record(z33.string(), z33.string()).optional()
|
|
2853
2809
|
});
|
|
2854
2810
|
async function readInstalledPackage(projectDir, name2) {
|
|
2855
|
-
const require2 = createRequire(
|
|
2811
|
+
const require2 = createRequire(join6(projectDir, "package.json"));
|
|
2856
2812
|
for (const directory of require2.resolve.paths(name2) ?? []) {
|
|
2857
2813
|
try {
|
|
2858
|
-
return packageSchema.parse(JSON.parse(await readFile7(
|
|
2814
|
+
return packageSchema.parse(JSON.parse(await readFile7(join6(directory, name2, "package.json"), "utf8")));
|
|
2859
2815
|
} catch (error) {
|
|
2860
2816
|
if (error.code !== "ENOENT")
|
|
2861
2817
|
throw error;
|
|
@@ -2865,8 +2821,8 @@ async function readInstalledPackage(projectDir, name2) {
|
|
|
2865
2821
|
}
|
|
2866
2822
|
|
|
2867
2823
|
// ../cli/dist/commands/setup-preflight.js
|
|
2868
|
-
import { access as
|
|
2869
|
-
import { dirname as
|
|
2824
|
+
import { access as access3, readFile as readFile8, realpath, readdir, readlink } from "fs/promises";
|
|
2825
|
+
import { dirname as dirname7, join as join7, relative as relative2, resolve, sep } from "path";
|
|
2870
2826
|
import { z as z34 } from "zod";
|
|
2871
2827
|
|
|
2872
2828
|
// ../cli/dist/commands/setup-process.js
|
|
@@ -2993,15 +2949,15 @@ var vercelProjectSchema = z34.object({
|
|
|
2993
2949
|
productionBranch: z34.string().optional()
|
|
2994
2950
|
}).nullable().optional()
|
|
2995
2951
|
});
|
|
2996
|
-
var exists = async (path) =>
|
|
2952
|
+
var exists = async (path) => access3(path).then(() => true, () => false);
|
|
2997
2953
|
var fail = (code, message) => {
|
|
2998
2954
|
throw new SetupFailure(code, message);
|
|
2999
2955
|
};
|
|
3000
2956
|
var stable = (version2, major) => new RegExp(`^${major}\\.\\d+\\.\\d+$`, "u").test(version2);
|
|
3001
2957
|
async function inspectSetupLocalProject(projectDir) {
|
|
3002
2958
|
const projectDirectory = await realpath(resolve(projectDir));
|
|
3003
|
-
const manifest = manifestSchema.parse(JSON.parse(await readFile8(
|
|
3004
|
-
const apps = (await Promise.all(["app", "src/app"].map(async (path) => await exists(
|
|
2959
|
+
const manifest = manifestSchema.parse(JSON.parse(await readFile8(join7(projectDirectory, "package.json"), "utf8")));
|
|
2960
|
+
const apps = (await Promise.all(["app", "src/app"].map(async (path) => await exists(join7(projectDirectory, path)) ? path : null))).filter((path) => path !== null);
|
|
3005
2961
|
if (apps.length !== 1)
|
|
3006
2962
|
fail("ambiguous_app_directory", "Select one Next.js App Router application with exactly one app/ or src/app/ directory.");
|
|
3007
2963
|
const repositoryRoot = (await setupProcess("git", ["rev-parse", "--show-toplevel"], {
|
|
@@ -3015,8 +2971,8 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3015
2971
|
fail("git_submodule_conflict", "The repository contains Git submodules. Resolve the explicit deployment source boundary before setup; the CLI will not copy external repositories.");
|
|
3016
2972
|
if (!entry.startsWith("120000 "))
|
|
3017
2973
|
continue;
|
|
3018
|
-
const path =
|
|
3019
|
-
const target = resolve(
|
|
2974
|
+
const path = join7(repositoryRoot, entry.slice(entry.indexOf(" ") + 1));
|
|
2975
|
+
const target = resolve(dirname7(path), await readlink(path));
|
|
3020
2976
|
const bound = relative2(repositoryRoot, target);
|
|
3021
2977
|
if (bound.startsWith("..") || bound.startsWith(sep))
|
|
3022
2978
|
fail("external_symlink_conflict", "A tracked symbolic link points outside this repository. Resolve that source boundary before setup; local external files cannot enter a deployment.");
|
|
@@ -3032,10 +2988,10 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3032
2988
|
];
|
|
3033
2989
|
let locks = [];
|
|
3034
2990
|
for (; ; ) {
|
|
3035
|
-
locks = (await Promise.all(lockNames.map(async (name3) => await exists(
|
|
3036
|
-
if (locks.length || lockfileRoot === repositoryRoot ||
|
|
2991
|
+
locks = (await Promise.all(lockNames.map(async (name3) => await exists(join7(lockfileRoot, name3)) ? name3 : null))).filter((name3) => name3 !== null);
|
|
2992
|
+
if (locks.length || lockfileRoot === repositoryRoot || dirname7(lockfileRoot) === lockfileRoot)
|
|
3037
2993
|
break;
|
|
3038
|
-
lockfileRoot =
|
|
2994
|
+
lockfileRoot = dirname7(lockfileRoot);
|
|
3039
2995
|
}
|
|
3040
2996
|
if (locks.length > 1)
|
|
3041
2997
|
fail("conflicting_lockfiles", "Resolve conflicting package-manager lockfiles before setup; Siteplane does not replace them.");
|
|
@@ -3044,9 +3000,9 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3044
3000
|
const lockName = locks[0];
|
|
3045
3001
|
if (!["package-lock.json", "pnpm-lock.yaml"].includes(lockName))
|
|
3046
3002
|
fail("unsupported_package_manager", "This setup supports npm 10 or pnpm 9/10 with their canonical lockfile.");
|
|
3047
|
-
const rootManifest = manifestSchema.parse(JSON.parse(await readFile8(
|
|
3003
|
+
const rootManifest = manifestSchema.parse(JSON.parse(await readFile8(join7(lockfileRoot, "package.json"), "utf8")));
|
|
3048
3004
|
if (lockfileRoot !== projectDirectory) {
|
|
3049
|
-
const workspaceFile =
|
|
3005
|
+
const workspaceFile = join7(lockfileRoot, "pnpm-workspace.yaml");
|
|
3050
3006
|
const workspace = lockName === "pnpm-lock.yaml" && await exists(workspaceFile) ? z34.object({ packages: z34.array(z34.string()) }).parse(parseYaml(await readFile8(workspaceFile, "utf8"))).packages : z34.union([
|
|
3051
3007
|
z34.array(z34.string()),
|
|
3052
3008
|
z34.object({ packages: z34.array(z34.string()) }).transform((value) => value.packages)
|
|
@@ -3055,14 +3011,14 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3055
3011
|
if (!workspace.some((pattern) => !pattern.startsWith("!") && minimatch(selected, pattern)) || workspace.some((pattern) => pattern.startsWith("!") && minimatch(selected, pattern.slice(1))))
|
|
3056
3012
|
fail("unbound_workspace_app", "The selected application is excluded from the canonical lockfile's workspace packages. Select its actual application root.");
|
|
3057
3013
|
}
|
|
3058
|
-
for (let ancestor =
|
|
3059
|
-
const ancestorLocks = await Promise.all(lockNames.map((name3) => exists(
|
|
3014
|
+
for (let ancestor = dirname7(lockfileRoot); ancestor.startsWith(repositoryRoot + sep) || ancestor === repositoryRoot; ancestor = dirname7(ancestor)) {
|
|
3015
|
+
const ancestorLocks = await Promise.all(lockNames.map((name3) => exists(join7(ancestor, name3))));
|
|
3060
3016
|
if (ancestorLocks.some(Boolean))
|
|
3061
3017
|
fail("ambiguous_lockfile_root", "Both the selected package and its repository ancestors contain lockfiles. Select one canonical workspace resolution before setup.");
|
|
3062
3018
|
if (ancestor === repositoryRoot)
|
|
3063
3019
|
break;
|
|
3064
3020
|
}
|
|
3065
|
-
const lockText = await readFile8(
|
|
3021
|
+
const lockText = await readFile8(join7(lockfileRoot, lockName), "utf8");
|
|
3066
3022
|
const npmLock = lockName === "package-lock.json" ? z34.object({
|
|
3067
3023
|
lockfileVersion: z34.number(),
|
|
3068
3024
|
packages: z34.record(z34.string(), z34.object({
|
|
@@ -3115,9 +3071,9 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3115
3071
|
fail("lockfile_format_conflict", "The canonical lockfile format does not match npm 10 or pnpm 9/10.");
|
|
3116
3072
|
const sourceConflicts = [];
|
|
3117
3073
|
for (const file of ["next.config.js", "next.config.mjs", "next.config.ts"]) {
|
|
3118
|
-
if (!await exists(
|
|
3074
|
+
if (!await exists(join7(projectDirectory, file)))
|
|
3119
3075
|
continue;
|
|
3120
|
-
const source = await readFile8(
|
|
3076
|
+
const source = await readFile8(join7(projectDirectory, file), "utf8");
|
|
3121
3077
|
if (/output\s*:\s*['"]export['"]/u.test(source))
|
|
3122
3078
|
sourceConflicts.push("static_export");
|
|
3123
3079
|
if (/\bbasePath\s*:/u.test(source))
|
|
@@ -3137,11 +3093,11 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3137
3093
|
"src/proxy.ts",
|
|
3138
3094
|
"src/proxy.js"
|
|
3139
3095
|
]) {
|
|
3140
|
-
if (await exists(
|
|
3096
|
+
if (await exists(join7(projectDirectory, name3))) {
|
|
3141
3097
|
sourceConflicts.push(`inspect_routing:${name3}`);
|
|
3142
|
-
if (await readlink(
|
|
3098
|
+
if (await readlink(join7(projectDirectory, name3)).catch(() => null))
|
|
3143
3099
|
continue;
|
|
3144
|
-
const policySource = await readFile8(
|
|
3100
|
+
const policySource = await readFile8(join7(projectDirectory, name3), "utf8");
|
|
3145
3101
|
if (/Content-Security-Policy|img-src|default-src/iu.test(policySource))
|
|
3146
3102
|
sourceConflicts.push(`inspect_image_csp:${name3}`);
|
|
3147
3103
|
}
|
|
@@ -3150,7 +3106,7 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3150
3106
|
for (const entry of await readdir(directory, { withFileTypes: true })) {
|
|
3151
3107
|
if (entry.isSymbolicLink() || ["node_modules", ".git", ".next", ".siteplane", ".vercel"].includes(entry.name))
|
|
3152
3108
|
continue;
|
|
3153
|
-
const path =
|
|
3109
|
+
const path = join7(directory, entry.name);
|
|
3154
3110
|
if (entry.isDirectory()) {
|
|
3155
3111
|
await inspectSource(path);
|
|
3156
3112
|
continue;
|
|
@@ -3170,7 +3126,7 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3170
3126
|
fail("next_security_advisory", `Next.js ${nextVersion} contains Server Actions affected by the July 2026 advisory. Review https://nextjs.org/blog/july-2026-security-release and explicitly update the affected dependency before setup.`);
|
|
3171
3127
|
}
|
|
3172
3128
|
}
|
|
3173
|
-
await inspectSource(
|
|
3129
|
+
await inspectSource(join7(projectDirectory, apps[0]));
|
|
3174
3130
|
const gitRead = async (args) => setupProcess("git", args, { cwd: projectDirectory }).then((value) => value.trim(), () => null);
|
|
3175
3131
|
return {
|
|
3176
3132
|
projectDirectory,
|
|
@@ -3182,7 +3138,7 @@ async function inspectSetupLocalProject(projectDir) {
|
|
|
3182
3138
|
nodeVersion: process.versions.node,
|
|
3183
3139
|
packageManager: { name: name2, version: localVersion, declared },
|
|
3184
3140
|
lockfile: {
|
|
3185
|
-
path: relative2(repositoryRoot,
|
|
3141
|
+
path: relative2(repositoryRoot, join7(lockfileRoot, lockName)),
|
|
3186
3142
|
format,
|
|
3187
3143
|
sha256: createHash2("sha256").update(lockText).digest("hex")
|
|
3188
3144
|
},
|
|
@@ -3201,14 +3157,14 @@ async function setupPreflightCommand(input) {
|
|
|
3201
3157
|
local = await inspectSetupLocalProject(input.projectDir);
|
|
3202
3158
|
await assertLocalCredentialsPathSafe(input.projectDir);
|
|
3203
3159
|
let linkDirectory = local.projectDirectory;
|
|
3204
|
-
while (!await exists(
|
|
3205
|
-
linkDirectory =
|
|
3206
|
-
if (!await exists(
|
|
3160
|
+
while (!await exists(join7(linkDirectory, ".vercel/project.json")) && linkDirectory !== local.repositoryRoot && dirname7(linkDirectory) !== linkDirectory)
|
|
3161
|
+
linkDirectory = dirname7(linkDirectory);
|
|
3162
|
+
if (!await exists(join7(linkDirectory, ".vercel/project.json")))
|
|
3207
3163
|
fail("vercel_project_not_linked", "Link this application to its intended Vercel project before setup; Siteplane will not guess a target.");
|
|
3208
3164
|
const linked = z34.object({
|
|
3209
3165
|
projectId: z34.string().regex(/^prj_[A-Za-z0-9]+$/u),
|
|
3210
3166
|
orgId: z34.string().regex(/^(?:team|user)_[A-Za-z0-9]+$/u)
|
|
3211
|
-
}).parse(JSON.parse(await readFile8(
|
|
3167
|
+
}).parse(JSON.parse(await readFile8(join7(linkDirectory, ".vercel/project.json"), "utf8")));
|
|
3212
3168
|
const project = vercelProjectSchema.parse(await setupVercelApi(linkDirectory, `/v9/projects/${linked.projectId}?teamId=${linked.orgId}`));
|
|
3213
3169
|
if (project.id !== linked.projectId || project.accountId !== linked.orgId)
|
|
3214
3170
|
fail("vercel_identity_conflict", "The provider project does not match the locally linked project and team.");
|
|
@@ -3346,7 +3302,7 @@ var bootstrapResponseSchema = z35.object({
|
|
|
3346
3302
|
}).strict();
|
|
3347
3303
|
async function bootstrapProjectConnection(input) {
|
|
3348
3304
|
const fetcher = input.fetcher ?? fetch;
|
|
3349
|
-
const existing = await
|
|
3305
|
+
const existing = await access4(join8(input.projectDir, "siteplane.config.json")).then(() => readProjectConfig(input.projectDir), () => null);
|
|
3350
3306
|
const response = await fetcher(`${input.apiBaseUrl.replace(/\/$/, "")}/api/cli/setup/bootstrap`, {
|
|
3351
3307
|
method: "POST",
|
|
3352
3308
|
signal: AbortSignal.timeout(2e4),
|
|
@@ -3377,10 +3333,10 @@ async function acknowledgeBootstrapResponse(input) {
|
|
|
3377
3333
|
}
|
|
3378
3334
|
}
|
|
3379
3335
|
async function persistSiteSetupBootstrap(input, bootstrap, appDirectory, installation) {
|
|
3380
|
-
const previous = await
|
|
3336
|
+
const previous = await access4(join8(input.projectDir, "siteplane.config.json")).then(() => readProjectConfig(input.projectDir), () => null);
|
|
3381
3337
|
if (previous && (previous.siteId !== bootstrap.siteId || previous.runId !== bootstrap.runId || previous.publicSiteKeyId !== bootstrap.publicSiteKeyId || previous.publicSiteKey !== bootstrap.publicSiteKey))
|
|
3382
3338
|
throw new Error("The grant does not match this local Siteplane run. Preserve this directory and choose the correct owner connection.");
|
|
3383
|
-
const previousCredentials = previous ? await
|
|
3339
|
+
const previousCredentials = previous ? await access4(join8(input.projectDir, ".siteplane/credentials.json")).then(() => readLocalSetupCredentials(input.projectDir), () => null) : null;
|
|
3384
3340
|
const credentialsPath = await writeLocalCredentials(input.projectDir, {
|
|
3385
3341
|
...previousCredentials && "adminSession" in previousCredentials && previousCredentials.adminSession ? { adminSession: previousCredentials.adminSession } : {},
|
|
3386
3342
|
...previousCredentials && "claimReceipt" in previousCredentials && previousCredentials.claimReceipt ? { claimReceipt: previousCredentials.claimReceipt } : {},
|
|
@@ -3433,7 +3389,7 @@ async function persistFeatureBootstrap(input, bootstrap) {
|
|
|
3433
3389
|
throw new Error("Siteplane credentials could not be verified.");
|
|
3434
3390
|
}
|
|
3435
3391
|
return {
|
|
3436
|
-
configPath:
|
|
3392
|
+
configPath: join8(input.projectDir, "siteplane.config.json"),
|
|
3437
3393
|
credentialsPath
|
|
3438
3394
|
};
|
|
3439
3395
|
}
|
|
@@ -3456,7 +3412,7 @@ function readErrorMessage(payload) {
|
|
|
3456
3412
|
|
|
3457
3413
|
// ../cli/dist/commands/scan.js
|
|
3458
3414
|
import { readdir as readdir2 } from "fs/promises";
|
|
3459
|
-
import { extname, join as
|
|
3415
|
+
import { extname, join as join9 } from "path";
|
|
3460
3416
|
var defaultScanRoots = ["app", "src", "pages", "components", "lib"];
|
|
3461
3417
|
var excludedDirectories = /* @__PURE__ */ new Set([
|
|
3462
3418
|
".git",
|
|
@@ -3474,14 +3430,14 @@ async function resolveScanFilePaths(filePaths, options = {}) {
|
|
|
3474
3430
|
return filePaths;
|
|
3475
3431
|
}
|
|
3476
3432
|
const projectDir = options.projectDir ?? process.cwd();
|
|
3477
|
-
const discovered = await Promise.all(defaultScanRoots.map((root) => collectSourceFiles(
|
|
3433
|
+
const discovered = await Promise.all(defaultScanRoots.map((root) => collectSourceFiles(join9(projectDir, root))));
|
|
3478
3434
|
return [...new Set(discovered.flat())].sort();
|
|
3479
3435
|
}
|
|
3480
3436
|
async function collectSourceFiles(directory) {
|
|
3481
3437
|
const entries = await readdir2(directory, { withFileTypes: true }).catch(() => []);
|
|
3482
3438
|
const files = [];
|
|
3483
3439
|
for (const entry of entries) {
|
|
3484
|
-
const entryPath =
|
|
3440
|
+
const entryPath = join9(directory, entry.name);
|
|
3485
3441
|
if (entry.isDirectory()) {
|
|
3486
3442
|
if (!excludedDirectories.has(entry.name)) {
|
|
3487
3443
|
files.push(...await collectSourceFiles(entryPath));
|
|
@@ -3502,7 +3458,7 @@ import { promisify as promisify2 } from "util";
|
|
|
3502
3458
|
import { z as z36 } from "zod";
|
|
3503
3459
|
|
|
3504
3460
|
// ../cli/dist/scan/next-source-scan.js
|
|
3505
|
-
import
|
|
3461
|
+
import ts3 from "typescript";
|
|
3506
3462
|
import { isAbsolute, relative as relative4 } from "path";
|
|
3507
3463
|
var legacyEditableComponentPrefix = "Editable";
|
|
3508
3464
|
var editableComponentNames = new Set(["Image", "Text", "LongText", "Link"].map((name2) => `${legacyEditableComponentPrefix}${name2}`));
|
|
@@ -3629,8 +3585,8 @@ async function readGitRevision(projectDir) {
|
|
|
3629
3585
|
|
|
3630
3586
|
// ../cli/dist/commands/setup-start.js
|
|
3631
3587
|
import { randomBytes, randomUUID as randomUUID4 } from "crypto";
|
|
3632
|
-
import { access as
|
|
3633
|
-
import { join as
|
|
3588
|
+
import { access as access5 } from "fs/promises";
|
|
3589
|
+
import { join as join10, relative as relative5 } from "path";
|
|
3634
3590
|
import { z as z37 } from "zod";
|
|
3635
3591
|
var bootstrapResponseSchema2 = z37.object({
|
|
3636
3592
|
ok: z37.literal(true),
|
|
@@ -3648,10 +3604,10 @@ var responseSchema2 = z38.object({
|
|
|
3648
3604
|
}).strict();
|
|
3649
3605
|
|
|
3650
3606
|
// ../cli/dist/commands/setup-prepare.js
|
|
3651
|
-
import { access as
|
|
3607
|
+
import { access as access6, lstat as lstat2, mkdir as mkdir6, open as open3, readFile as readFile10, rename as rename3, rm as rm3 } from "fs/promises";
|
|
3652
3608
|
import { randomUUID as randomUUID5 } from "crypto";
|
|
3653
|
-
import { dirname as
|
|
3654
|
-
import
|
|
3609
|
+
import { dirname as dirname8, join as join11, relative as relative6, sep as sep2 } from "path";
|
|
3610
|
+
import ts4 from "typescript";
|
|
3655
3611
|
|
|
3656
3612
|
// ../cli/dist/commands/setup-lock.js
|
|
3657
3613
|
import { randomUUID as randomUUID6 } from "crypto";
|
|
@@ -3664,7 +3620,7 @@ var ownerSchema = z39.object({ pid: z39.number().int().positive(), nonce: z39.st
|
|
|
3664
3620
|
import { createHash as createHash3 } from "crypto";
|
|
3665
3621
|
import { execFile as execFile3 } from "child_process";
|
|
3666
3622
|
import { lstat as lstat4, readFile as readFile12, writeFile as writeFile5, mkdir as mkdir8 } from "fs/promises";
|
|
3667
|
-
import { dirname as
|
|
3623
|
+
import { dirname as dirname9, isAbsolute as isAbsolute2, join as join12, relative as relative7, resolve as resolve3, sep as sep3 } from "path";
|
|
3668
3624
|
import { isDeepStrictEqual, promisify as promisify3 } from "util";
|
|
3669
3625
|
import { z as z40 } from "zod";
|
|
3670
3626
|
var execute = promisify3(execFile3);
|
|
@@ -3704,15 +3660,15 @@ async function writeBuildProvenance(checkout, revision) {
|
|
|
3704
3660
|
if (entry.mode !== "120000")
|
|
3705
3661
|
continue;
|
|
3706
3662
|
const { readlink: readlink2 } = await import("fs/promises");
|
|
3707
|
-
const path =
|
|
3708
|
-
const target2 = resolve3(
|
|
3663
|
+
const path = join12(checkout, entry.path);
|
|
3664
|
+
const target2 = resolve3(dirname9(path), await readlink2(path));
|
|
3709
3665
|
const bound = relative7(checkout, target2);
|
|
3710
3666
|
if (bound.startsWith("..") || isAbsolute2(bound))
|
|
3711
3667
|
throw new Error("A tracked symbolic link escapes the committed upload; resolve that source boundary before deployment.");
|
|
3712
3668
|
}
|
|
3713
3669
|
const providerConfigurations = await Promise.all(entries.filter((entry) => /(?:^|\/)vercel\.json$/u.test(entry.path)).map(async (entry) => ({
|
|
3714
3670
|
path: entry.path,
|
|
3715
|
-
source: await readFile12(
|
|
3671
|
+
source: await readFile12(join12(checkout, entry.path), "utf8")
|
|
3716
3672
|
})));
|
|
3717
3673
|
const record = schema.parse({
|
|
3718
3674
|
version: 2,
|
|
@@ -3721,16 +3677,16 @@ async function writeBuildProvenance(checkout, revision) {
|
|
|
3721
3677
|
entries,
|
|
3722
3678
|
providerConfigurations
|
|
3723
3679
|
});
|
|
3724
|
-
const target =
|
|
3725
|
-
await mkdir8(
|
|
3680
|
+
const target = join12(checkout, name);
|
|
3681
|
+
await mkdir8(dirname9(target), { recursive: true, mode: 448 });
|
|
3726
3682
|
await writeFile5(target, JSON.stringify(record), { flag: "wx", mode: 384 });
|
|
3727
3683
|
}
|
|
3728
3684
|
|
|
3729
3685
|
// ../cli/dist/commands/setup-deploy.js
|
|
3730
3686
|
import { createHash as createHash4, randomBytes as randomBytes2, randomUUID as randomUUID7 } from "crypto";
|
|
3731
|
-
import { access as
|
|
3687
|
+
import { access as access7, mkdir as mkdir9, mkdtemp, rm as rm5, writeFile as writeFile6 } from "fs/promises";
|
|
3732
3688
|
import { tmpdir } from "os";
|
|
3733
|
-
import { join as
|
|
3689
|
+
import { join as join13 } from "path";
|
|
3734
3690
|
import { z as z41 } from "zod";
|
|
3735
3691
|
var envSchema = z41.object({
|
|
3736
3692
|
id: z41.string(),
|