Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -37,14 +37,15 @@
"stack-trace": "^1.0.0-pre2"
},
"devDependencies": {
"@cloudflare/vite-plugin": "^1.0.8",
"@types/node": "^20.11.16",
"dedent": "^1.5.3",
"magic-string": "^0.30.6",
"prettier": "^2.8.8",
"prettier-config-rschristian": "^0.1.1",
"tmp-promise": "^3.0.3",
"uvu": "^0.5.6",
"vite": "^5.0.12"
"vite": "^6.3.1"
},
"prettier": "prettier-config-rschristian"
}
1,335 changes: 1,123 additions & 212 deletions pnpm-lock.yaml

Large diffs are not rendered by default.

16 changes: 15 additions & 1 deletion src/plugins/prerender-plugin.js
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ function serializeElement(element) {
export function prerenderPlugin({ prerenderScript, renderTarget, additionalPrerenderRoutes } = {}) {
let viteConfig = {};
let userEnabledSourceMaps;
let ssrBuild = false;

/** @type {import('./types.d.ts').PrerenderedRoute[]} */
let routes = [];
Expand Down Expand Up @@ -124,9 +125,19 @@ export function prerenderPlugin({ prerenderScript, renderTarget, additionalPrere
name: 'vite-prerender-plugin',
apply: 'build',
enforce: 'post',
applyToEnvironment(environment) {
return environment.name == 'client';
},
// Vite is pretty inconsistent with how it resolves config options, both
// hooks are needed to set their respective options. ¯\_(ツ)_/¯
config(config) {
// Only required for Vite 5 and older. In 6+, this is handled by the
// Environment API (`applyToEnvironment`)
if (config.build?.ssr) {
ssrBuild = true
return;
}

userEnabledSourceMaps = !!config.build?.sourcemap;

if (!config.customLogger) {
Expand Down Expand Up @@ -161,6 +172,7 @@ export function prerenderPlugin({ prerenderScript, renderTarget, additionalPrere
config.build.sourcemap = true;
},
configResolved(config) {
if (ssrBuild) return;
// We're only going to alter the chunking behavior in the default cases, where the user and/or
// other plugins haven't already configured this. It'd be impossible to avoid breakages otherwise.
if (
Expand All @@ -181,7 +193,7 @@ export function prerenderPlugin({ prerenderScript, renderTarget, additionalPrere
viteConfig = config;
},
async options(opts) {
if (!opts.input) return;
if (ssrBuild || !opts.input) return;
if (!prerenderScript) {
prerenderScript = await getPrerenderScriptFromHTML(opts.input);
}
Expand All @@ -197,6 +209,7 @@ export function prerenderPlugin({ prerenderScript, renderTarget, additionalPrere
},
// Injects window checks into Vite's preload helper & modulepreload polyfill
transform(code, id) {
if (ssrBuild) return;
if (id.includes(preloadHelperId)) {
// Injects a window check into Vite's preload helper, instantly resolving
// the module rather than attempting to add a <link> to the document.
Expand Down Expand Up @@ -238,6 +251,7 @@ export function prerenderPlugin({ prerenderScript, renderTarget, additionalPrere
}
},
async generateBundle(_opts, bundle) {
if (ssrBuild) return;
// @ts-ignore
globalThis.location = {};
// @ts-ignore
Expand Down
44 changes: 44 additions & 0 deletions tests/environments.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import { test } from 'uvu';
import * as assert from 'uvu/assert';

import { setupTest, teardownTest, loadFixture, viteBuild, viteBuildCli } from './lib/lifecycle.js';

let env;
test.before.each(async () => {
env = await setupTest();
});

test.after.each(async () => {
await teardownTest(env);
});

test('Should skip plugin during SSR build', async () => {
await loadFixture('environments/ssr', env);

let message = '';
try {
await viteBuild(env.tmp.path);
} catch (error) {
message = error.message;
}

assert.match(message, '');
});

test('Should skip plugin during SSR build (CLI)', async () => {
await loadFixture('simple', env);
const output = await viteBuildCli(env.tmp.path, ['--ssr', 'src/index.js']);
await output.done;

assert.equal(output.stderr, []);
});

test('Should skip plugin during non-client environment build (Cloudflare plugin)', async () => {
await loadFixture('environments/cloudflare', env);
const output = await viteBuildCli(env.tmp.path);
await output.done;

assert.equal(output.stderr, []);
});

test.run();
9 changes: 9 additions & 0 deletions tests/fixtures/environments/cloudflare/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
</head>
<body>
<script prerender type="module" src="/src/index.js"></script>
</body>
</html>
3 changes: 3 additions & 0 deletions tests/fixtures/environments/cloudflare/src/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export async function prerender() {
return `<h1>Simple Test Result</h1>`;
}
1 change: 1 addition & 0 deletions tests/fixtures/environments/cloudflare/src/server.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
console.log("Server is running...");
9 changes: 9 additions & 0 deletions tests/fixtures/environments/cloudflare/vite.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import { defineConfig } from 'vite';
import { vitePrerenderPlugin } from 'vite-prerender-plugin';
import { cloudflare } from '@cloudflare/vite-plugin';

console.log('Config is used');

export default defineConfig({
plugins: [cloudflare(), vitePrerenderPlugin()],
});
4 changes: 4 additions & 0 deletions tests/fixtures/environments/cloudflare/wrangler.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
name = "my-worker"
compatibility_date = "2023-03-01"

main = "src/server.js"
9 changes: 9 additions & 0 deletions tests/fixtures/environments/ssr/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
</head>
<body>
<script prerender type="module" src="/src/index.js"></script>
</body>
</html>
3 changes: 3 additions & 0 deletions tests/fixtures/environments/ssr/src/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export async function prerender() {
return `<h1>Simple Test Result</h1>`;
}
12 changes: 12 additions & 0 deletions tests/fixtures/environments/ssr/vite.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import { defineConfig } from 'vite';
import { vitePrerenderPlugin } from 'vite-prerender-plugin';

export default defineConfig({
build: {
ssr: true,
rollupOptions: {
input: 'src/index.js'
}
},
plugins: [vitePrerenderPlugin()],
});
1 change: 0 additions & 1 deletion tests/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,6 @@ test('Should support custom output filenames', async () => {
plugins: [vitePrerenderPlugin()],
});
`);
await viteBuild(env.tmp.path);

let message = '';
try {
Expand Down
5 changes: 3 additions & 2 deletions tests/lib/lifecycle.js
Original file line number Diff line number Diff line change
Expand Up @@ -50,9 +50,10 @@ export async function viteBuild(cwd) {

/**
* @param {string} cwd
* @param {string[]} flags
*/
export async function viteBuildCli(cwd) {
const child = childProcess.spawn('node', ['node_modules/vite/bin/vite.js', 'build'], {
export async function viteBuildCli(cwd, flags = []) {
const child = childProcess.spawn('node', ['node_modules/vite/bin/vite.js', 'build', ...flags], {
cwd,
});

Expand Down
3 changes: 3 additions & 0 deletions tests/lib/utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,9 @@ export async function copyDependencies(cwd) {
await copyNodeModule('source-map');
await copyNodeModule('stack-trace');
await copyNodeModule('kolorist');

// Dependencies used by tests
await copyNodeModule('@cloudflare/vite-plugin');
}

/**
Expand Down