Node.js - 使用 Express 获取原始请求正文
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/18710225/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Node.js - get raw request body using Express
提问by haitao_wu
When I use Express, and my code is:
当我使用 Express 时,我的代码是:
app.use(express.bodyParser());
How would I get the raw request body?
我将如何获得原始请求正文?
回答by hexacyanide
Edit 2:Release 1.15.2 of the body parser module introduces raw mode, which returns the body as a Buffer. By default, it also automatically handles deflate and gzip decompression. Example usage:
编辑 2:主体解析器模块的 1.15.2 版引入了原始模式,它将主体作为Buffer返回。默认情况下,它还自动处理 deflate 和 gzip 解压缩。用法示例:
var bodyParser = require('body-parser');
app.use(bodyParser.raw(options));
app.get(path, function(req, res) {
// req.body is a Buffer object
});
By default, the optionsobject has the following default options:
默认情况下,options对象具有以下默认选项:
var options = {
inflate: true,
limit: '100kb',
type: 'application/octet-stream'
};
If you want your raw parser to parse other MIME types other than application/octet-stream, you will need to change it here. It will also support wildcard matching such as */*or */application.
如果您希望原始解析器解析除 之外的其他 MIME 类型application/octet-stream,则需要在此处进行更改。它还将支持通配符匹配,例如*/*或*/application。
Note:The following answer is for versions before Express 4, where middleware was still bundled with the framework. The modern equivalent is the body-parsermodule, which must be installed separately.
注意:以下答案适用于 Express 4 之前的版本,其中中间件仍与框架捆绑在一起。现代的等价物是body-parser模块,它必须单独安装。
The rawBodyproperty in Express was once available, but removed since version 1.5.1. To get the raw request body, you have to put in some middleware before using the bodyParser. You can also read a GitHub discussion about it here.
rawBodyExpress 中的属性曾经可用,但从 1.5.1 版开始删除。要获取原始请求正文,您必须在使用 bodyParser 之前放入一些中间件。您还可以在此处阅读有关它的 GitHub 讨论。
app.use(function(req, res, next) {
req.rawBody = '';
req.setEncoding('utf8');
req.on('data', function(chunk) {
req.rawBody += chunk;
});
req.on('end', function() {
next();
});
});
app.use(express.bodyParser());
That middleware will read from the actual data stream, and store it in the rawBodyproperty of the request. You can then access the raw body like this:
该中间件将从实际数据流中读取,并将其存储在rawBody请求的属性中。然后,您可以像这样访问原始正文:
app.post('/', function(req, res) {
// do something with req.rawBody
// use req.body for the parsed body
});
Edit:It seems that this method and bodyParser refuse to coexist, because one will consume the request stream before the other, leading to whichever one is second to never fire end, thus never calling next(), and hanging your application.
编辑:似乎这个方法和 bodyParser 拒绝共存,因为一个会在另一个之前消耗请求流,导致第二个永远不会触发end,因此永远不会调用next(),并挂起你的应用程序。
The simplest solution would most likely be to modify the source of bodyParser, which you would find on line 57of Connect's JSON parser. This is what the modified version would look like.
最简单的解决方案很可能是修改 bodyParser 的源代码,您可以在Connect 的 JSON 解析器的第 57 行找到它。这就是修改后的版本的样子。
var buf = '';
req.setEncoding('utf8');
req.on('data', function(chunk){ buf += chunk });
req.on('end', function() {
req.rawBody = buf;
var first = buf.trim()[0];
...
});
You would find the file at this location:
您将在以下位置找到该文件:
/node_modules/express/node_modules/connect/lib/middleware/json.js.
/node_modules/express/node_modules/connect/lib/middleware/json.js.
回答by Tiago A.
I got a solution that plays nice with bodyParser, using the verifycallback in bodyParser. In this code, I am using it to get a sha1 of the content and also getting the raw body.
我得到了一个与 bodyParser 配合得很好的解决方案,它使用了 bodyParser 中的verify回调。在这段代码中,我使用它来获取内容的 sha1 并获取原始正文。
app.use(bodyParser.json({
verify: function(req, res, buf, encoding) {
// sha1 content
var hash = crypto.createHash('sha1');
hash.update(buf);
req.hasha = hash.digest('hex');
console.log("hash", req.hasha);
// get rawBody
req.rawBody = buf.toString();
console.log("rawBody", req.rawBody);
}
}));
I am new in Node.js and express.js (started yesterday, literally!) so I'd like to hear comments on this solution.
我是 Node.js 和 express.js 的新手(从昨天开始,字面意思!)所以我想听听对此解决方案的评论。
回答by Pavel Evstigneev
This solution worked for me:
这个解决方案对我有用:
var rawBodySaver = function (req, res, buf, encoding) {
if (buf && buf.length) {
req.rawBody = buf.toString(encoding || 'utf8');
}
}
app.use(bodyParser.json({ verify: rawBodySaver }));
app.use(bodyParser.urlencoded({ verify: rawBodySaver, extended: true }));
app.use(bodyParser.raw({ verify: rawBodySaver, type: '*/*' }));
When I use solution with req.on('data', function(chunk) { });it not working on chunked request body.
当我使用解决方案时,req.on('data', function(chunk) { });它不适用于分块请求正文。
回答by nortron
BE CAREFUL with those other answers as they will not play properly with bodyParser if you're looking to also support json, urlencoded, etc. To get it to work with bodyParser you should condition your handler to only register on the Content-Typeheader(s) you care about, just like bodyParser itself does.
请注意其他答案,因为如果您还希望支持 json、urlencoded 等,它们将无法与 bodyParser 一起正常播放。要使其与 bodyParser 一起使用,您应该将处理程序设置为仅在您的Content-Type标头上注册关心,就像 bodyParser 本身一样。
To get the raw body content of a request with Content-Type: "text/plain"into req.rawBodyyou can do:
为了得到一个请求的原始主体内容Content-Type: "text/plain"到req.rawBody你可以这样做:
app.use(function(req, res, next) {
var contentType = req.headers['content-type'] || ''
, mime = contentType.split(';')[0];
if (mime != 'text/plain') {
return next();
}
var data = '';
req.setEncoding('utf8');
req.on('data', function(chunk) {
data += chunk;
});
req.on('end', function() {
req.rawBody = data;
next();
});
});
回答by oferei
This is a variation on hexacyanide's answer above. This middleware also handles the 'data' event but does not wait for the data to be consumed before calling 'next'. This way both this middleware and bodyParser may coexist, consuming the stream in parallel.
这是上述六氰化物答案的变体。该中间件还处理“数据”事件,但不会在调用“下一步”之前等待数据被使用。这样,这个中间件和 bodyParser 可以共存,并行消费流。
app.use(function(req, res, next) {
req.rawBody = '';
req.setEncoding('utf8');
req.on('data', function(chunk) {
req.rawBody += chunk;
});
next();
});
app.use(express.bodyParser());
回答by mewc
Use body-parserParse the body with what it will be:
使用body-parser解析正文:
app.use(bodyParser.text());
app.use(bodyParser.text());
app.use(bodyParser.urlencoded());
app.use(bodyParser.urlencoded());
app.use(bodyParser.raw());
app.use(bodyParser.raw());
app.use(bodyParser.json());
app.use(bodyParser.json());
ie. If you are supposed to get raw text file, run .text().
IE。如果您应该获取原始文本文件,请运行.text().
Thats what body-parser currently supports
这就是 body-parser 目前支持的内容

