一、8080端口是好的,但是http://localhost:8080/ 打开报错
Failed to load module script: Expected a JavaScript module script but the server responded with a MIME type of "text/plain". Strict MIME type checking is enforced for module scripts per HTML spec.
浏览器在加载你的静态资源(比如app.js或者main.js)时,期望它是JavaScript module,但Nginx返回的Content-Type是text/plain,所以浏览器拒绝加载。
🎯 主要原因分析
MIME类型配置不对
说明你的Nginx或者其他服务器,没有正确配置MIME类型,导致.js文件被识别成了text/plain,而不是application/javascript。构建产物的问题
检查一下:
你的dist目录里是不是构建出了xxx.js文件
这些文件是不是Vite的ES Module,如果build配置有问题,可能导致产物异常。
我判断主要是还是第一个原因:MIME类型配置不对
🔧 重点解决思路
【核心】Nginx要配置好MIME类型(强烈推荐检查)
1️⃣ 确认Nginx里有没有这个:
nginx.conf:
types {
application/javascript js;
text/css css;
text/html html;
}
有些精简版nginx镜像,/etc/nginx/mime.types没加载,需要手动补上上面这些。
2️⃣ 如果nginx.conf里有include mime.types,就去看看mime.types里是否缺失:
mime.types(标准内容):
types {
application/javascript js;
text/css css;
text/html html;
}
【可选】Vite构建检查
你的vite.config.ts里,build部分看看:
build: {
rollupOptions: {
output: {
entryFileNames: 'assets/[name].[hash].js',
chunkFileNames: 'assets/[name].[hash].js',
assetFileNames: 'assets/[name].[hash][extname]'
}
}
}
检查你产物是否都正确放到了dist/assets,有没有可能是构建没跑完就进镜像了。
【可选】手动curl看下Content-Type
curl -I http://47.103.71.185:8080/assets/index.abc123.js
如果返回:
Content-Type: text/plain
说明Nginx的MIME类型确实有问题。
如果是:
Content-Type: application/javascript
那就可能是构建产物的问题了。
【总结处理步骤】
1、确认nginx.conf里types配置完整;
2、确认你的Vite构建产物结构正常;
3、curl检查线上返回的Content-Type;
如果Nginx配置改了,一定要:
docker-compose down
docker-compose build
docker-compose up -d
nginx.conf:
worker_processes 1;
events {
worker_connections 1024;
}
http {
include mime.types; # 这一行非常关键!!
default_type application/octet-stream; # 防止未知类型变成text/plain
server {
listen 80;
root /usr/share/nginx/html;
index index.html;
location / {
try_files $uri /index.html;
}
location ~* \.(?:ico|css|js|gif|jpe?g|png|woff2?|eot|ttf|svg|otf|map)$ {
expires 6M;
access_log off;
}
}
}
build.sh 推荐模板:
#!/bin/bash
set -e # 有错误就退出
echo ">>> 安装依赖"
yarn install --frozen-lockfile
echo ">>> 构建生产包"
yarn run build:prod
echo ">>> 停止并清理旧容器"
docker-compose down
echo ">>> 构建镜像"
docker-compose build
echo ">>> 启动新容器"
docker-compose up -d
echo ">>> 部署完成!"
Dockerfile推荐写法(适合vite项目):
# 构建阶段
FROM node:18 as builder
WORKDIR /app
COPY . .
RUN yarn install --frozen-lockfile
RUN yarn run build:prod
# 部署阶段
FROM nginx:alpine
COPY nginx.conf /etc/nginx/nginx.conf
COPY --from=builder /app/dist /usr/share/nginx/html
EXPOSE 80
mime.types内容(放到同目录下):
types {
text/html html htm shtml;
text/css css;
text/xml xml;
image/gif gif;
image/jpeg jpeg jpg;
application/javascript js;
application/atom+xml atom;
application/rss+xml rss;
text/mathml mml;
text/plain txt;
text/vnd.sun.j2me.app-descriptor jad;
text/vnd.wap.wml wml;
text/x-component htc;
image/png png;
image/svg+xml svg svgz;
image/tiff tif tiff;
image/vnd.wap.wbmp wbmp;
image/webp webp;
image/x-icon ico;
image/x-jng jng;
image/x-ms-bmp bmp;
font/woff woff;
font/woff2 woff2;
application/java-archive jar war ear;
application/json json;
application/mac-binhex40 hqx;
application/msword doc;
application/pdf pdf;
application/postscript ps eps ai;
application/rtf rtf;
application/vnd.apple.mpegurl m3u8;
application/vnd.ms-excel xls;
application/vnd.ms-powerpoint ppt;
application/vnd.wap.wmlc wmlc;
application/x-cocoa cco;
application/x-java-archive-diff jardiff;
application/x-java-jnlp-file jnlp;
application/x-makeself run;
application/x-perl pl pm;
application/x-pilot prc pdb;
application/x-rar-compressed rar;
application/x-redhat-package-manager rpm;
application/x-sea sea;
application/x-shockwave-flash swf;
application/x-stuffit sit;
application/x-tcl tcl tk;
application/x-x509-ca-cert der pem crt;
application/x-xpinstall xpi;
application/xhtml+xml xhtml;
application/xspf+xml xspf;
application/zip zip;
application/octet-stream bin exe dll;
application/octet-stream deb;
application/octet-stream dmg;
application/octet-stream iso img;
application/octet-stream msi msp msm;
application/vnd.openxmlformats-officedocument.wordprocessingml.document docx;
application/vnd.openxmlformats-officedocument.spreadsheetml.sheet xlsx;
application/vnd.openxmlformats-officedocument.presentationml.presentation pptx;
audio/midi mid midi kar;
audio/mpeg mp3;
audio/ogg ogg;
audio/x-m4a m4a;
audio/x-realaudio ra;
video/3gpp 3gpp 3gp;
video/mp2t ts;
video/mp4 mp4;
video/mpeg mpeg mpg;
video/quicktime mov;
video/webm webm;
video/x-flv flv;
video/x-m4v m4v;
video/x-mng mng;
video/x-ms-asf asx asf;
video/x-ms-wmv wmv;
video/x-msvideo avi;
}
二、部署项目的时候,执行docker构建后,前端内容是空的,没产生dist,本地npm run build能生成dist,但在Docker构建时反而没有dist
# 第一阶段:构建前端
FROM node:18 AS builder
WORKDIR /app
# 加速国内网络
RUN npm config set registry https://registry.npmmirror.com
# 安装依赖
COPY package*.json ./
RUN npm install --frozen-lockfile
# 复制源码并构建
COPY . .
RUN npm run build
# 第二阶段:Nginx托管
FROM nginx:alpine
# 设置前端产物输出目录,方便后续灵活调整
ARG OUTPUT_DIR=dist
ENV OUTPUT_DIR=$OUTPUT_DIR
# 覆盖nginx配置
COPY nginx /etc/nginx
# 拷贝前端打包产物
COPY --from=builder /app/$OUTPUT_DIR /usr/share/nginx/html
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
# 1. 基于node16
FROM node:16 AS builder
WORKDIR /app
# 2. 先copy package.json和lock,装依赖
COPY package*.json ./
RUN npm install
# 3. 再copy代码
COPY . .
# 4. 运行build,并打印整个/app的内容
RUN npm run build && ls -al /app && ls -al /app/dist
# 5. 用nginx托管
FROM nginx:alpine
COPY nginx.conf /etc/nginx/nginx.conf
COPY --from=builder /app/dist /usr/share/nginx/html
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
当我运行build,并打印整个/app的内容
RUN npm run build && ls -al /app && ls -al /app/dist
这一步导致服务器断开了,会不会是因为打印很占内存?
📌 为什么断开?
ls -al /app 会把node_modules里的东西全打出来,几万文件的输出,非常恐怖。
如果你是远程连的服务器(比如SSH),这种巨量输出会让终端连接异常(SSH通道炸掉)。
如果服务器内存不高、CPU负担重,docker构建容器本身可能直接被系统kill(Out Of Memory,简称OOM)。
后续继续更新