前端服务共享
This commit is contained in:
@@ -1,108 +1,111 @@
|
||||
import { defineConfig } from 'vite'
|
||||
import vue from '@vitejs/plugin-vue'
|
||||
import vueJsx from '@vitejs/plugin-vue-jsx'
|
||||
import { federation } from '@module-federation/vite'
|
||||
import { resolve, dirname } from 'path'
|
||||
import { fileURLToPath } from 'url'
|
||||
|
||||
// ES 模块中获取 __dirname
|
||||
const __filename = fileURLToPath(import.meta.url)
|
||||
const __dirname = dirname(__filename)
|
||||
|
||||
/**
|
||||
* ES Module 构建配置
|
||||
* 用于 Import Maps 方案
|
||||
* Module Federation 构建配置(@module-federation/vite)
|
||||
* 官方维护版本,支持 Vite 6 + 开发模式热更新
|
||||
*
|
||||
* 策略:将 Vue、Element Plus 等依赖打包进共享模块
|
||||
* 业务应用只需引入 @shared/*,无需关心底层依赖
|
||||
* 优势:
|
||||
* - ✅ 完整支持 Vite 开发模式
|
||||
* - ✅ dev 模式能生成 remoteEntry.js
|
||||
* - ✅ 自动处理内部路径别名 (@/)
|
||||
* - ✅ 真正的生产可用版本
|
||||
*/
|
||||
export default defineConfig({
|
||||
plugins: [vue(), vueJsx()],
|
||||
define: {
|
||||
__VUE_PROD_DEVTOOLS__: true,
|
||||
// __VUE_OPTIONS_API__: true, // 确保启用 Options API
|
||||
// __VUE_PROD_HYDRATION_MISMATCH_DETAILS__: true
|
||||
},
|
||||
resolve: {
|
||||
alias: [
|
||||
{ find: '@', replacement: resolve(__dirname, 'src') }
|
||||
plugins: [
|
||||
vue({
|
||||
script: {
|
||||
defineModel: true,
|
||||
propsDestructure: true
|
||||
}
|
||||
}),
|
||||
vueJsx(),
|
||||
federation({
|
||||
name: 'shared',
|
||||
filename: 'remoteEntry.js',
|
||||
// 暴露的模块
|
||||
exposes: {
|
||||
// 通用组件
|
||||
'./FileUpload': './src/components/fileupload/FileUpload.vue',
|
||||
'./DynamicFormItem': './src/components/dynamicFormItem/DynamicFormItem.vue',
|
||||
|
||||
// API 模块
|
||||
'./api': './src/api/index.ts',
|
||||
'./authAPI': './src/api/auth/auth.ts',
|
||||
'./fileAPI': './src/api/file/file.ts',
|
||||
|
||||
// Utils 模块
|
||||
'./utils': './src/utils/index.ts',
|
||||
|
||||
// Types 模块
|
||||
'./types': './src/types/index.ts',
|
||||
|
||||
// 整体导出
|
||||
'./components': './src/components/index.ts'
|
||||
},
|
||||
// 共享依赖(重要:避免重复加载)
|
||||
shared: {
|
||||
vue: {},
|
||||
'vue-router': {},
|
||||
'element-plus': {},
|
||||
'@element-plus/icons-vue': {},
|
||||
axios: {}
|
||||
}
|
||||
})
|
||||
],
|
||||
extensions: ['.mjs', '.js', '.ts', '.jsx', '.tsx', '.json', '.vue']
|
||||
},
|
||||
|
||||
build: {
|
||||
lib: {
|
||||
entry: {
|
||||
components: resolve(__dirname, 'src/components/index.ts'),
|
||||
utils: resolve(__dirname, 'src/utils/index.ts'),
|
||||
api: resolve(__dirname, 'src/api/index.ts'),
|
||||
composables: resolve(__dirname, 'src/composables/index.ts'),
|
||||
types: resolve(__dirname, 'src/types/index.ts')
|
||||
},
|
||||
formats: ['es'], // 仅构建 ES Module
|
||||
fileName: (format, entryName) => `${entryName}.js`
|
||||
|
||||
define: {
|
||||
__VUE_OPTIONS_API__: true,
|
||||
__VUE_PROD_DEVTOOLS__: true,
|
||||
__VUE_PROD_HYDRATION_MISMATCH_DETAILS__: true
|
||||
},
|
||||
|
||||
rollupOptions: {
|
||||
// ⚠️ 不外部化依赖,将它们打包进共享模块
|
||||
// 这样业务应用只需引入 @shared/* 即可
|
||||
external: [],
|
||||
|
||||
output: {
|
||||
// 保持 ES Module 格式
|
||||
format: 'es',
|
||||
// 导出命名导出
|
||||
exports: 'named',
|
||||
// 生成 sourcemap
|
||||
resolve: {
|
||||
alias: {
|
||||
'@': resolve(__dirname, 'src')
|
||||
},
|
||||
extensions: ['.mjs', '.js', '.ts', '.jsx', '.tsx', '.json', '.vue']
|
||||
},
|
||||
|
||||
build: {
|
||||
target: 'esnext',
|
||||
minify: false,
|
||||
cssCodeSplit: false,
|
||||
sourcemap: true,
|
||||
// 分块策略:将大的依赖分离出来
|
||||
manualChunks(id) {
|
||||
// Vue 核心
|
||||
if (id.includes('node_modules/vue/') ||
|
||||
id.includes('node_modules/@vue/')) {
|
||||
return 'vue-core'
|
||||
}
|
||||
// Vue Router
|
||||
if (id.includes('node_modules/vue-router/')) {
|
||||
return 'vue-router'
|
||||
}
|
||||
// Pinia
|
||||
if (id.includes('node_modules/pinia/')) {
|
||||
return 'pinia'
|
||||
}
|
||||
// Element Plus
|
||||
if (id.includes('node_modules/element-plus/')) {
|
||||
return 'element-plus'
|
||||
}
|
||||
// VueUse
|
||||
if (id.includes('node_modules/@vueuse/')) {
|
||||
return 'vueuse'
|
||||
}
|
||||
rollupOptions: {
|
||||
output: {
|
||||
format: 'es'
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
// 输出目录
|
||||
outDir: 'dist/esm',
|
||||
emptyOutDir: true,
|
||||
server: {
|
||||
port: 5000,
|
||||
strictPort: true,
|
||||
host: true,
|
||||
cors: true,
|
||||
headers: {
|
||||
'Access-Control-Allow-Origin': '*',
|
||||
'Access-Control-Allow-Methods': 'GET, POST, PUT, DELETE, OPTIONS',
|
||||
'Access-Control-Allow-Headers': 'Content-Type, Authorization'
|
||||
}
|
||||
},
|
||||
|
||||
// 目标浏览器
|
||||
target: 'esnext',
|
||||
|
||||
// 不压缩(开发环境)
|
||||
minify: false,
|
||||
|
||||
// 启用代码分割
|
||||
cssCodeSplit: true
|
||||
},
|
||||
// 开发服务器配置
|
||||
server: {
|
||||
port: 5000,
|
||||
host: true,
|
||||
cors: true,
|
||||
headers: {
|
||||
'Access-Control-Allow-Origin': '*',
|
||||
'Access-Control-Allow-Methods': 'GET, OPTIONS',
|
||||
// 'Content-Type': 'application/javascript; charset=utf-8'
|
||||
preview: {
|
||||
port: 5000,
|
||||
host: true,
|
||||
cors: true,
|
||||
headers: {
|
||||
'Access-Control-Allow-Origin': '*',
|
||||
'Access-Control-Allow-Methods': 'GET, POST, PUT, DELETE, OPTIONS',
|
||||
'Access-Control-Allow-Headers': 'Content-Type, Authorization'
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user