Skip to content

Commit

Permalink
patch 404 as non-streaming in dev
Browse files Browse the repository at this point in the history
  • Loading branch information
huozhi committed Nov 5, 2021
1 parent 1f311e3 commit aa53bac
Show file tree
Hide file tree
Showing 9 changed files with 51 additions and 31 deletions.
10 changes: 5 additions & 5 deletions packages/next/build/entries.ts
Expand Up @@ -12,7 +12,7 @@ import { ClientPagesLoaderOptions } from './webpack/loaders/next-client-pages-lo
import { ServerlessLoaderQuery } from './webpack/loaders/next-serverless-loader'
import { LoadedEnvFiles } from '@next/env'
import { NextConfigComplete } from '../server/config-shared'
import { isFlightPage, isReservedPage } from './utils'
import { isCustomErrorPage, isFlightPage, isReservedPage } from './utils'
import { ssrEntries } from './webpack/plugins/middleware-plugin'
import type { webpack5 } from 'next/dist/compiled/webpack/webpack'
import { MIDDLEWARE_SSR_RUNTIME_WEBPACK } from '../shared/lib/constants'
Expand Down Expand Up @@ -142,8 +142,8 @@ export function createEntrypoints(

const isLikeServerless = isTargetLikeServerless(target)
const isReserved = isReservedPage(page)
const isFlight =
hasServerComponents && isFlightPage(config, absolutePagePath)
const isCustomError = isCustomErrorPage(page)
const isFlight = isFlightPage(config, absolutePagePath)

const webServerRuntime = !!config.experimental.concurrentFeatures

Expand All @@ -159,7 +159,7 @@ export function createEntrypoints(
return
}

if (webServerRuntime && !isReserved && !isApiRoute) {
if (webServerRuntime && !isReserved && !isCustomError && !isApiRoute) {
ssrEntries.set(clientBundlePath, { requireFlightManifest: isFlight })
serverWeb[serverBundlePath] = finalizeEntrypoint({
name: '[name].js',
Expand Down Expand Up @@ -188,7 +188,7 @@ export function createEntrypoints(
serverlessLoaderOptions
)}!`
} else if (isApiRoute || target === 'server') {
if (!webServerRuntime || isReserved) {
if (!webServerRuntime || isReserved || isCustomError) {
server[serverBundlePath] = [absolutePagePath]
}
} else if (
Expand Down
7 changes: 2 additions & 5 deletions packages/next/build/index.ts
Expand Up @@ -1385,9 +1385,8 @@ export default async function build(
const combinedPages = [...staticPages, ...ssgPages]

if (
(!hasConcurrentFeatures && combinedPages.length > 0) ||
useStatic404 ||
useDefaultStatic500
!hasConcurrentFeatures &&
(combinedPages.length > 0 || useStatic404 || useDefaultStatic500)
) {
const staticGenerationSpan = nextBuildSpan.traceChild('static-generation')
await staticGenerationSpan.traceAsyncFn(async () => {
Expand Down Expand Up @@ -1653,12 +1652,10 @@ export default async function build(
}

// Only move /404 to /404 when there is no custom 404 as in that case we don't know about the 404 page
console.log('!hasPages404 && useStatic404', !hasPages404, useStatic404)
if (!hasPages404 && useStatic404) {
await moveExportedPage('/_error', '/404', '/404', false, 'html')
}

console.log('useDefaultStatic500', useDefaultStatic500)
if (useDefaultStatic500) {
await moveExportedPage('/_error', '/500', '/500', false, 'html')
}
Expand Down
4 changes: 4 additions & 0 deletions packages/next/build/utils.ts
Expand Up @@ -1149,3 +1149,7 @@ export function getUnresolvedModuleFromError(
export function isReservedPage(page: string) {
return RESERVED_PAGE.test(page)
}

export function isCustomErrorPage(page: string) {
return page === '/404' || page === '/500'
}
23 changes: 19 additions & 4 deletions packages/next/server/dev/hot-reloader.ts
Expand Up @@ -29,7 +29,12 @@ import { fileExists } from '../../lib/file-exists'
import { ClientPagesLoaderOptions } from '../../build/webpack/loaders/next-client-pages-loader'
import { ssrEntries } from '../../build/webpack/plugins/middleware-plugin'
import { stringify } from 'querystring'
import { difference, isFlightPage, isReservedPage } from '../../build/utils'
import {
difference,
isCustomErrorPage,
isFlightPage,
isReservedPage,
} from '../../build/utils'
import { NextConfigComplete } from '../config-shared'
import { CustomRoutes } from '../../lib/load-custom-routes'
import { DecodeError } from '../../shared/lib/utils'
Expand Down Expand Up @@ -235,7 +240,6 @@ export default class HotReloader {
.map((param) => decodeURIComponent(param))
.join('/')}`
} catch (_) {
console.error(_)
throw new DecodeError('failed to decode param')
}

Expand Down Expand Up @@ -453,6 +457,7 @@ export default class HotReloader {
: 'server'.length
)
const isMiddleware = !!page.match(MIDDLEWARE_ROUTE)

if (isClientCompilation && page.match(API_ROUTE) && !isMiddleware) {
return
}
Expand All @@ -471,12 +476,18 @@ export default class HotReloader {
return
}

const isCustomError = isCustomErrorPage(page)
const isReserved = isReservedPage(page)
const isServerComponent =
this.hasServerComponents &&
isFlightPage(this.config, absolutePagePath)

if (isServerCompilation && this.webServerRuntime && !isApiRoute) {
if (
isServerCompilation &&
this.webServerRuntime &&
!isApiRoute &&
!isCustomError
) {
return
}

Expand All @@ -502,7 +513,11 @@ export default class HotReloader {

if (isServerComponent) {
ssrEntries.set(bundlePath, { requireFlightManifest: true })
} else if (this.webServerRuntime && !isReserved) {
} else if (
this.webServerRuntime &&
!isReserved &&
!isCustomError
) {
ssrEntries.set(bundlePath, { requireFlightManifest: false })
}
} else if (isServerWebCompilation) {
Expand Down
7 changes: 3 additions & 4 deletions packages/next/server/dev/next-dev-server.ts
Expand Up @@ -275,7 +275,8 @@ export default class DevServer extends Server {
!(
pageName === '/_app' ||
pageName === '/_error' ||
pageName === '/_document'
pageName === '/_document' ||
pageName === '/404'
)
) {
routedMiddleware.push(pageName)
Expand Down Expand Up @@ -393,7 +394,6 @@ export default class DevServer extends Server {
setGlobal('telemetry', telemetry)

process.on('unhandledRejection', (reason) => {
console.log('unhandledRejection', reason)
this.logErrorWithOriginalStack(reason, 'unhandledRejection').catch(
() => {}
)
Expand Down Expand Up @@ -874,7 +874,7 @@ export default class DevServer extends Server {
): Promise<FindComponentsResult | null> {
await this.devReady
const compilationErr = await this.getCompilationError(pathname)
// console.trace('findPageComponents:dev')

if (compilationErr) {
// Wrap build errors so that they don't get logged again
throw new WrappedBuildError(compilationErr)
Expand All @@ -883,7 +883,6 @@ export default class DevServer extends Server {
await this.hotReloader!.ensurePage(pathname)
return super.findPageComponents(pathname, query, params)
} catch (err) {
console.error(err)
if ((err as any).code !== 'ENOENT') {
throw err
}
Expand Down
9 changes: 7 additions & 2 deletions packages/next/server/dev/on-demand-entry-handler.ts
Expand Up @@ -9,6 +9,7 @@ import { API_ROUTE, MIDDLEWARE_ROUTE } from '../../lib/constants'
import { reportTrigger } from '../../build/output'
import type ws from 'ws'
import { NextConfigComplete } from '../config-shared'
import { isCustomErrorPage } from '../../build/utils'

export const ADDED = Symbol('added')
export const BUILDING = Symbol('building')
Expand Down Expand Up @@ -158,7 +159,7 @@ export default function onDemandEntryHandler(
try {
normalizedPagePath = normalizePagePath(page)
} catch (err) {
console.error('normalizedPagePath', err)
console.error(err)
throw pageNotFoundError(page)
}

Expand Down Expand Up @@ -204,6 +205,7 @@ export default function onDemandEntryHandler(
const isMiddleware = normalizedPage.match(MIDDLEWARE_ROUTE)
const isApiRoute = normalizedPage.match(API_ROUTE) && !isMiddleware
const isServerWeb = !!nextConfig.experimental.concurrentFeatures
const isCustomError = isCustomErrorPage(page)

let entriesChanged = false
const addPageEntry = (type: 'client' | 'server' | 'server-web') => {
Expand Down Expand Up @@ -243,13 +245,16 @@ export default function onDemandEntryHandler(
}

const isClientOnly = clientOnly || isMiddleware

const promise = isApiRoute
? addPageEntry('server')
: isClientOnly
? addPageEntry('client')
: Promise.all([
addPageEntry('client'),
addPageEntry(isServerWeb ? 'server-web' : 'server'),
addPageEntry(
isServerWeb && !isCustomError ? 'server-web' : 'server'
),
])

if (entriesChanged) {
Expand Down
11 changes: 1 addition & 10 deletions packages/next/server/next-server.ts
Expand Up @@ -1135,7 +1135,6 @@ export default class Server {

let result: FetchEventResult | null = null

console.log('runMiddleware')
try {
result = await this.runMiddleware({
request: req,
Expand Down Expand Up @@ -1356,9 +1355,7 @@ export default class Server {
pathname,
this.nextConfig.i18n?.locales
))
} catch (_) {
console.error(_)
}
} catch (_) {}

return found
}
Expand Down Expand Up @@ -1538,7 +1535,6 @@ export default class Server {
parsedUrl: UrlWithParsedQuery
): Promise<void> {
this.handleCompression(req, res)
console.trace('run')

try {
const matched = await this.router.execute(req, res, parsedUrl)
Expand Down Expand Up @@ -1695,7 +1691,6 @@ export default class Server {

for (const pagePath of paths) {
try {
console.log('loadComponents', pagePath)
const components = await loadComponents(
this.distDir,
pagePath!,
Expand Down Expand Up @@ -1727,8 +1722,6 @@ export default class Server {
},
}
} catch (err) {
// @ts-ignore
console.error('err', err)
if (isError(err) && err.code !== 'ENOENT') throw err
}
}
Expand Down Expand Up @@ -2388,14 +2381,12 @@ export default class Server {
result!
)
} catch (maybeFallbackError) {
console.error('maybeFallbackError', maybeFallbackError)
if (maybeFallbackError instanceof NoFallbackError) {
throw new Error('invariant: failed to render error page')
}
throw maybeFallbackError
}
} catch (error) {
console.error('error', error)
const renderToHtmlError = isError(error)
? error
: error
Expand Down
@@ -1,3 +1,3 @@
export default function Page404() {
return '404-page'
return 'custom-404-page'
}
Expand Up @@ -199,11 +199,20 @@ async function runBasicTests(context) {
'/routes/dynamic2'
)

const path404HTML = await renderViaHTTP(context.appPort, '/404')
const pathNotFoundHTML = await renderViaHTTP(
context.appPort,
'/this-is-not-found'
)

expect(homeHTML).toContain('thisistheindexpage.server')
expect(homeHTML).toContain('foo.client')

expect(dynamicRouteHTML1).toContain('[pid]')
expect(dynamicRouteHTML2).toContain('[pid]')

expect(path404HTML).toContain('custom-404-page')
expect(pathNotFoundHTML).toContain('custom-404-page')
})

it('should suspense next/link on server side', async () => {
Expand Down

0 comments on commit aa53bac

Please sign in to comment.