Node.js HTTP服务接收POST数据时仅获取到首个Buffer数据块
问题根因
Node.js 原生 HTTP 模块的请求体是分片流式传输的:
- 每抵达一个数据分片,触发一次
data事件 - 全部分片传输完毕,才会触发
end事件
你的代码在注册data事件监听后立刻调用res.end()返回响应,连接被提前终止,后续还没传完的分片直接被丢弃,自然只能拿到第一个Buffer块。
修复方案
先声明数组存储所有收到的Buffer分片,等end事件触发(数据全部接收完成)后,再拼接完整请求体、处理业务逻辑、返回响应。
修正后的完整代码如下:
const http = require('http'); const server = http.createServer((req, res) => { if (req.url === '/') { res.write('<html><head><title>Form</title></head>'); res.write( '<body><form method="post" action="/process"><input name="message" /></form></body>' ); res.end(); } else if (req.url === '/process' && req.method === 'POST') { // 存储所有数据分片 const bodyChunks = []; req.on('data', (chunk) => { bodyChunks.push(chunk); console.log('收到数据分片:', chunk); }); req.on('end', () => { // 所有分片接收完成后拼接为完整请求体 const fullBody = Buffer.concat(bodyChunks); // 表单默认是urlencoded格式,转字符串即可读取提交内容 console.log('完整请求体:', fullBody.toString()); // 数据全部处理完再返回响应 res.write('Thank you for submitting'); res.end(); }); } else { res.write('Not found'); res.end(); } }); server.listen(3000); console.log('listening on port 3000');
运行效果说明
修复前控制台仅能打印第一个分片,效果如下:
修复后会逐次打印所有收到的分片,最终输出完整拼接后的请求体内容,不会出现数据丢失。
提示:如果需要接收超大体积文本,建议额外增加请求体大小校验逻辑,避免恶意大请求占满服务器内存。
内容的提问来源于stack exchange,提问作者Sudipta Das
相关产品推荐
相关产品推荐

