Files
wordloop/frontend/vite.config.ts
T
john db5465c646 Fix iOS WebKit crash by shipping external app.js instead of inlined HTML.
Stop embedding the 1.4MB bundle in index.html to avoid std::overflow_error on launch, validate the iOS asset build, and surface load failures in the native shell.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-06-06 21:53:26 +08:00

79 lines
2.3 KiB
TypeScript

import { defineConfig, type Plugin } from 'vite'
import vue from '@vitejs/plugin-vue'
/** WKWebView 用 file:// 加载时,crossorigin 会导致脚本无法执行、页面空白 */
function stripCrossOriginForIOS(): Plugin {
return {
name: 'strip-crossorigin-ios',
apply: 'build',
enforce: 'post',
transformIndexHtml(html) {
return html.replace(/\s+crossorigin(="[^"]*")?/g, '')
},
}
}
/** iOS 内嵌启动配置:在模块脚本之前注入,避免 file:// 下懒加载 chunk 失败 */
function injectIOSRuntimeBootstrap(): Plugin {
return {
name: 'inject-ios-runtime-bootstrap',
apply: 'build',
transformIndexHtml(html) {
const bootstrap = `<script>
window.__WORDLOOP_RUNTIME__ = {
embedded: true,
iosApp: true,
apiBase: 'https://w.tkmind.cn/api'
};
(function () {
if (!location.hash || location.hash === '#') {
var base = location.href.split('#')[0];
location.replace(base + '#/');
}
})();
</script>`
if (html.includes('__WORDLOOP_RUNTIME__')) return html
const withoutModule = html
.replace(/\s+crossorigin(="[^"]*")?/g, '')
.replace('<script type="module"', '<script')
const withBootstrap = withoutModule.replace('<script src=', `${bootstrap}\n <script src=`)
const scriptTag = withBootstrap.match(/<script src="\.\/assets\/[^"]+"><\/script>/)
if (!scriptTag) return withBootstrap
const withoutHeadScript = withBootstrap.replace(scriptTag[0], '')
return withoutHeadScript.replace('</body>', ` ${scriptTag[0]}\n </body>`)
},
}
}
export default defineConfig(({ mode }) => ({
base: mode === 'ios' ? './' : '/',
plugins: [
vue(),
...(mode === 'ios' ? [stripCrossOriginForIOS(), injectIOSRuntimeBootstrap()] : []),
],
build: mode === 'ios'
? {
modulePreload: false,
cssCodeSplit: false,
rollupOptions: {
output: {
// WKWebView file:// 下 type=module 常无法执行,改为 IIFE 普通脚本
format: 'iife',
inlineDynamicImports: true,
entryFileNames: 'assets/app.js',
assetFileNames: 'assets/app.[ext]',
},
},
}
: undefined,
server: {
port: 18003,
proxy: {
'/api': {
target: 'http://localhost:18004',
changeOrigin: true,
},
},
},
}))