基于Vite与Module Federation的微前端部署MIME类型问题
Module Federation动态导入远程组件出现MIME类型错误
错误信息
Failed to load module script: Expected a JavaScript module script but the server responded with a MIME type of "text/html". Strict MIME type checking is enforced for module scripts per HTML spec. _federation_expose_Page.0d00fb5f.js:1
环境配置
主机应用vite.config.js
import { defineConfig } from "vite"; import { resolve } from "path"; import react from "@vitejs/plugin-react"; import federation from "@originjs/vite-plugin-federation"; export default defineConfig({ base: "/", plugins: [ react(), federation({ name: "app", remotes: { billing: "https://billing-microfrontend.delever.uz/assets/remoteEntry.js?v=1.2.2", singleOrder: "https://order-microfrontend.delever.uz/assets/remoteEntry.js?v=1.3.5", }, shared: ["react", "react-dom", "@tanstack/react-query"], }), ], publicDir: "public", build: { outDir: "build", modulePreload: false, target: "esnext", minify: false, cssCodeSplit: false, rollupOptions: { onwarn(warning, warn) { if (warning.code === "MODULE_LEVEL_DIRECTIVE") { return; } warn(warning); }, }, }, // Additional server configurations server: { port: 7777, cors: { origin: "*", methods: ["GET", "POST", "PUT", "DELETE", "PATCH", "OPTIONS"], allowedHeaders: ["X-Requested-With", "content-type", "Authorization"], }, }, // sass configuration css: { preprocessorOptions: { scss: { api: "modern", }, }, }, resolve: { alias: [ { find: "@", replacement: resolve(__dirname, "src"), }, ], }, });
主机应用Nginx配置
user nginx; worker_processes 1; error_log /var/log/nginx/error.log warn; pid /var/run/nginx.pid; events { worker_connections 1024; } http { include /etc/nginx/mime.types; default_type application/octet-stream; log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; access_log /var/log/nginx/access.log main; sendfile on; keepalive_timeout 65; gzip on; gzip_types text/plain application/xml application/json application/javascript text/css image/svg+xml font/woff2; gzip_proxied no-cache no-store private expired auth; gzip_min_length 1000; gzip_vary on; server { listen 80; server_name localhost; root /build; # Ensure this is the correct path to your build folder location / { try_files $uri $uri/ /index.html; # Catch-all for client-side routing } location /assets/remoteEntry.js { add_header Content-Type application/javascript; # Correct MIME type try_files $uri =404; # Serve 404 if the file doesn't exist } # Serve static files with caching location ~* \.(?:js|css|woff2?|ttf|svg|png|jpg|jpeg|gif|ico|html)$ { try_files $uri =404; expires 6M; # Cache static files for 6 months access_log off; } error_page 500 502 503 504 /50x.html; location = /50x.html { root /usr/share/nginx/html; } } }
远程组件(singleOrder)Nginx配置
user nginx; worker_processes 1; error_log /var/log/nginx/error.log warn; pid /var/run/nginx.pid; events { worker_connections 1024; } http { include /etc/nginx/mime.types; default_type application/octet-stream; log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; access_log /var/log/nginx/access.log main; sendfile on; keepalive_timeout 65; server { gzip on; gzip_types text/plain application/xml; gzip_proxied no-cache no-store private expired auth; gzip_min_length 1000; listen 3000; server_name localhost; location / { root /build; index index.html; try_files $uri $uri/ /index.html; } location /assets/remoteEntry.js { root /build; } error_page 500 502 503 504 /50x.html; location = /50x.html { root /usr/share/nginx/html; } } }
已知背景
此前通过禁用service workers和更新主机应用Nginx配置解决过同类问题;当前billing远程组件运行正常,但singleOrder组件出现上述MIME错误,二者路径与MIME配置逻辑一致。
问题排查与解决方案
1. 缓存问题(优先级最高)
- 浏览器缓存:强制刷新页面(
Ctrl+Shift+R),或在开发者工具中禁用缓存后重新加载,检查是否仍报错。 - CDN/反向代理缓存:如果singleOrder组件部署在CDN后,需清除对应CDN节点的缓存,尤其是
_federation_expose_Page.0d00fb5f.js这类动态生成的文件。 - Nginx缓存:检查远程服务器是否开启了Nginx缓存,若有则临时关闭或清除缓存目录。
2. 远程组件Nginx配置缺陷
对比主机应用的Nginx配置,singleOrder的Nginx存在以下问题:
- 缺少JS文件的MIME类型处理:主机应用中针对
/assets/remoteEntry.js单独设置了Content-Type: application/javascript,且有覆盖所有静态文件的location ~* \.(?:js|...)规则;但singleOrder的Nginx仅对/assets/remoteEntry.js设置了root,未指定MIME类型,且全局的gzip_types未包含application/javascript,可能导致JS文件被错误识别为text/html。 - 修复建议:
- 在singleOrder的Nginx配置中,给
/assets/remoteEntry.js添加MIME类型头:location /assets/remoteEntry.js { root /build; add_header Content-Type application/javascript; try_files $uri =404; } - 更新全局
gzip_types,包含JS类型:gzip_types text/plain application/xml application/json application/javascript text/css image/svg+xml font/woff2; - 确保静态文件规则覆盖所有JS文件,添加类似主机应用的静态文件location规则:
location ~* \.(?:js|css|woff2?|ttf|svg|png|jpg|jpeg|gif|ico|html)$ { try_files $uri =404; expires 6M; access_log off; }
- 在singleOrder的Nginx配置中,给
3. Vite构建配置差异
检查singleOrder远程组件的Vite构建配置:
- 确认
build.target设置为esnext,避免生成非模块格式的JS文件。 - 检查
federation配置中的exposes是否正确,确保导出的组件路径无误,避免构建后生成的文件路径错误导致404(进而被Nginx重定向到index.html,返回text/html)。 - 确认
build.outDir为build,且部署到Nginx的root /build路径下的文件完整,没有缺失_federation_expose_Page.0d00fb5f.js这类文件。
4. 网络请求验证
在浏览器开发者工具的Network面板中,查看_federation_expose_Page.0d00fb5f.js的请求:
- 检查响应状态码:若为200,查看Response Headers中的
Content-Type是否为application/javascript;若为404,说明文件不存在,Nginx返回了index.html(text/html)。 - 检查请求URL是否正确:确认远程组件的资源路径是否与部署路径匹配,比如是否存在路径前缀错误。
内容的提问来源于stack exchange,提问作者Fazliddin
相关产品推荐
相关产品推荐

