From 1d6842fa69326aea980f16aab62af6df5c837234 Mon Sep 17 00:00:00 2001 From: leo Date: Thu, 28 May 2026 12:53:51 +0800 Subject: [PATCH] build: change runtime config asset naming strategy for PWA compatibility (#7963) replace query-based config url (_app.config.js?v=...) with deterministic hashed filename (_app-config-v{version}-{hash}.js) ensure service worker precache matches runtime injected asset --- docs/src/en/guide/essentials/server.md | 2 +- docs/src/en/guide/essentials/settings.md | 10 +++++----- docs/src/guide/essentials/server.md | 2 +- docs/src/guide/essentials/settings.md | 10 +++++----- internal/vite-config/src/plugins/extra-app-config.ts | 10 +++++----- 5 files changed, 17 insertions(+), 17 deletions(-) diff --git a/docs/src/en/guide/essentials/server.md b/docs/src/en/guide/essentials/server.md index c22b08f43..b17db80dd 100644 --- a/docs/src/en/guide/essentials/server.md +++ b/docs/src/en/guide/essentials/server.md @@ -98,7 +98,7 @@ VITE_GLOB_API_URL=https://mock-napi.vben.pro/api ::: tip How to Dynamically Modify API Endpoint in Production -Variables starting with `VITE_GLOB_*` in the `.env` file are injected into the `_app.config.js` file during packaging. After packaging, you can modify the corresponding API addresses in `dist/_app.config.js` and refresh the page to apply the changes. This eliminates the need to package multiple times for different environments, allowing a single package to be deployed across multiple API environments. +Variables starting with `VITE_GLOB_*` in the `.env` file are injected into the `_app-config-{version}-{hash}.js` file during packaging. After packaging, you can modify the corresponding API addresses in `dist/_app-config-{version}-{hash}.js` and refresh the page to apply the changes. This eliminates the need to package multiple times for different environments, allowing a single package to be deployed across multiple API environments. ::: diff --git a/docs/src/en/guide/essentials/settings.md b/docs/src/en/guide/essentials/settings.md index 69aedbde2..3bbc4383b 100644 --- a/docs/src/en/guide/essentials/settings.md +++ b/docs/src/en/guide/essentials/settings.md @@ -21,7 +21,7 @@ The rules are consistent with [Vite Env Variables and Modes](https://vitejs.dev/ console.log(import.meta.env.VITE_PROT); ``` -- Variables starting with `VITE_GLOB_*` will be added to the `_app.config.js` configuration file during packaging. +- Variables starting with `VITE_GLOB_*` will be added to the `_app-config-{version}-{hash}.js` configuration file during packaging. ::: @@ -87,9 +87,9 @@ VITE_ARCHIVER=true ## Dynamic Configuration in Production Environment -When executing `pnpm build` in the root directory of the monorepo, a `dist/_app.config.js` file will be automatically generated in the corresponding application and inserted into `index.html`. +When executing `pnpm build` in the root directory of the monorepo, a `dist/_app-config-{version}-{hash}.js` file will be automatically generated in the corresponding application and inserted into `index.html`. -`_app.config.js` is a dynamic configuration file that allows for modifications to the configuration dynamically based on different environments after the project has been built. The content is as follows: +`_app-config-{version}-{hash}.js` is a dynamic configuration file that allows for modifications to the configuration dynamically based on different environments after the project has been built. The content is as follows: ```ts window._VBEN_ADMIN_PRO_APP_CONF_ = { @@ -104,11 +104,11 @@ Object.defineProperty(window, '_VBEN_ADMIN_PRO_APP_CONF_', { ### Purpose -`_app.config.js` is used for projects that need to dynamically modify configurations after packaging, such as API endpoints. There's no need to repackage; you can simply modify the variables in `/dist/_app.config.js` after packaging, and refresh to update the variables in the code. A `js` file is used to ensure that the configuration file is loaded early in the order. +`_app-config-{version}-{hash}.js` is used for projects that need to dynamically modify configurations after packaging, such as API endpoints. There's no need to repackage; you can simply modify the variables in `/dist/_app-config-{version}-{hash}.js` after packaging, and refresh to update the variables in the code. A `js` file is used to ensure that the configuration file is loaded early in the order. ### Usage -To access the variables inside `_app.config.js`, you need to use the `useAppConfig` method provided by `@vben/hooks`. +To access the variables inside `_app-config-{version}-{hash}.js`, you need to use the `useAppConfig` method provided by `@vben/hooks`. ```ts const { apiURL } = useAppConfig(import.meta.env, import.meta.env.PROD); diff --git a/docs/src/guide/essentials/server.md b/docs/src/guide/essentials/server.md index 337248fc3..2ae16e763 100644 --- a/docs/src/guide/essentials/server.md +++ b/docs/src/guide/essentials/server.md @@ -98,7 +98,7 @@ VITE_GLOB_API_URL=https://mock-napi.vben.pro/api ::: tip 打包如何动态修改接口地址 -`.env` 文件内的 `VITE_GLOB_*` 开头的变量会在打包的时候注入 `_app.config.js` 文件内。在 `dist/_app.config.js` 修改相应的接口地址后刷新页面即可,不需要在根据不同环境打包多次,一次打包可以用于多个不同接口环境的部署。 +`.env` 文件内的 `VITE_GLOB_*` 开头的变量会在打包的时候注入 `_app-config-{version}-{hash}.js` 文件内。在 `dist/_app-config-{version}-{hash}.js` 修改相应的接口地址后刷新页面即可,不需要在根据不同环境打包多次,一次打包可以用于多个不同接口环境的部署。 ::: diff --git a/docs/src/guide/essentials/settings.md b/docs/src/guide/essentials/settings.md index 067a1cb95..32111d4f1 100644 --- a/docs/src/guide/essentials/settings.md +++ b/docs/src/guide/essentials/settings.md @@ -21,7 +21,7 @@ console.log(import.meta.env.VITE_PROT); ``` -- 以 `VITE_GLOB_*` 开头的的变量,在打包的时候,会被加入 `_app.config.js`配置文件当中. +- 以 `VITE_GLOB_*` 开头的的变量,在打包的时候,会被加入 `_app-config-{version}-{hash}.js`配置文件当中. ::: @@ -86,9 +86,9 @@ VITE_ARCHIVER=true ## 生产环境动态配置 -当在大仓根目录下,执行 `pnpm build`构建项目之后,会自动在对应的应用下生成 `dist/_app.config.js`文件并插入 `index.html`。 +当在大仓根目录下,执行 `pnpm build`构建项目之后,会自动在对应的应用下生成 `dist/_app-config-{version}-{hash}.js`文件并插入 `index.html`。 -`_app.config.js` 是一个动态配置文件,可以在项目构建之后,根据不同的环境动态修改配置。内容如下: +`_app-config-{version}-{hash}.js` 是一个动态配置文件,可以在项目构建之后,根据不同的环境动态修改配置。内容如下: ```ts window._VBEN_ADMIN_PRO_APP_CONF_ = { @@ -103,11 +103,11 @@ Object.defineProperty(window, '_VBEN_ADMIN_PRO_APP_CONF_', { ### 作用 -`_app.config.js` 用于项目在打包后,需要动态修改配置的需求,如接口地址。不用重新进行打包,可在打包后修改 /`dist/_app.config.js` 内的变量,刷新即可更新代码内的局部变量。这里使用`js`文件,是为了确保配置文件加载顺序保持在前面。 +`_app-config-{version}-{hash}.js` 用于项目在打包后,需要动态修改配置的需求,如接口地址。不用重新进行打包,可在打包后修改 /`dist/_app-config-{version}-{hash}.js` 内的变量,刷新即可更新代码内的局部变量。这里使用`js`文件,是为了确保配置文件加载顺序保持在前面。 ### 使用 -想要获取 `_app.config.js` 内的变量,需要使用`@vben/hooks`提供的 `useAppConfig`方法。 +想要获取 `_app-config-{version}-{hash}.js` 内的变量,需要使用`@vben/hooks`提供的 `useAppConfig`方法。 ```ts const { apiURL } = useAppConfig(import.meta.env, import.meta.env.PROD); diff --git a/internal/vite-config/src/plugins/extra-app-config.ts b/internal/vite-config/src/plugins/extra-app-config.ts index 813819bbd..903aa6fd6 100644 --- a/internal/vite-config/src/plugins/extra-app-config.ts +++ b/internal/vite-config/src/plugins/extra-app-config.ts @@ -13,7 +13,7 @@ interface PluginOptions { root: string; } -const GLOBAL_CONFIG_FILE_NAME = '_app.config.js'; +const GLOBAL_CONFIG_FILE_NAME = '_app-config'; const VBEN_ADMIN_PRO_APP_CONF = '_VBEN_ADMIN_PRO_APP_CONF_'; /** @@ -27,6 +27,7 @@ async function viteExtraAppConfigPlugin({ }: PluginOptions): Promise { let publicPath: string; let source: string; + let hash: string; if (!isBuild) { return; @@ -38,11 +39,12 @@ async function viteExtraAppConfigPlugin({ async configResolved(config) { publicPath = ensureTrailingSlash(config.base); source = await getConfigSource(); + hash = generatorContentHash(source, 8); }, async generateBundle() { try { this.emitFile({ - fileName: GLOBAL_CONFIG_FILE_NAME, + fileName: `${GLOBAL_CONFIG_FILE_NAME}-${version}-${hash}.js`, source, type: 'asset', }); @@ -58,9 +60,7 @@ async function viteExtraAppConfigPlugin({ }, name: 'vite:extra-app-config', async transformIndexHtml(html) { - const hash = `v=${version}-${generatorContentHash(source, 8)}`; - - const appConfigSrc = `${publicPath}${GLOBAL_CONFIG_FILE_NAME}?${hash}`; + const appConfigSrc = `${publicPath}${GLOBAL_CONFIG_FILE_NAME}-${version}-${hash}.js`; return { html,