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

Stripe Webhook签名验证失败求助(本地正常线上报错)

Stripe Webhook签名验证失败(本地正常,Cloud Run部署后报错)

问题核心原因

Stripe Webhook的签名验证依赖原始未解析的HTTP请求体字节,你的代码中使用了req.body——如果Express全局配置了express.json()中间件,这个req.body已经是解析后的JSON对象,并非Stripe计算签名时用的原始字节,直接导致签名匹配失败。本地可能因中间件顺序或环境差异未触发解析,但Cloud Run环境下中间件正常生效,因此报错。

解决方案

1. 针对Webhook路由单独配置原始请求体解析

在Webhook路由上禁用默认JSON解析,改用express.raw()中间件获取原始Buffer:

const express = require('express');

// 调整路由,将raw中间件放在最前面
router.post("/orderupdate", express.raw({ type: "application/json" }), catchAsync(async (req, res) => {
    const payload = req.body; // 此时为原始Buffer,符合Stripe验证要求
    const sig = req.headers['stripe-signature'];
    let event;

    try {
        event = stripe.webhooks.constructEvent(payload, sig, endpointSecret);
    } catch (e) {
        console.error("签名验证失败:", e);
        return res.status(400).send(`Webhook Error: ${e.message}`);
    }

    try {
        if (event.type === "checkout.session.completed") {
            // 你的业务逻辑代码
        }
    } catch (e) {
        console.error("事件处理失败:", e);
    }

    res.status(200).end();
}))

2. 额外排查点

  • 确认签名密钥正确性:检查endpointSecret是否为Stripe Dashboard中对应Webhook的签名密钥(测试环境用测试密钥,生产环境用生产密钥,不可混用)。
  • 中间件顺序:确保express.raw()是Webhook路由的第一个中间件,避免日志、JSON解析等其他中间件提前修改请求体。
  • Cloud Run环境检查:确认没有网关或负载均衡在转发请求时自动解析并修改JSON请求体,Stripe要求请求体必须和发送时完全一致。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.05 04:05:15