Add dataRoutes field to routes-manifest for SSG and serverProps routes (#10622)
* Add dataRoutes field to routes-manifest for SSG and serverProps routes * Update routes-manifest test
This commit is contained in:
parent
395714a475
commit
6dea45bdc9
4 changed files with 186 additions and 69 deletions
|
@ -569,12 +569,13 @@ export default async function build(dir: string, conf = null): Promise<void> {
|
|||
)
|
||||
staticCheckWorkers.end()
|
||||
|
||||
if (serverPropsPages.size > 0) {
|
||||
if (serverPropsPages.size > 0 || ssgPages.size > 0) {
|
||||
// We update the routes manifest after the build with the
|
||||
// serverProps routes since we can't determine this until after build
|
||||
routesManifest.serverPropsRoutes = {}
|
||||
|
||||
for (const page of serverPropsPages) {
|
||||
// data routes since we can't determine these until after build
|
||||
routesManifest.dataRoutes = getSortedRoutes([
|
||||
...serverPropsPages,
|
||||
...ssgPages,
|
||||
]).map(page => {
|
||||
const pagePath = normalizePagePath(page)
|
||||
const dataRoute = path.posix.join(
|
||||
'/_next/data',
|
||||
|
@ -582,7 +583,7 @@ export default async function build(dir: string, conf = null): Promise<void> {
|
|||
`${pagePath}.json`
|
||||
)
|
||||
|
||||
routesManifest.serverPropsRoutes[page] = {
|
||||
return {
|
||||
page,
|
||||
dataRouteRegex: isDynamicRoute(page)
|
||||
? getRouteRegex(dataRoute.replace(/\.json$/, '')).re.source.replace(
|
||||
|
@ -597,7 +598,7 @@ export default async function build(dir: string, conf = null): Promise<void> {
|
|||
)}$`
|
||||
).source,
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
await fsWriteFile(
|
||||
routesManifestPath,
|
||||
|
|
|
@ -15,6 +15,7 @@ import {
|
|||
normalizeRegEx,
|
||||
} from 'next-test-utils'
|
||||
import cheerio from 'cheerio'
|
||||
import escapeRegex from 'escape-string-regexp'
|
||||
|
||||
jasmine.DEFAULT_TIMEOUT_INTERVAL = 1000 * 60 * 2
|
||||
|
||||
|
@ -485,6 +486,10 @@ function runTests(dev) {
|
|||
route.regex = normalizeRegEx(route.regex)
|
||||
}
|
||||
|
||||
for (const route of manifest.dataRoutes) {
|
||||
route.dataRouteRegex = normalizeRegEx(route.dataRouteRegex)
|
||||
}
|
||||
|
||||
expect(manifest).toEqual({
|
||||
version: 1,
|
||||
pages404: true,
|
||||
|
@ -492,6 +497,32 @@ function runTests(dev) {
|
|||
headers: [],
|
||||
rewrites: [],
|
||||
redirects: [],
|
||||
dataRoutes: [
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/p1\\/p2\\/all\\-ssg\\/(.+?)\\.json$`
|
||||
),
|
||||
page: '/p1/p2/all-ssg/[...rest]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/p1\\/p2\\/nested\\-all\\-ssg\\/(.+?)\\.json$`
|
||||
),
|
||||
page: '/p1/p2/nested-all-ssg/[...rest]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/p1\\/p2\\/predefined\\-ssg\\/(.+?)\\.json$`
|
||||
),
|
||||
page: '/p1/p2/predefined-ssg/[...rest]',
|
||||
},
|
||||
],
|
||||
dynamicRoutes: [
|
||||
{
|
||||
page: '/blog/[name]/comment/[id]',
|
||||
|
|
|
@ -25,72 +25,72 @@ let appPort
|
|||
let buildId
|
||||
let stderr
|
||||
|
||||
const expectedManifestRoutes = () => ({
|
||||
'/something': {
|
||||
page: '/something',
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/something.json$`
|
||||
),
|
||||
},
|
||||
'/blog/[post]': {
|
||||
page: '/blog/[post]',
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/blog\\/([^/]+?)\\.json$`
|
||||
),
|
||||
},
|
||||
'/': {
|
||||
page: '/',
|
||||
const expectedManifestRoutes = () => [
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/index.json$`
|
||||
),
|
||||
page: '/',
|
||||
},
|
||||
'/default-revalidate': {
|
||||
page: '/default-revalidate',
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/default-revalidate.json$`
|
||||
),
|
||||
},
|
||||
'/catchall/[...path]': {
|
||||
page: '/catchall/[...path]',
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/catchall\\/(.+?)\\.json$`
|
||||
),
|
||||
},
|
||||
'/blog': {
|
||||
page: '/blog',
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/blog.json$`
|
||||
),
|
||||
},
|
||||
'/blog/[post]/[comment]': {
|
||||
page: '/blog/[post]/[comment]',
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/blog\\/([^/]+?)\\/([^/]+?)\\.json$`
|
||||
),
|
||||
},
|
||||
'/user/[user]/profile': {
|
||||
page: '/user/[user]/profile',
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/user\\/([^/]+?)\\/profile\\.json$`
|
||||
),
|
||||
},
|
||||
'/another': {
|
||||
page: '/another',
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/another.json$`
|
||||
),
|
||||
page: '/another',
|
||||
},
|
||||
'/invalid-keys': {
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/blog.json$`
|
||||
),
|
||||
page: '/blog',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/blog\\/([^\\/]+?)\\.json$`
|
||||
),
|
||||
page: '/blog/[post]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/blog\\/([^\\/]+?)\\/([^\\/]+?)\\.json$`
|
||||
),
|
||||
page: '/blog/[post]/[comment]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/catchall\\/(.+?)\\.json$`
|
||||
),
|
||||
page: '/catchall/[...path]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/default-revalidate.json$`
|
||||
),
|
||||
page: '/default-revalidate',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/invalid-keys.json$`
|
||||
),
|
||||
page: '/invalid-keys',
|
||||
},
|
||||
})
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/something.json$`
|
||||
),
|
||||
page: '/something',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/user\\/([^\\/]+?)\\/profile\\.json$`
|
||||
),
|
||||
page: '/user/[user]/profile',
|
||||
},
|
||||
]
|
||||
|
||||
const navigateTest = (dev = false) => {
|
||||
it('should navigate between pages successfully', async () => {
|
||||
|
@ -209,7 +209,10 @@ const runTests = (dev = false) => {
|
|||
expect(JSON.parse(query)).toEqual({ path: ['first'] })
|
||||
|
||||
const data = JSON.parse(
|
||||
await renderViaHTTP(appPort, `/_next/data/${buildId}/catchall/first.json`)
|
||||
await renderViaHTTP(
|
||||
appPort,
|
||||
`/_next/data/${escapeRegex(buildId)}/catchall/first.json`
|
||||
)
|
||||
)
|
||||
|
||||
expect(data.pageProps.params).toEqual({ path: ['first'] })
|
||||
|
@ -217,7 +220,10 @@ const runTests = (dev = false) => {
|
|||
|
||||
it('should return data correctly', async () => {
|
||||
const data = JSON.parse(
|
||||
await renderViaHTTP(appPort, `/_next/data/${buildId}/something.json`)
|
||||
await renderViaHTTP(
|
||||
appPort,
|
||||
`/_next/data/${escapeRegex(buildId)}/something.json`
|
||||
)
|
||||
)
|
||||
expect(data.pageProps.world).toBe('world')
|
||||
})
|
||||
|
@ -226,7 +232,7 @@ const runTests = (dev = false) => {
|
|||
const data = JSON.parse(
|
||||
await renderViaHTTP(
|
||||
appPort,
|
||||
`/_next/data/${buildId}/something.json?another=thing`
|
||||
`/_next/data/${escapeRegex(buildId)}/something.json?another=thing`
|
||||
)
|
||||
)
|
||||
expect(data.pageProps.query.another).toBe('thing')
|
||||
|
@ -234,7 +240,10 @@ const runTests = (dev = false) => {
|
|||
|
||||
it('should return data correctly for dynamic page', async () => {
|
||||
const data = JSON.parse(
|
||||
await renderViaHTTP(appPort, `/_next/data/${buildId}/blog/post-1.json`)
|
||||
await renderViaHTTP(
|
||||
appPort,
|
||||
`/_next/data/${escapeRegex(buildId)}/blog/post-1.json`
|
||||
)
|
||||
)
|
||||
expect(data.pageProps.post).toBe('post-1')
|
||||
})
|
||||
|
@ -367,15 +376,14 @@ const runTests = (dev = false) => {
|
|||
})
|
||||
|
||||
it('should output routes-manifest correctly', async () => {
|
||||
const { serverPropsRoutes } = await fs.readJSON(
|
||||
const { dataRoutes } = await fs.readJSON(
|
||||
join(appDir, '.next/routes-manifest.json')
|
||||
)
|
||||
for (const key of Object.keys(serverPropsRoutes)) {
|
||||
const val = serverPropsRoutes[key].dataRouteRegex
|
||||
serverPropsRoutes[key].dataRouteRegex = normalizeRegEx(val)
|
||||
for (const route of dataRoutes) {
|
||||
route.dataRouteRegex = normalizeRegEx(route.dataRouteRegex)
|
||||
}
|
||||
|
||||
expect(serverPropsRoutes).toEqual(expectedManifestRoutes())
|
||||
expect(dataRoutes).toEqual(expectedManifestRoutes())
|
||||
})
|
||||
|
||||
it('should set no-cache, no-store, must-revalidate header', async () => {
|
||||
|
|
|
@ -589,6 +589,83 @@ const runTests = (dev = false, looseMode = false) => {
|
|||
})
|
||||
}
|
||||
|
||||
it('outputs dataRoutes in routes-manifest correctly', async () => {
|
||||
const { dataRoutes } = JSON.parse(
|
||||
await fs.readFile(join(appDir, '.next/routes-manifest.json'), 'utf8')
|
||||
)
|
||||
|
||||
for (const route of dataRoutes) {
|
||||
route.dataRouteRegex = normalizeRegEx(route.dataRouteRegex)
|
||||
}
|
||||
|
||||
expect(dataRoutes).toEqual([
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/index.json$`
|
||||
),
|
||||
page: '/',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/another.json$`
|
||||
),
|
||||
page: '/another',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/blog.json$`
|
||||
),
|
||||
page: '/blog',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/blog\\/([^\\/]+?)\\.json$`
|
||||
),
|
||||
page: '/blog/[post]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/blog\\/([^\\/]+?)\\/([^\\/]+?)\\.json$`
|
||||
),
|
||||
page: '/blog/[post]/[comment]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/catchall\\/(.+?)\\.json$`
|
||||
),
|
||||
page: '/catchall/[...slug]',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/default-revalidate.json$`
|
||||
),
|
||||
page: '/default-revalidate',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(buildId)}\\/something.json$`
|
||||
),
|
||||
page: '/something',
|
||||
},
|
||||
{
|
||||
dataRouteRegex: normalizeRegEx(
|
||||
`^\\/_next\\/data\\/${escapeRegex(
|
||||
buildId
|
||||
)}\\/user\\/([^\\/]+?)\\/profile\\.json$`
|
||||
),
|
||||
page: '/user/[user]/profile',
|
||||
},
|
||||
])
|
||||
})
|
||||
|
||||
it('outputs a prerender-manifest correctly', async () => {
|
||||
const manifest = JSON.parse(
|
||||
await fs.readFile(join(appDir, '.next/prerender-manifest.json'), 'utf8')
|
||||
|
|
Loading…
Reference in a new issue