diff --git a/packages/next/server/next-server.ts b/packages/next/server/next-server.ts index fec28ec7d022b..851f57ea8da6e 100644 --- a/packages/next/server/next-server.ts +++ b/packages/next/server/next-server.ts @@ -74,7 +74,7 @@ import BaseServer, { NoFallbackError, RequestContext, } from './base-server' -import { getPagePath, requireFontManifest } from './require' +import { getMaybePagePath, getPagePath, requireFontManifest } from './require' import { denormalizePagePath } from '../shared/lib/page-path/denormalize-page-path' import { normalizePagePath } from '../shared/lib/page-path/normalize-page-path' import { loadComponents } from './load-components' @@ -327,12 +327,12 @@ export default class NextNodeServer extends BaseServer { } protected async hasPage(pathname: string): Promise { - let found = false - try { - found = !!this.getPagePath(pathname, this.nextConfig.i18n?.locales) - } catch (_) {} - - return found + return !!getMaybePagePath( + pathname, + this.distDir, + this.nextConfig.i18n?.locales, + this.hasAppDir + ) } protected getBuildId(): string { diff --git a/packages/next/server/require.ts b/packages/next/server/require.ts index 2bbcdfe1dc7e3..2de811ff13fc4 100644 --- a/packages/next/server/require.ts +++ b/packages/next/server/require.ts @@ -11,13 +11,33 @@ import { normalizePagePath } from '../shared/lib/page-path/normalize-page-path' import { denormalizePagePath } from '../shared/lib/page-path/denormalize-page-path' import type { PagesManifest } from '../build/webpack/plugins/pages-manifest-plugin' import { PageNotFoundError, MissingStaticPage } from '../shared/lib/utils' +import LRUCache from 'next/dist/compiled/lru-cache' -export function getPagePath( +const pagePathCache = + process.env.NODE_ENV === 'development' + ? { + get: (_key: string) => { + return null + }, + set: () => {}, + has: () => false, + } + : new LRUCache({ + max: 1000, + }) + +export function getMaybePagePath( page: string, distDir: string, locales?: string[], appDirEnabled?: boolean -): string { +): string | null { + const cacheKey = `${page}:${locales}` + + if (pagePathCache.has(cacheKey)) { + return pagePathCache.get(cacheKey) as string | null + } + const serverBuildPath = join(distDir, SERVER_DIRECTORY) let appPathsManifest: undefined | PagesManifest @@ -60,10 +80,30 @@ export function getPagePath( pagePath = checkManifest(pagesManifest) } + if (!pagePath) { + pagePathCache.set(cacheKey, null) + return null + } + + const path = join(serverBuildPath, pagePath) + pagePathCache.set(cacheKey, path) + + return path +} + +export function getPagePath( + page: string, + distDir: string, + locales?: string[], + appDirEnabled?: boolean +): string { + const pagePath = getMaybePagePath(page, distDir, locales, appDirEnabled) + if (!pagePath) { throw new PageNotFoundError(page) } - return join(serverBuildPath, pagePath) + + return pagePath } export function requirePage(