fix: 404 and 500 route matching (#12182)

Co-authored-by: Florian Lefebvre <contact@florian-lefebvre.dev>
This commit is contained in:
Braden Wong 2025-01-13 11:05:44 -05:00 committed by GitHub
parent 0ef1613ea3
commit c30070b927
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 23 additions and 6 deletions

View file

@ -0,0 +1,5 @@
---
'astro': patch
---
Improves matching of 404 and 500 routes

View file

@ -17,6 +17,17 @@ export function matchAllRoutes(pathname: string, manifest: ManifestData): RouteD
return manifest.routes.filter((route) => route.pattern.test(decodeURI(pathname)));
}
const ROUTE404_RE = /^\/404\/?$/;
const ROUTE500_RE = /^\/500\/?$/;
export function isRoute404(route: string) {
return ROUTE404_RE.test(route);
}
export function isRoute500(route: string) {
return ROUTE500_RE.test(route);
}
/**
* Determines if the given route matches a 404 or 500 error page.
*
@ -24,5 +35,5 @@ export function matchAllRoutes(pathname: string, manifest: ManifestData): RouteD
* @returns {boolean} `true` if the route matches a 404 or 500 error page, otherwise `false`.
*/
export function isRoute404or500(route: RouteData): boolean {
return route.pattern.test('/404') || route.pattern.test('/500');
return isRoute404(route.route) || isRoute500(route.route);
}

View file

@ -4,6 +4,7 @@ import { shouldAppendForwardSlash } from '../core/build/util.js';
import { REROUTE_DIRECTIVE_HEADER } from '../core/constants.js';
import { MissingLocale, i18nNoLocaleFoundInPath } from '../core/errors/errors-data.js';
import { AstroError } from '../core/errors/index.js';
import { isRoute404, isRoute500 } from '../core/routing/match.js';
import type { AstroConfig, Locales, ValidRedirectStatus } from '../types/public/config.js';
import type { APIContext } from '../types/public/context.js';
import { createI18nMiddleware } from './middleware.js';
@ -17,8 +18,9 @@ export function requestHasLocale(locales: Locales) {
export function requestIs404Or500(request: Request, base = '') {
const url = new URL(request.url);
const pathname = url.pathname.slice(base.length);
return url.pathname.startsWith(`${base}/404`) || url.pathname.startsWith(`${base}/500`);
return isRoute404(pathname) || isRoute500(pathname);
}
// Checks if the pathname has any locale

View file

@ -15,6 +15,7 @@ import { getProps } from '../core/render/index.js';
import { createRequest } from '../core/request.js';
import { redirectTemplate } from '../core/routing/3xx.js';
import { matchAllRoutes } from '../core/routing/index.js';
import { isRoute404, isRoute500 } from '../core/routing/match.js';
import { PERSIST_SYMBOL } from '../core/session.js';
import { getSortedPreloadedMatches } from '../prerender/routing.js';
import type { ComponentInstance, ManifestData } from '../types/astro.js';
@ -41,13 +42,11 @@ function isLoggedRequest(url: string) {
}
function getCustom404Route(manifestData: ManifestData): RouteData | undefined {
const route404 = /^\/404\/?$/;
return manifestData.routes.find((r) => route404.test(r.route));
return manifestData.routes.find((r) => isRoute404(r.route));
}
function getCustom500Route(manifestData: ManifestData): RouteData | undefined {
const route500 = /^\/500\/?$/;
return manifestData.routes.find((r) => route500.test(r.route));
return manifestData.routes.find((r) => isRoute500(r.route));
}
export async function matchRoute(