You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Node Express.js应用本地正常,Docker中显示Cannot GET /问题排查

问题描述

本地运行正常的Express应用,Docker容器启动后访问http://localhost:3000/出现Cannot GET /错误

本地运行情况

通过node api/src/server.js在VS Code中启动Express服务器,代码如下:

const express = require('express')
const SignRequest = require('./SignRequest/lambda/index.js')
const VerifyResponse = require('./VerifyResponse/lambda/index.js')

const port = "3000";

const app = express();
app.set('port', port)
app.use(express.static('../../web/dist'))
app.post('/signrequest', SignRequest.handler)
app.post('/verifyresponse', VerifyResponse.handler)
 
app.listen(port, () => console.log(`Listening on port ${port}`))

本地访问http://localhost:3000/完全正常。

Docker配置

Dockerfile内容如下:

FROM node:16 AS development

ARG NODE_ENV=development
ENV NODE_ENV $NODE_ENV

WORKDIR /code/demo

COPY package.json /code/demo/package.json
COPY package-lock.json /code/demo/package-lock.json
RUN npm install

COPY . /code/demo

RUN update-ca-certificates
RUN export NODE_EXTRA_CA_CERTS=/usr/local/share/ca-certificates/swbc-certificate.crt

CMD [ "node", "api/src/server.js" ]

EXPOSE 3000

执行docker build --no-cache -t sdk-tester .构建镜像,再通过docker run -p 3000:3000 sdk-tester启动容器,容器启动无报错,但浏览器访问http://localhost:3000/返回Cannot GET /,已确认容器内已完整复制包括server.js和web/dist在内的所有文件。

问题原因与解决方案

核心问题:相对路径在Docker中解析错误

问题确实出在app.use(express.static('../../web/dist'))的相对路径上,本地和Docker环境的工作目录差异导致路径解析结果不同:

  • 本地运行时,工作目录是项目根目录,执行node api/src/server.js时,../../web/dist是相对于api/src/目录的路径,最终指向项目根/web/dist,该目录存在,所以静态资源能正常加载。
  • Docker容器中,WORKDIR设置为/code/demo,执行node api/src/server.js时,当前工作目录是/code/demo,此时../../web/dist会被解析为/code/web/dist,但实际web/dist目录在/code/demo/web/dist,路径不匹配导致Express找不到静态资源目录,无法响应GET /请求(因为默认首页index.html在静态资源目录中)。

解决方案

方案1:使用绝对路径(推荐)

修改server.js中的静态资源路径,通过__dirname拼接绝对路径,确保在任何环境下路径都准确:

// 先引入path模块
const path = require('path');
// 替换原来的express.static配置行
app.use(express.static(path.join(__dirname, '../../web/dist')));

__dirname代表当前文件(server.js)所在的目录(即api/src/),拼接../../web/dist后会正确指向项目根目录下的web/dist,在Docker容器中就是/code/demo/web/dist。

方案2:调整Docker工作目录(不推荐)

如果不想修改代码,可以调整Dockerfile的WORKDIR为/code/demo/api/src,并修改启动命令:

WORKDIR /code/demo/api/src
# ...其他配置不变
CMD [ "node", "server.js" ]

这种方式依赖Docker的工作目录设置,灵活性较差,不如绝对路径方案通用。

额外修复:Docker环境变量设置错误

Dockerfile中RUN export NODE_EXTRA_CA_CERTS=...这行无效,因为RUN命令的环境变量只在构建阶段的临时容器中生效,容器启动后不会保留。正确做法是使用ENV命令:

# 替换原来的RUN export行
ENV NODE_EXTRA_CA_CERTS=/usr/local/share/ca-certificates/swbc-certificate.crt

内容的提问来源于stack exchange,提问作者CB_at_Sw

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.02 18:43:13