Skip to content

Commit 4792ded

Browse files
[Fix] Add prerendered assets to Vercel config (#8332)
* Add prerendered assets to Vercel config * use adapter-vercel logic inside adapter-static * simplify * update changeset * add adapter-vercel changeset Co-authored-by: Rich Harris <[email protected]>
1 parent ac2b2a8 commit 4792ded

File tree

5 files changed

+103
-104
lines changed

5 files changed

+103
-104
lines changed

.changeset/healthy-singers-stare.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'@sveltejs/adapter-vercel': patch
3+
---
4+
5+
[fix] only apply immutable cache-control headers to immutable assets

.changeset/old-chicken-cough.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'@sveltejs/adapter-static': patch
3+
---
4+
5+
[fix] match `adapter-vercel` logic for serving prerendered content

packages/adapter-static/index.js

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -71,9 +71,7 @@ See https://kit.svelte.dev/docs/page-options#prerender for more details`
7171
assets = pages,
7272
fallback,
7373
precompress
74-
} = options ??
75-
platform?.defaults(builder.config) ??
76-
/** @type {import('./index').AdapterOptions} */ ({});
74+
} = options ?? platform?.defaults ?? /** @type {import('./index').AdapterOptions} */ ({});
7775

7876
builder.rimraf(assets);
7977
builder.rimraf(pages);

packages/adapter-static/platforms.js

Lines changed: 38 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -4,26 +4,22 @@ import fs from 'fs';
44
* @typedef {{
55
* name: string;
66
* test: () => boolean;
7-
* defaults: (config: any) => import('./index').AdapterOptions; // TODO
7+
* defaults: import('./index').AdapterOptions;
88
* done: (builder: import('@sveltejs/kit').Builder) => void;
99
* }}
1010
* Platform */
1111

12+
// This function is duplicated in adapter-vercel
1213
/** @param {import('@sveltejs/kit').Builder} builder */
13-
function vercel_routes(builder) {
14+
function static_vercel_config(builder) {
1415
/** @type {any[]} */
15-
const routes = [
16-
{
17-
src: `/${builder.config.kit.appDir}/immutable/.+`,
18-
headers: {
19-
'cache-control': 'public, immutable, max-age=31536000'
20-
}
21-
}
22-
];
16+
const prerendered_redirects = [];
17+
18+
/** @type {Record<string, { path: string }>} */
19+
const overrides = {};
2320

24-
// explicit redirects
2521
for (const [src, redirect] of builder.prerendered.redirects) {
26-
routes.push({
22+
prerendered_redirects.push({
2723
src,
2824
headers: {
2925
Location: redirect.location
@@ -32,51 +28,48 @@ function vercel_routes(builder) {
3228
});
3329
}
3430

35-
// prerendered pages
36-
for (const [src, page] of builder.prerendered.pages) {
37-
routes.push({
38-
src,
39-
dest: `${builder.config.kit.appDir}/prerendered/${page.file}`
40-
});
41-
}
31+
for (const [path, page] of builder.prerendered.pages) {
32+
if (path.endsWith('/') && path !== '/') {
33+
prerendered_redirects.push(
34+
{ src: path, dest: path.slice(0, -1) },
35+
{ src: path.slice(0, -1), status: 308, headers: { Location: path } }
36+
);
4237

43-
// implicit redirects (trailing slashes)
44-
for (const [src] of builder.prerendered.pages) {
45-
if (src !== '/') {
46-
routes.push({
47-
src: src.endsWith('/') ? src.slice(0, -1) : src + '/',
48-
headers: {
49-
location: src
50-
},
51-
status: 308
52-
});
38+
overrides[page.file] = { path: path.slice(1, -1) };
39+
} else {
40+
overrides[page.file] = { path: path.slice(1) };
5341
}
5442
}
5543

56-
routes.push({
57-
handle: 'filesystem'
58-
});
59-
60-
return routes;
44+
return {
45+
version: 3,
46+
routes: [
47+
...prerendered_redirects,
48+
{
49+
src: `/${builder.getAppPath()}/immutable/.+`,
50+
headers: {
51+
'cache-control': 'public, immutable, max-age=31536000'
52+
}
53+
},
54+
{
55+
handle: 'filesystem'
56+
}
57+
],
58+
overrides
59+
};
6160
}
6261

6362
/** @type {Platform[]} */
6463
export const platforms = [
6564
{
6665
name: 'Vercel',
6766
test: () => !!process.env.VERCEL,
68-
defaults: (config) => ({
69-
pages: `.vercel/output/static/${config.kit.appDir}/prerendered`,
70-
assets: '.vercel/output/static'
71-
}),
67+
defaults: {
68+
pages: '.vercel/output/static'
69+
},
7270
done: (builder) => {
73-
fs.writeFileSync(
74-
'.vercel/output/config.json',
75-
JSON.stringify({
76-
version: 3,
77-
routes: vercel_routes(builder)
78-
})
79-
);
71+
const config = static_vercel_config(builder);
72+
fs.writeFileSync('.vercel/output/config.json', JSON.stringify(config, null, ' '));
8073
}
8174
}
8275
];

packages/adapter-vercel/index.js

Lines changed: 54 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -25,48 +25,7 @@ const plugin = function ({ external = [], edge, split } = {}) {
2525
functions: `${dir}/functions`
2626
};
2727

28-
/** @type {any[]} */
29-
const prerendered_redirects = [];
30-
31-
/** @type {Record<string, { path: string }>} */
32-
const overrides = {};
33-
34-
for (const [src, redirect] of builder.prerendered.redirects) {
35-
prerendered_redirects.push({
36-
src,
37-
headers: {
38-
Location: redirect.location
39-
},
40-
status: redirect.status
41-
});
42-
}
43-
44-
for (const [path, page] of builder.prerendered.pages) {
45-
if (path.endsWith('/') && path !== '/') {
46-
prerendered_redirects.push(
47-
{ src: path, dest: path.slice(0, -1) },
48-
{ src: path.slice(0, -1), status: 308, headers: { Location: path } }
49-
);
50-
51-
overrides[page.file] = { path: path.slice(1, -1) };
52-
} else {
53-
overrides[page.file] = { path: path.slice(1) };
54-
}
55-
}
56-
57-
/** @type {any[]} */
58-
const routes = [
59-
...prerendered_redirects,
60-
{
61-
src: `/${builder.getAppPath()}/.+`,
62-
headers: {
63-
'cache-control': 'public, immutable, max-age=31536000'
64-
}
65-
},
66-
{
67-
handle: 'filesystem'
68-
}
69-
];
28+
const config = static_vercel_config(builder);
7029

7130
builder.log.minor('Generating serverless function...');
7231

@@ -97,7 +56,7 @@ const plugin = function ({ external = [], edge, split } = {}) {
9756
`nodejs${node_version.major}.x`
9857
);
9958

100-
routes.push({ src: pattern, dest: `/${name}` });
59+
config.routes.push({ src: pattern, dest: `/${name}` });
10160
}
10261

10362
/**
@@ -142,7 +101,7 @@ const plugin = function ({ external = [], edge, split } = {}) {
142101
})
143102
);
144103

145-
routes.push({ src: pattern, dest: `/${name}` });
104+
config.routes.push({ src: pattern, dest: `/${name}` });
146105
}
147106

148107
const generate_function = edge ? generate_edge_function : generate_serverless_function;
@@ -182,18 +141,7 @@ const plugin = function ({ external = [], edge, split } = {}) {
182141

183142
builder.log.minor('Writing routes...');
184143

185-
write(
186-
`${dir}/config.json`,
187-
JSON.stringify(
188-
{
189-
version: 3,
190-
routes,
191-
overrides
192-
},
193-
null,
194-
' '
195-
)
196-
);
144+
write(`${dir}/config.json`, JSON.stringify(config, null, ' '));
197145
}
198146
};
199147
};
@@ -225,6 +173,56 @@ function get_node_version() {
225173
return { major, full };
226174
}
227175

176+
// This function is duplicated in adapter-static
177+
/** @param {import('@sveltejs/kit').Builder} builder */
178+
function static_vercel_config(builder) {
179+
/** @type {any[]} */
180+
const prerendered_redirects = [];
181+
182+
/** @type {Record<string, { path: string }>} */
183+
const overrides = {};
184+
185+
for (const [src, redirect] of builder.prerendered.redirects) {
186+
prerendered_redirects.push({
187+
src,
188+
headers: {
189+
Location: redirect.location
190+
},
191+
status: redirect.status
192+
});
193+
}
194+
195+
for (const [path, page] of builder.prerendered.pages) {
196+
if (path.endsWith('/') && path !== '/') {
197+
prerendered_redirects.push(
198+
{ src: path, dest: path.slice(0, -1) },
199+
{ src: path.slice(0, -1), status: 308, headers: { Location: path } }
200+
);
201+
202+
overrides[page.file] = { path: path.slice(1, -1) };
203+
} else {
204+
overrides[page.file] = { path: path.slice(1) };
205+
}
206+
}
207+
208+
return {
209+
version: 3,
210+
routes: [
211+
...prerendered_redirects,
212+
{
213+
src: `/${builder.getAppPath()}/immutable/.+`,
214+
headers: {
215+
'cache-control': 'public, immutable, max-age=31536000'
216+
}
217+
},
218+
{
219+
handle: 'filesystem'
220+
}
221+
],
222+
overrides
223+
};
224+
}
225+
228226
/**
229227
* @param {import('@sveltejs/kit').Builder} builder
230228
* @param {string} entry

0 commit comments

Comments
 (0)