Express 4.17为一个端点获取raw body



我正试图在我的web API中实现条纹,需要读取请求的原始体。我的应用程序中已经存在不需要原始正文的API路径。

我实现的代码是基于Stripe文档的例子,见下文。

const stripe = require('stripe')('apikey...');
const endpointSecret = 'whsec_...';
const express = require('express');
const app = express();
app.post('/webhook', express.raw({type: 'application/json'}), (request, response) => {
let event = request.body;
console.log('body', event);
const headers = JSON.stringify(request.headers);
console.log('Headers', headers);
// Only verify the event if you have an endpoint secret defined.
// Otherwise use the basic event deserialized with JSON.parse
if (endpointSecret) {
// Get the signature sent by Stripe
const signature = request.headers['stripe-signature'];
try {
event = stripe.webhooks.constructEvent(request.body, signature, endpointSecret);
} catch (err) {
console.log(`⚠️  Webhook signature verification failed.`, err.message);
return response.sendStatus(400);
}
}
// Handle the event
...
// Return a 200 response to acknowledge receipt of the event
response.send();
});
app.listen(443, () => console.log('Running on port 443'));

这段代码记录了下面的消息——因为原始正文是空的。

body
Headers {"host":".....}
⚠️ Webhook signature verification failed. No signatures found matching the expected signature for payload. Are you passing the raw request body you received from Stripe? https://github.com/stripe/stripe-node#webhook-signing

我已经尝试通过添加一个中间件来读取原始体来解决这个问题。

// Custom middleware that keeps the raw request body. This is needed for Stripe
app.use((req, res, next)=>{
req.rawBody = '';
req.on('data', (chunk) => { req.rawBody += chunk; });
req.on('end', () => {
try {
req.body = JSON.parse(req.rawBody);
next();
} catch (err) {
console.log('Error parsing body')
next();
}
});
});
app.post('/webhook', (request, response) => {
let event = request.body;
console.log('rawBody', request.rawBody)
if (endpointSecret) {
// Get the signature sent by Stripe
const signature = request.headers['stripe-signature'];
try {
event = stripe.webhooks.constructEvent(request.rawBody, signature, endpointSecret);
} catch (err) {
console.log(`⚠️  Webhook signature verification failed.`, err.message);
return resp.sendStatus(400);
}

根据日志,原始主体仍然是空的。在控制台我仍然得到相同的错误信息。

如何将原始正文添加到请求中?最好使用中间件。问候/K

更新:(感谢Bravo!)下面的代码似乎可以通过暴露原始体

来工作
app.post('/webhook', express.raw(), (request, response) => {
let event = request.rawBody;

我能够通过将verify方法添加到express.json中间件配置(在引子下使用body-parser)来解决这个问题。

的例子:

const RAW_BODY_WHITELIST = ['/webhooks/stripe'];
app.use(express.json({
verify: (req: Request, _res: Response, buf: Buffer, _encoding: string) => {
if (RAW_BODY_WHITELIST.includes(req.path)) {
req.rawBody = buf.toString();
}
},
}));

这样,你可以很好地组织所有中间件,而不必在其他中间件之前或之间声明webhook路由。

相关内容

最新更新