From fc8d4f87f54136c38c8eca32646399bbb9982305 Mon Sep 17 00:00:00 2001 From: liximomo Date: Thu, 9 Feb 2023 10:51:21 +0800 Subject: [PATCH] fix: hmr not working with custom publicPath that has a different protocol --- .../src/shared/helper/getAppData.ts | 4 +-- .../src/shared/loader/loader.ts | 2 +- .../src/shuvi-app/dev/hotDevClient.ts | 2 +- .../platform-web/src/shuvi-app/dev/index.ts | 3 +- .../src/shuvi-app/dev/websocket.ts | 30 +++++++++++++------ test/e2e/css.test.ts | 6 ++-- 6 files changed, 30 insertions(+), 17 deletions(-) diff --git a/packages/platform-shared/src/shared/helper/getAppData.ts b/packages/platform-shared/src/shared/helper/getAppData.ts index f5b43381b..2d08e20a1 100644 --- a/packages/platform-shared/src/shared/helper/getAppData.ts +++ b/packages/platform-shared/src/shared/helper/getAppData.ts @@ -29,7 +29,7 @@ export function getAppData(): IAppData { return { ssr: false, filesByRoutId: {}, - publicPath: '' + publicPath: '/' }; } @@ -39,7 +39,7 @@ export function getAppData(): IAppData { ssr: false, pageData: {}, filesByRoutId: {}, - publicPath: '' + publicPath: '/' }; } diff --git a/packages/platform-shared/src/shared/loader/loader.ts b/packages/platform-shared/src/shared/loader/loader.ts index 271b855ec..6beca2762 100644 --- a/packages/platform-shared/src/shared/loader/loader.ts +++ b/packages/platform-shared/src/shared/loader/loader.ts @@ -73,7 +73,7 @@ function redirectHelper(to: string, status: number = 302) { if (process.env.NODE_ENV === 'development') { invariant( typeof to === 'string', - `redirect fist argument should be string, now is ${typeof to}` + `redirect's frist argument should be string, now is ${typeof to}` ); } diff --git a/packages/platform-web/src/shuvi-app/dev/hotDevClient.ts b/packages/platform-web/src/shuvi-app/dev/hotDevClient.ts index b53a019cf..40f0159b0 100644 --- a/packages/platform-web/src/shuvi-app/dev/hotDevClient.ts +++ b/packages/platform-web/src/shuvi-app/dev/hotDevClient.ts @@ -62,7 +62,7 @@ export type HotDevClient = { export default function connect(options: { launchEditorEndpoint: string; path: string; - location: Location; + assetPublicPath: string; }): HotDevClient { startReportingRuntimeErrors({ onError: function () { diff --git a/packages/platform-web/src/shuvi-app/dev/index.ts b/packages/platform-web/src/shuvi-app/dev/index.ts index da4e4800b..acd027426 100644 --- a/packages/platform-web/src/shuvi-app/dev/index.ts +++ b/packages/platform-web/src/shuvi-app/dev/index.ts @@ -3,6 +3,7 @@ import { DEV_HOT_MIDDLEWARE_PATH, DEV_HOT_LAUNCH_EDITOR_ENDPOINT } from '@shuvi/shared/constants'; +import { getPublicPath } from '@shuvi/platform-shared/shared/helper/getPublicPath'; import { InternalApplication } from '../../shared'; import connect, { HotDevClient } from './hotDevClient'; @@ -21,7 +22,7 @@ export const initHMRAndDevClient = (app: InternalApplication) => { devClient = connect({ launchEditorEndpoint: DEV_HOT_LAUNCH_EDITOR_ENDPOINT, path: DEV_HOT_MIDDLEWARE_PATH, - location + assetPublicPath: getPublicPath() }); setInterval(() => { diff --git a/packages/platform-web/src/shuvi-app/dev/websocket.ts b/packages/platform-web/src/shuvi-app/dev/websocket.ts index 66f0ff2fd..61cc15721 100644 --- a/packages/platform-web/src/shuvi-app/dev/websocket.ts +++ b/packages/platform-web/src/shuvi-app/dev/websocket.ts @@ -3,7 +3,14 @@ const eventCallbacks: ((event: any) => void)[] = []; let lastActivity = Date.now(); let initDataBeforeWsOnline: any[] = []; -function getSocketProtocol(protocol: string): string { +function getSocketProtocol(assetPublicPath: string): string { + let protocol = window.location.protocol; + + try { + // assetPublicPath is a url + protocol = new URL(assetPublicPath).protocol; + } catch (_) {} + return protocol === 'http:' ? 'ws' : 'wss'; } @@ -28,11 +35,7 @@ export function connectHMR(options: { path: string; timeout: number; log?: boolean; - location: { - protocol: string; - hostname: string; - port?: string; - }; + assetPublicPath: string; }) { if (!options.timeout) { options.timeout = 5000; @@ -48,9 +51,18 @@ export function connectHMR(options: { function init() { if (source) source.close(); - let { protocol, hostname, port } = options.location; - protocol = getSocketProtocol(protocol); - let url = `${protocol}://${hostname}:${port}`; + + const { hostname, port } = window.location; + const protocol = getSocketProtocol(options.assetPublicPath); + const assetPublicPath = options.assetPublicPath.replace(/^\/+/, ''); + + let url = `${protocol}://${hostname}:${port}${ + assetPublicPath ? `/${assetPublicPath}` : '' + }`; + + if (assetPublicPath.startsWith('http')) { + url = `${protocol}://${assetPublicPath.split('://')[1]}`; + } source = new WebSocket(`${url}${options.path}`); source.onopen = handleOnline; diff --git a/test/e2e/css.test.ts b/test/e2e/css.test.ts index cbff8560e..bcb0447fc 100644 --- a/test/e2e/css.test.ts +++ b/test/e2e/css.test.ts @@ -1,12 +1,12 @@ import { DEV_STYLE_HIDE_FOUC } from '@shuvi/shared/constants'; import { AppCtx, Page, devFixture } from '../utils'; -let ctx: AppCtx; -let page: Page; - jest.setTimeout(5 * 60 * 1000); ['CSS', 'LightningCss'].forEach(function (describeName) { + let ctx: AppCtx; + let page: Page; + describe(describeName, () => { beforeAll(async () => { ctx = await devFixture(