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

不使用Express如何实现多文件服务?附问题代码及异常

嘿,我来帮你搞定这个问题!你的代码现在的问题很典型——因为fs.readFile是异步操作,你同时发起了两个文件读取请求,而且不管哪个先完成,都直接调用res.end(),这就导致响应被覆盖或者提前结束了,所以有时候页面只显示CSS内容。

问题根源

你的代码里同时执行了两个fs.readFile,这两个操作是并行的。当其中一个先完成时,就会调用res.writeHead和res.end,直接把响应发回给浏览器了。另一个操作完成后再调用res.end的时候,响应已经结束了,浏览器只会收到第一个返回的内容,所以才会出现有时候显示HTML、有时候显示CSS的情况。而且res.end()只能被调用一次,多次调用会导致错误。

正确的实现思路

要处理不同的请求路径,根据浏览器请求的URL来返回对应的文件,而不是不管请求什么都同时返回两个文件。具体步骤:

  • 解析请求的URL,判断用户要访问的是哪个文件
  • 根据不同的路径,设置对应的Content-Type
  • 读取对应文件并返回,处理文件不存在的情况
完整代码示例
const http = require('http');
const fs = require('fs');
const path = require('path');
const port = 3000;

http.createServer((req, res) => {
  // 处理请求路径,默认返回index.html
  let filePath = '.' + req.url;
  if (filePath === './') {
    filePath = './public/index.html';
  }

  // 根据文件扩展名设置Content-Type
  const extname = path.extname(filePath);
  let contentType = 'text/html';
  switch (extname) {
    case '.css':
      contentType = 'text/css';
      break;
    case '.js':
      contentType = 'text/javascript';
      break;
    case '.json':
      contentType = 'application/json';
      break;
    case '.png':
      contentType = 'image/png';
      break;
    case '.jpg':
      contentType = 'image/jpeg';
      break;
  }

  // 读取文件并返回响应
  fs.readFile(filePath, (err, content) => {
    if (err) {
      if (err.code === 'ENOENT') {
        // 文件不存在时返回404页面
        fs.readFile('./public/404.html', (err, content) => {
          res.writeHead(404, {'Content-Type': 'text/html'});
          res.end(content, 'utf-8');
        });
      } else {
        // 服务器内部错误
        res.writeHead(500);
        res.end(`服务器错误: ${err.code}`, 'utf-8');
      }
    } else {
      // 文件存在时返回对应内容
      res.writeHead(200, {'Content-Type': contentType});
      res.end(content, 'utf-8');
    }
  });
}).listen(port, () => {
  console.log(`服务器运行在 http://localhost:${port}/`);
});
代码说明
  • 路径解析:通过req.url获取浏览器请求的路径,默认访问根路径时返回index.html
  • Content-Type设置:用path.extname获取文件扩展名,根据不同类型设置正确的响应头,这样浏览器才能正确解析文件
  • 错误处理:处理文件不存在(404)和服务器内部错误(500)的情况,避免服务器崩溃
  • 单一响应:每个请求只读取对应文件,调用一次res.end(),确保响应内容正确无误

这样修改后,浏览器请求/时返回HTML,请求/styles/style.css时返回CSS,就不会出现内容混乱的问题了。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.25 07:51:24