Skip to content

Commit

Permalink
feat(vercel): incremental static generation + swr (#545)
Browse files Browse the repository at this point in the history
  • Loading branch information
danielroe committed Nov 15, 2022
1 parent 0ccdc18 commit 88ce2de
Show file tree
Hide file tree
Showing 5 changed files with 50 additions and 4 deletions.
26 changes: 24 additions & 2 deletions src/presets/vercel.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { resolve } from 'pathe'
import fsp from 'fs/promises'
import { dirname, relative, resolve } from 'pathe'
import { defu } from 'defu'
import { withoutLeadingSlash } from 'ufo'
import { writeFile } from '../utils'
Expand Down Expand Up @@ -34,6 +35,18 @@ export const vercel = defineNitroPreset({
shouldAddHelpers: false
}
await writeFile(functionConfigPath, JSON.stringify(functionConfig, null, 2))

// Write prerender functions
for (const [key, value] of Object.entries(nitro.options.routeRules).filter(([_, value]) => value.cache && (value.cache.swr || value.cache.static))) {
if (!value.cache) { continue } // for type support
const funcPrefix = resolve(nitro.options.output.serverDir, '..' + generateEndpoint(key))
await fsp.mkdir(dirname(funcPrefix), { recursive: true })
await fsp.symlink('./' + relative(dirname(funcPrefix), nitro.options.output.serverDir), funcPrefix + '.func', 'junction')
await writeFile(funcPrefix + '.prerender-config.json', JSON.stringify({
expiration: value.cache.static ? false : typeof value.cache.swr === 'number' ? value.cache.swr : 60,
allowQuery: key.includes('/**') ? ['url'] : undefined
}))
}
}
}
})
Expand Down Expand Up @@ -72,7 +85,6 @@ export const vercelEdge = defineNitroPreset({
})

function generateBuildConfig (nitro: Nitro) {
// const overrides = generateOverrides(nitro._prerenderedRoutes?.filter(r => r.fileName !== r.route) || [])
return defu(nitro.options.vercel?.config, <VercelBuildConfigV3> {
version: 3,
overrides: Object.fromEntries(
Expand Down Expand Up @@ -112,10 +124,20 @@ function generateBuildConfig (nitro: Nitro) {
{
handle: 'filesystem'
},
...Object.entries(nitro.options.routeRules)
.filter(([key, value]) => value.cache && (value.cache.swr || value.cache.static) && key.includes('/**'))
.map(([key]) => ({
src: key.replace(/^(.*)\/\*\*/, '(?<url>$1/.*)'),
dest: generateEndpoint(key) + '?url=$url'
})),
{
src: '/(.*)',
dest: '/__nitro'
}
]
})
}

function generateEndpoint (url: string) {
return url.includes('/**') ? '/__nitro-' + withoutLeadingSlash(url.replace(/\/\*\*.*/, '').replace(/[^a-z]/g, '-')) : url
}
16 changes: 14 additions & 2 deletions src/runtime/entries/vercel.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,17 @@
import '#internal/nitro/virtual/polyfill'
import { toNodeListener } from 'h3'
import { toNodeListener, NodeListener } from 'h3'
import { parseQuery } from 'ufo'
import { nitroApp } from '../app'

export default toNodeListener(nitroApp.h3App)
const handler = toNodeListener(nitroApp.h3App)

export default <NodeListener> function (req, res) {
const query = req.headers['x-now-route-matches'] as string
if (query) {
const { url } = parseQuery(query)
if (url) {
req.url = url as string
}
}
return handler(req, res)
}
2 changes: 2 additions & 0 deletions test/presets/netlify.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@ describe('nitro:preset:netlify', async () => {
/rules/nested/* /base 302
/rules/redirect/obj https://nitro.unjs.io/ 301
/rules/redirect /base 302
/rules/swr-ttl/* /.netlify/builders/server 200
/rules/swr/* /.netlify/builders/server 200
/rules/static /.netlify/builders/server 200
/* /.netlify/functions/server 200"
`)
Expand Down
8 changes: 8 additions & 0 deletions test/presets/vercel.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,14 @@ describe('nitro:preset:vercel', async () => {
{
"handle": "filesystem",
},
{
"dest": "/__nitro--rules-swr?url=$url",
"src": "(?<url>/rules/swr/.*)",
},
{
"dest": "/__nitro--rules-swr-ttl?url=$url",
"src": "(?<url>/rules/swr-ttl/.*)",
},
{
"dest": "/__nitro",
"src": "/(.*)",
Expand Down
2 changes: 2 additions & 0 deletions test/tests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,8 @@ export async function setupTest (preset) {
'/rules/cors': { cors: true, headers: { 'access-control-allowed-methods': 'GET' } },
'/rules/redirect': { redirect: '/base' },
'/rules/static': { static: true },
'/rules/swr/**': { swr: true },
'/rules/swr-ttl/**': { swr: 60 },
'/rules/redirect/obj': {
redirect: { to: 'https://nitro.unjs.io/', statusCode: 308 }
},
Expand Down

0 comments on commit 88ce2de

Please sign in to comment.