@valbuild/cli 0.138.0 → 0.138.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +12 -0
- package/cli/dist/valbuild-cli-cli.cjs.dev.js +25 -4
- package/cli/dist/valbuild-cli-cli.cjs.prod.js +25 -4
- package/cli/dist/valbuild-cli-cli.esm.js +25 -4
- package/package.json +3 -3
- package/src/publish/__fixtures__/buildPublishProbe.ts +12 -0
- package/src/publish/buildArtifacts.ts +29 -4
- package/src/publish/buildPublish.test.ts +10 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,17 @@
|
|
|
1
1
|
# @valbuild/cli
|
|
2
2
|
|
|
3
|
+
## 0.138.1
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [#758](https://github.com/valbuild/val/pull/758) [`af57406`](https://github.com/valbuild/val/commit/af57406fb679f5917559a8c97507b7c42f2b48fe) Thanks [@freekh](https://github.com/freekh)! - `val publish` no longer stores a project's stylesheets as its source. It still compiles them, so the site's CSS is unchanged, but the source a managed project's Studio builds from comes without them — as the platform's own publish has always stored it.
|
|
8
|
+
|
|
9
|
+
A stored stylesheet broke every Studio publish that followed: a browser build cannot run a Tailwind `@plugin` (the starter's `src/styles.css` has `@plugin "@tailwindcss/typography"`), so it refused the stylesheet and the publish failed with "build failed 3 times". Without one, the Studio ships the live site's CSS, which is right — a Studio edit never changes a stylesheet.
|
|
10
|
+
|
|
11
|
+
- Updated dependencies []:
|
|
12
|
+
- @valbuild/server@0.138.1
|
|
13
|
+
- @valbuild/language-server@0.138.1
|
|
14
|
+
|
|
3
15
|
## 0.138.0
|
|
4
16
|
|
|
5
17
|
### Minor Changes
|
|
@@ -2351,6 +2351,25 @@ const CODE_FILE = /\.(tsx?|jsx?|mjs|cjs|css)$/;
|
|
|
2351
2351
|
*/
|
|
2352
2352
|
const JSON_FILE = /\.json$/;
|
|
2353
2353
|
|
|
2354
|
+
/**
|
|
2355
|
+
* The project's source as it is STORED, which is what the Studio builds from:
|
|
2356
|
+
* every file this build read, less the stylesheets.
|
|
2357
|
+
*
|
|
2358
|
+
* This build compiles them, because it can run what a stylesheet asks for -- a
|
|
2359
|
+
* Tailwind `@plugin` is a module resolved and executed from `node_modules`. A
|
|
2360
|
+
* build in the browser cannot, and refuses the stylesheet rather than ship a
|
|
2361
|
+
* page that is quietly unstyled; the starter's `src/styles.css` has
|
|
2362
|
+
* `@plugin "@tailwindcss/typography"`. So a stored stylesheet made every
|
|
2363
|
+
* Studio publish after the first one fail. Without it, the Studio's build has
|
|
2364
|
+
* no CSS of its own and ships the live site's (`liveStylesheet` in the
|
|
2365
|
+
* Studio), which is right: a Studio save changes content and uploaded files,
|
|
2366
|
+
* never a stylesheet. It is also what the platform's own publish has always
|
|
2367
|
+
* stored.
|
|
2368
|
+
*/
|
|
2369
|
+
function withoutStylesheets(sources) {
|
|
2370
|
+
return Object.fromEntries(Object.entries(sources).filter(([key]) => !key.endsWith(".css")));
|
|
2371
|
+
}
|
|
2372
|
+
|
|
2354
2373
|
/**
|
|
2355
2374
|
* The project's own files: its source as text, and the binaries it imports
|
|
2356
2375
|
* (an image, a font) base64, as `BuildInput.assets` takes them. `public/` is
|
|
@@ -2487,6 +2506,7 @@ async function buildArtifacts(options) {
|
|
|
2487
2506
|
// Less the one about the layer, which is the thing this goes on to build.
|
|
2488
2507
|
warnings.push(...((wiring === null || wiring === void 0 ? void 0 : wiring.warnings) ?? []).filter(warning => !warning.includes("dependency layer built for it")));
|
|
2489
2508
|
const sources = (wiring === null || wiring === void 0 ? void 0 : wiring.files) ?? onDisk;
|
|
2509
|
+
const projectSource = withoutStylesheets(sources);
|
|
2490
2510
|
|
|
2491
2511
|
// The dependency layer: from what the project imports, of what it declares.
|
|
2492
2512
|
log("Building the dependency layer");
|
|
@@ -2526,9 +2546,10 @@ async function buildArtifacts(options) {
|
|
|
2526
2546
|
env: publicEnv(options.env ?? process.env),
|
|
2527
2547
|
publicFiles: readPublicFiles(root),
|
|
2528
2548
|
assets,
|
|
2529
|
-
// The project's own files, without the generated tree
|
|
2530
|
-
// publish -- the Studio's included -- starts
|
|
2531
|
-
|
|
2549
|
+
// The project's own files, without the generated tree or the
|
|
2550
|
+
// stylesheets: what the next publish -- the Studio's included -- starts
|
|
2551
|
+
// from. See `withoutStylesheets`.
|
|
2552
|
+
projectSource,
|
|
2532
2553
|
loadCssModule: node.cssModuleLoader(root),
|
|
2533
2554
|
...(splitter ? {
|
|
2534
2555
|
routeSplitter: splitter
|
|
@@ -2536,7 +2557,7 @@ async function buildArtifacts(options) {
|
|
|
2536
2557
|
rsc: target.project.rsc
|
|
2537
2558
|
});
|
|
2538
2559
|
const artifacts = await builder.publishArtifacts(built, {
|
|
2539
|
-
projectSource
|
|
2560
|
+
projectSource
|
|
2540
2561
|
});
|
|
2541
2562
|
const dir = options.outDir ?? fs__default$1["default"].mkdtempSync(path__default["default"].join(os__default["default"].tmpdir(), "val-publish-"));
|
|
2542
2563
|
for (const artifact of artifacts) {
|
|
@@ -2351,6 +2351,25 @@ const CODE_FILE = /\.(tsx?|jsx?|mjs|cjs|css)$/;
|
|
|
2351
2351
|
*/
|
|
2352
2352
|
const JSON_FILE = /\.json$/;
|
|
2353
2353
|
|
|
2354
|
+
/**
|
|
2355
|
+
* The project's source as it is STORED, which is what the Studio builds from:
|
|
2356
|
+
* every file this build read, less the stylesheets.
|
|
2357
|
+
*
|
|
2358
|
+
* This build compiles them, because it can run what a stylesheet asks for -- a
|
|
2359
|
+
* Tailwind `@plugin` is a module resolved and executed from `node_modules`. A
|
|
2360
|
+
* build in the browser cannot, and refuses the stylesheet rather than ship a
|
|
2361
|
+
* page that is quietly unstyled; the starter's `src/styles.css` has
|
|
2362
|
+
* `@plugin "@tailwindcss/typography"`. So a stored stylesheet made every
|
|
2363
|
+
* Studio publish after the first one fail. Without it, the Studio's build has
|
|
2364
|
+
* no CSS of its own and ships the live site's (`liveStylesheet` in the
|
|
2365
|
+
* Studio), which is right: a Studio save changes content and uploaded files,
|
|
2366
|
+
* never a stylesheet. It is also what the platform's own publish has always
|
|
2367
|
+
* stored.
|
|
2368
|
+
*/
|
|
2369
|
+
function withoutStylesheets(sources) {
|
|
2370
|
+
return Object.fromEntries(Object.entries(sources).filter(([key]) => !key.endsWith(".css")));
|
|
2371
|
+
}
|
|
2372
|
+
|
|
2354
2373
|
/**
|
|
2355
2374
|
* The project's own files: its source as text, and the binaries it imports
|
|
2356
2375
|
* (an image, a font) base64, as `BuildInput.assets` takes them. `public/` is
|
|
@@ -2487,6 +2506,7 @@ async function buildArtifacts(options) {
|
|
|
2487
2506
|
// Less the one about the layer, which is the thing this goes on to build.
|
|
2488
2507
|
warnings.push(...((wiring === null || wiring === void 0 ? void 0 : wiring.warnings) ?? []).filter(warning => !warning.includes("dependency layer built for it")));
|
|
2489
2508
|
const sources = (wiring === null || wiring === void 0 ? void 0 : wiring.files) ?? onDisk;
|
|
2509
|
+
const projectSource = withoutStylesheets(sources);
|
|
2490
2510
|
|
|
2491
2511
|
// The dependency layer: from what the project imports, of what it declares.
|
|
2492
2512
|
log("Building the dependency layer");
|
|
@@ -2526,9 +2546,10 @@ async function buildArtifacts(options) {
|
|
|
2526
2546
|
env: publicEnv(options.env ?? process.env),
|
|
2527
2547
|
publicFiles: readPublicFiles(root),
|
|
2528
2548
|
assets,
|
|
2529
|
-
// The project's own files, without the generated tree
|
|
2530
|
-
// publish -- the Studio's included -- starts
|
|
2531
|
-
|
|
2549
|
+
// The project's own files, without the generated tree or the
|
|
2550
|
+
// stylesheets: what the next publish -- the Studio's included -- starts
|
|
2551
|
+
// from. See `withoutStylesheets`.
|
|
2552
|
+
projectSource,
|
|
2532
2553
|
loadCssModule: node.cssModuleLoader(root),
|
|
2533
2554
|
...(splitter ? {
|
|
2534
2555
|
routeSplitter: splitter
|
|
@@ -2536,7 +2557,7 @@ async function buildArtifacts(options) {
|
|
|
2536
2557
|
rsc: target.project.rsc
|
|
2537
2558
|
});
|
|
2538
2559
|
const artifacts = await builder.publishArtifacts(built, {
|
|
2539
|
-
projectSource
|
|
2560
|
+
projectSource
|
|
2540
2561
|
});
|
|
2541
2562
|
const dir = options.outDir ?? fs__default$1["default"].mkdtempSync(path__default["default"].join(os__default["default"].tmpdir(), "val-publish-"));
|
|
2542
2563
|
for (const artifact of artifacts) {
|
|
@@ -2316,6 +2316,25 @@ const CODE_FILE = /\.(tsx?|jsx?|mjs|cjs|css)$/;
|
|
|
2316
2316
|
*/
|
|
2317
2317
|
const JSON_FILE = /\.json$/;
|
|
2318
2318
|
|
|
2319
|
+
/**
|
|
2320
|
+
* The project's source as it is STORED, which is what the Studio builds from:
|
|
2321
|
+
* every file this build read, less the stylesheets.
|
|
2322
|
+
*
|
|
2323
|
+
* This build compiles them, because it can run what a stylesheet asks for -- a
|
|
2324
|
+
* Tailwind `@plugin` is a module resolved and executed from `node_modules`. A
|
|
2325
|
+
* build in the browser cannot, and refuses the stylesheet rather than ship a
|
|
2326
|
+
* page that is quietly unstyled; the starter's `src/styles.css` has
|
|
2327
|
+
* `@plugin "@tailwindcss/typography"`. So a stored stylesheet made every
|
|
2328
|
+
* Studio publish after the first one fail. Without it, the Studio's build has
|
|
2329
|
+
* no CSS of its own and ships the live site's (`liveStylesheet` in the
|
|
2330
|
+
* Studio), which is right: a Studio save changes content and uploaded files,
|
|
2331
|
+
* never a stylesheet. It is also what the platform's own publish has always
|
|
2332
|
+
* stored.
|
|
2333
|
+
*/
|
|
2334
|
+
function withoutStylesheets(sources) {
|
|
2335
|
+
return Object.fromEntries(Object.entries(sources).filter(([key]) => !key.endsWith(".css")));
|
|
2336
|
+
}
|
|
2337
|
+
|
|
2319
2338
|
/**
|
|
2320
2339
|
* The project's own files: its source as text, and the binaries it imports
|
|
2321
2340
|
* (an image, a font) base64, as `BuildInput.assets` takes them. `public/` is
|
|
@@ -2452,6 +2471,7 @@ async function buildArtifacts(options) {
|
|
|
2452
2471
|
// Less the one about the layer, which is the thing this goes on to build.
|
|
2453
2472
|
warnings.push(...((wiring === null || wiring === void 0 ? void 0 : wiring.warnings) ?? []).filter(warning => !warning.includes("dependency layer built for it")));
|
|
2454
2473
|
const sources = (wiring === null || wiring === void 0 ? void 0 : wiring.files) ?? onDisk;
|
|
2474
|
+
const projectSource = withoutStylesheets(sources);
|
|
2455
2475
|
|
|
2456
2476
|
// The dependency layer: from what the project imports, of what it declares.
|
|
2457
2477
|
log("Building the dependency layer");
|
|
@@ -2491,9 +2511,10 @@ async function buildArtifacts(options) {
|
|
|
2491
2511
|
env: publicEnv(options.env ?? process.env),
|
|
2492
2512
|
publicFiles: readPublicFiles(root),
|
|
2493
2513
|
assets,
|
|
2494
|
-
// The project's own files, without the generated tree
|
|
2495
|
-
// publish -- the Studio's included -- starts
|
|
2496
|
-
|
|
2514
|
+
// The project's own files, without the generated tree or the
|
|
2515
|
+
// stylesheets: what the next publish -- the Studio's included -- starts
|
|
2516
|
+
// from. See `withoutStylesheets`.
|
|
2517
|
+
projectSource,
|
|
2497
2518
|
loadCssModule: node.cssModuleLoader(root),
|
|
2498
2519
|
...(splitter ? {
|
|
2499
2520
|
routeSplitter: splitter
|
|
@@ -2501,7 +2522,7 @@ async function buildArtifacts(options) {
|
|
|
2501
2522
|
rsc: target.project.rsc
|
|
2502
2523
|
});
|
|
2503
2524
|
const artifacts = await builder.publishArtifacts(built, {
|
|
2504
|
-
projectSource
|
|
2525
|
+
projectSource
|
|
2505
2526
|
});
|
|
2506
2527
|
const dir = options.outDir ?? fs$1.mkdtempSync(path.join(os.tmpdir(), "val-publish-"));
|
|
2507
2528
|
for (const artifact of artifacts) {
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@valbuild/cli",
|
|
3
3
|
"private": false,
|
|
4
|
-
"version": "0.138.
|
|
4
|
+
"version": "0.138.1",
|
|
5
5
|
"description": "Val CLI tools",
|
|
6
6
|
"repository": {
|
|
7
7
|
"type": "git",
|
|
@@ -28,8 +28,8 @@
|
|
|
28
28
|
"zod-validation-error": "^5.0.0",
|
|
29
29
|
"@valbuild/core": "0.138.0",
|
|
30
30
|
"@valbuild/eslint-plugin": "0.125.0",
|
|
31
|
-
"@valbuild/language-server": "0.138.
|
|
32
|
-
"@valbuild/server": "0.138.
|
|
31
|
+
"@valbuild/language-server": "0.138.1",
|
|
32
|
+
"@valbuild/server": "0.138.1",
|
|
33
33
|
"@valbuild/shared": "0.138.0"
|
|
34
34
|
},
|
|
35
35
|
"peerDependencies": {
|
|
@@ -86,6 +86,10 @@ type Report = {
|
|
|
86
86
|
uploadedLayerRev: string | null;
|
|
87
87
|
/** Whether the source artifact holds the project's own route file. */
|
|
88
88
|
sourceHasRoute: boolean;
|
|
89
|
+
/** Whether the source artifact holds a stylesheet -- it must not. */
|
|
90
|
+
sourceHasStylesheet: boolean;
|
|
91
|
+
/** Whether the stylesheet was compiled into the site's CSS all the same. */
|
|
92
|
+
cssHasRule: boolean;
|
|
89
93
|
/** Whether the client build carries the page's text. */
|
|
90
94
|
clientHasPage: boolean;
|
|
91
95
|
/** Whether the imported image reached the build, inlined. */
|
|
@@ -183,6 +187,14 @@ async function publishOnce(
|
|
|
183
187
|
? "src/routes/index.tsx" in
|
|
184
188
|
(JSON.parse(source.toString("utf8")) as Record<string, string>)
|
|
185
189
|
: false,
|
|
190
|
+
sourceHasStylesheet: source
|
|
191
|
+
? Object.keys(
|
|
192
|
+
JSON.parse(source.toString("utf8")) as Record<string, string>,
|
|
193
|
+
).some((key) => key.endsWith(".css"))
|
|
194
|
+
: false,
|
|
195
|
+
cssHasRule: (fake.stored.get("css")?.toString("utf8") ?? "").includes(
|
|
196
|
+
"rebeccapurple",
|
|
197
|
+
),
|
|
186
198
|
clientHasPage: clientText.includes("hello from the checkout"),
|
|
187
199
|
clientHasLogo: clientText.includes(
|
|
188
200
|
`data:image/png;base64,${LOGO.toString("base64")}`,
|
|
@@ -97,6 +97,29 @@ const CODE_FILE = /\.(tsx?|jsx?|mjs|cjs|css)$/;
|
|
|
97
97
|
*/
|
|
98
98
|
const JSON_FILE = /\.json$/;
|
|
99
99
|
|
|
100
|
+
/**
|
|
101
|
+
* The project's source as it is STORED, which is what the Studio builds from:
|
|
102
|
+
* every file this build read, less the stylesheets.
|
|
103
|
+
*
|
|
104
|
+
* This build compiles them, because it can run what a stylesheet asks for -- a
|
|
105
|
+
* Tailwind `@plugin` is a module resolved and executed from `node_modules`. A
|
|
106
|
+
* build in the browser cannot, and refuses the stylesheet rather than ship a
|
|
107
|
+
* page that is quietly unstyled; the starter's `src/styles.css` has
|
|
108
|
+
* `@plugin "@tailwindcss/typography"`. So a stored stylesheet made every
|
|
109
|
+
* Studio publish after the first one fail. Without it, the Studio's build has
|
|
110
|
+
* no CSS of its own and ships the live site's (`liveStylesheet` in the
|
|
111
|
+
* Studio), which is right: a Studio save changes content and uploaded files,
|
|
112
|
+
* never a stylesheet. It is also what the platform's own publish has always
|
|
113
|
+
* stored.
|
|
114
|
+
*/
|
|
115
|
+
export function withoutStylesheets(
|
|
116
|
+
sources: Record<string, string>,
|
|
117
|
+
): Record<string, string> {
|
|
118
|
+
return Object.fromEntries(
|
|
119
|
+
Object.entries(sources).filter(([key]) => !key.endsWith(".css")),
|
|
120
|
+
);
|
|
121
|
+
}
|
|
122
|
+
|
|
100
123
|
/**
|
|
101
124
|
* The project's own files: its source as text, and the binaries it imports
|
|
102
125
|
* (an image, a font) base64, as `BuildInput.assets` takes them. `public/` is
|
|
@@ -244,6 +267,7 @@ export async function buildArtifacts(options: {
|
|
|
244
267
|
),
|
|
245
268
|
);
|
|
246
269
|
const sources = wiring?.files ?? onDisk;
|
|
270
|
+
const projectSource = withoutStylesheets(sources);
|
|
247
271
|
|
|
248
272
|
// The dependency layer: from what the project imports, of what it declares.
|
|
249
273
|
log("Building the dependency layer");
|
|
@@ -295,15 +319,16 @@ export async function buildArtifacts(options: {
|
|
|
295
319
|
env: publicEnv(options.env ?? process.env),
|
|
296
320
|
publicFiles: readPublicFiles(root),
|
|
297
321
|
assets,
|
|
298
|
-
// The project's own files, without the generated tree
|
|
299
|
-
// publish -- the Studio's included -- starts
|
|
300
|
-
|
|
322
|
+
// The project's own files, without the generated tree or the
|
|
323
|
+
// stylesheets: what the next publish -- the Studio's included -- starts
|
|
324
|
+
// from. See `withoutStylesheets`.
|
|
325
|
+
projectSource,
|
|
301
326
|
loadCssModule: node.cssModuleLoader(root),
|
|
302
327
|
...(splitter ? { routeSplitter: splitter } : {}),
|
|
303
328
|
rsc: target.project.rsc,
|
|
304
329
|
});
|
|
305
330
|
const artifacts: PublishArtifact[] = await builder.publishArtifacts(built, {
|
|
306
|
-
projectSource
|
|
331
|
+
projectSource,
|
|
307
332
|
});
|
|
308
333
|
|
|
309
334
|
const dir =
|
|
@@ -29,6 +29,8 @@ type Run = {
|
|
|
29
29
|
buildTargetCalls: number;
|
|
30
30
|
uploadedLayerRev: string | null;
|
|
31
31
|
sourceHasRoute: boolean;
|
|
32
|
+
sourceHasStylesheet: boolean;
|
|
33
|
+
cssHasRule: boolean;
|
|
32
34
|
clientHasPage: boolean;
|
|
33
35
|
clientHasLogo: boolean;
|
|
34
36
|
buildRouteBuilt: boolean;
|
|
@@ -76,6 +78,14 @@ test("the stored source is the project's own files", () => {
|
|
|
76
78
|
expect(probe.fresh.sourceHasRoute).toBe(true);
|
|
77
79
|
});
|
|
78
80
|
|
|
81
|
+
test("a stylesheet is built, and not stored as source", () => {
|
|
82
|
+
// The Studio builds from the stored source, in a browser that cannot run a
|
|
83
|
+
// Tailwind `@plugin`; a stored stylesheet failed every Studio publish after
|
|
84
|
+
// the first. Without one it ships the live site's CSS, compiled here.
|
|
85
|
+
expect(probe.fresh.cssHasRule).toBe(true);
|
|
86
|
+
expect(probe.fresh.sourceHasStylesheet).toBe(false);
|
|
87
|
+
});
|
|
88
|
+
|
|
79
89
|
test("an image the project imports reaches the build", () => {
|
|
80
90
|
expect(probe.fresh.clientHasLogo).toBe(true);
|
|
81
91
|
});
|