Node.js应用部署到Docker Swarm后无法正常访问问题求助
问题原因及排查解决方法
核心原因汇总
- 缺失package.json或未配置正确的
npm start启动脚本,导致容器启动失败反复重启 - Node服务未显式监听
0.0.0.0,默认绑定的地址无法接收容器外部请求 - Dockerfile中用户切换和文件复制的顺序错误,导致node用户无权限读取项目文件,服务启动报错
- Swarm集群使用IPv6地址作为广播地址,端口仅绑定IPv6栈,访问IPv4的localhost无响应
排查步骤
- 检查服务运行状态与日志
- 执行
sudo docker service ps node01查看任务是否存在反复重启、异常退出的记录 - 执行
sudo docker service logs node01查看服务运行日志,确认是否有脚本缺失、权限报错、启动失败等提示
- 执行
- 确认项目根目录存在package.json文件,且配置了正确的启动脚本,示例配置如下:
{ "name": "node-demo", "version": "1.0.0", "scripts": { "start": "node index.js" } }
注:需保证你的Node服务代码文件名为index.js,若为其他名称需对应修改脚本
3. 检查Node服务监听配置,原代码仅指定端口,未指定监听地址,需修改为显式监听0.0.0.0:
const http=require('http'); http.createServer((req,res)=>{ res.writeHead(200,{'Content-Type': 'text/html'}); res.end('<h1>Hello World</h1>') }).listen(3000, '0.0.0.0'); console.log('Service Started on port 3000')
- 修正Dockerfile的执行顺序,解决文件权限问题:
原Dockerfile先切换为node用户再复制文件,导致复制的文件属主为root,node用户无读取权限,修改后的Dockerfile如下:
FROM node RUN apt-get update -q && apt-get dist-upgrade -y && apt-get clean && apt-get autoclean EXPOSE 3000 ENV APP_PATH /usr/share/app WORKDIR $APP_PATH # 先复制文件 COPY . $APP_PATH # 修改文件属主为node用户 RUN chown -R node:node $APP_PATH # 再切换用户 USER node CMD ["npm","start"]
- 检查端口绑定情况
执行sudo ss -tulpn | grep 3000查看3000端口绑定的地址:
- 如果仅绑定IPv6的
:::3000,可尝试访问http://[::1]:3000验证服务可用性 - 若需要支持IPv4访问,可重新初始化Swarm时指定IPv4的广播地址,或者创建服务时添加
--publish mode=host,target=3000,published=3000参数绑定所有地址
修复后重新部署流程
- 停止删除现有服务:
sudo docker service rm node01 - 重新构建镜像:
sudo docker build -t prototype . - 重新创建服务:
sudo docker service create -d --name node01 -p 3000:3000 prototype
内容的提问来源于stack exchange,提问作者Santam
相关产品推荐
相关产品推荐

