Node.js配置express.static托管静态文件访问报错求助
我在编写Node.js服务端代码时,尝试配置静态文件夹实现公开访问,对应的server.js代码如下:
server.js 代码
const express = require("express"); const app = express(); require("dotenv").config(); const cookieParser = require("cookie-parser"); const bodyParser = require("body-parser"); const { connectDB } = require("./config/connectDB"); connectDB(); const upload = require("./routes/uploadsFile"); const user = require("./routes/user"); const path = require("path"); app.use(bodyParser.json()); app.use(bodyParser.urlencoded({ extended: true })); app.use(cookieParser()); app.use(express.json("content-type", "application/json")); const publicFolder = path.join(__dirname, "../uploads"); console.log(publicFolder); app.use(express.static(publicFolder)); app.use("/api/v1/upload", upload); app.use("/api/v1/user", user); const PORT = process.env.PORT || 3030; app.listen(PORT, () => { console.log(`Server Started Listening On PORT ${PORT}`); });
我的项目文件夹结构如下图所示:
访问静态资源时出现报错:
Cannot GET /uploads/image/actual-size/banner-Image-1.jpg
我已经查阅过Stack Overflow上大量该类问题的已有解答,但始终没有找到适配的解决方案,恳请各位帮忙排查问题原因。
核心原因是静态资源的挂载路径和访问路径不匹配:
你当前写的app.use(express.static(publicFolder))是把uploads目录直接挂载到了服务根路径,也就是说uploads文件夹内的文件,访问路径不需要带/uploads前缀。比如文件实际路径是uploads/image/actual-size/banner-Image-1.jpg,按你现在的配置,正确访问路径应该是http://你的域名:端口/image/actual-size/banner-Image-1.jpg,你访问时多带了一层/uploads,自然会报404。
两种修复方案选其一即可:
- 方案1(推荐):给静态资源添加统一访问前缀,把静态资源挂载代码改成:
app.use("/uploads", express.static(publicFolder));
改完后你原来的访问路径/uploads/image/actual-size/banner-Image-1.jpg就能正常映射到对应文件,也方便后续统一管理静态资源路由,不会和其他接口/路由冲突。
- 方案2:不修改挂载配置,访问时去掉路径里的
/uploads前缀,直接访问/image/actual-size/banner-Image-1.jpg即可,不推荐用这种方式,后续根路径下路由多了很容易出现冲突。
额外排查提示:
你代码里已经写了console.log(publicFolder),启动服务时可以先复制控制台打印的绝对路径,直接在文件管理器里打开,确认路径下确实存在你要访问的目标文件,排除路径拼接错误的问题。从你提供的目录结构来看,path.join(__dirname, "../uploads")的路径是正确的,不需要调整。
顺便提一句无关但会埋坑的问题:你代码里的app.use(express.json("content-type", "application/json"));写法错误,express.json()只接收配置对象参数,不需要传这两个字符串,直接写app.use(express.json())即可,而且你前面已经引入配置了bodyParser.json(),这行重复配置甚至可以直接删掉,避免后续接口解析出问题。
内容的提问来源于stack exchange,提问作者fzee07

