From cf202577ab00e4eab49252b884b79d06a6d26551 Mon Sep 17 00:00:00 2001 From: Jiachi Liu Date: Wed, 18 Sep 2024 15:25:26 +0200 Subject: [PATCH] Replace URL.canParse (#70215) --- .../internal/helpers/get-socket-url.ts | 3 ++- packages/next/src/lib/url.ts | 12 ++++++++++++ packages/next/src/server/lib/router-server.ts | 3 ++- .../next/src/shared/lib/normalized-asset-prefix.ts | 4 +++- 4 files changed, 19 insertions(+), 3 deletions(-) diff --git a/packages/next/src/client/components/react-dev-overlay/internal/helpers/get-socket-url.ts b/packages/next/src/client/components/react-dev-overlay/internal/helpers/get-socket-url.ts index 3a3b87ac28a5b..a2e51cb138689 100644 --- a/packages/next/src/client/components/react-dev-overlay/internal/helpers/get-socket-url.ts +++ b/packages/next/src/client/components/react-dev-overlay/internal/helpers/get-socket-url.ts @@ -1,3 +1,4 @@ +import { canParseUrl } from '../../../../../lib/url' import { normalizedAssetPrefix } from '../../../../../shared/lib/normalized-asset-prefix' function getSocketProtocol(assetPrefix: string): string { @@ -15,7 +16,7 @@ export function getSocketUrl(assetPrefix: string | undefined): string { const prefix = normalizedAssetPrefix(assetPrefix) const protocol = getSocketProtocol(assetPrefix || '') - if (URL.canParse(prefix)) { + if (canParseUrl(prefix)) { // since normalized asset prefix is ensured to be a URL format, // we can safely replace the protocol return prefix.replace(/^http/, 'ws') diff --git a/packages/next/src/lib/url.ts b/packages/next/src/lib/url.ts index cc0b37d23c365..2d301e03c6f9a 100644 --- a/packages/next/src/lib/url.ts +++ b/packages/next/src/lib/url.ts @@ -20,3 +20,15 @@ export function stripNextRscUnionQuery(relativeUrl: string): string { return urlInstance.pathname + urlInstance.search } + +export function canParseUrl(url: string): boolean { + if (typeof URL.canParse === 'function') { + return URL.canParse(url) + } + try { + new URL(url) + return true + } catch {} + + return false +} diff --git a/packages/next/src/server/lib/router-server.ts b/packages/next/src/server/lib/router-server.ts index 999a4d0805dd2..bea8e56d13e40 100644 --- a/packages/next/src/server/lib/router-server.ts +++ b/packages/next/src/server/lib/router-server.ts @@ -47,6 +47,7 @@ import { } from '../dev/hot-reloader-types' import { normalizedAssetPrefix } from '../../shared/lib/normalized-asset-prefix' import { NEXT_PATCH_SYMBOL } from './patch-fetch' +import { canParseUrl } from '../../lib/url' const debug = setupDebug('next:router-server:main') const isNextFont = (pathname: string | null) => @@ -676,7 +677,7 @@ export async function initialize(opts: { if (assetPrefix) { hmrPrefix = normalizedAssetPrefix(assetPrefix) - if (URL.canParse(hmrPrefix)) { + if (canParseUrl(hmrPrefix)) { // remove trailing slash from pathname // return empty string if pathname is '/' // to avoid conflicts with '/_next' below diff --git a/packages/next/src/shared/lib/normalized-asset-prefix.ts b/packages/next/src/shared/lib/normalized-asset-prefix.ts index 352e836698c5c..34b7dbca6b44f 100644 --- a/packages/next/src/shared/lib/normalized-asset-prefix.ts +++ b/packages/next/src/shared/lib/normalized-asset-prefix.ts @@ -1,3 +1,5 @@ +import { canParseUrl } from '../../lib/url' + export function normalizedAssetPrefix(assetPrefix: string | undefined): string { // remove all leading slashes and trailing slashes const escapedAssetPrefix = assetPrefix?.replace(/^\/+|\/+$/g, '') || false @@ -8,7 +10,7 @@ export function normalizedAssetPrefix(assetPrefix: string | undefined): string { return '' } - if (URL.canParse(escapedAssetPrefix)) { + if (canParseUrl(escapedAssetPrefix)) { const url = new URL(escapedAssetPrefix).toString() return url.endsWith('/') ? url.slice(0, -1) : url }