Stripe支付链接Webhook触发‘User not found’错误排查求助
问题排查方案
针对你遇到的Stripe Webhook触发“User not found!”错误,核心原因是云函数处理事件时,用于查询Firebase用户的UID无效或未正确获取,以下是具体排查和修复步骤:
1. 验证client_reference_id的传递与存储
- 登录Stripe测试仪表板,找到触发报错的事件对应的Checkout Session(比如从
checkout.session.completed事件直接进入,或从invoice/subscription关联的会话进入),查看client_reference_id字段的值是否与你传入的十六进制UID完全一致。如果值为空或不符,说明生成支付链接时参数传递有误。
2. 针对不同事件类型,修正client_reference_id的获取路径
不同Stripe事件中,client_reference_id的存储位置不同,直接错误取值会导致拿到空值或无效值:
checkout.session.completed:直接从事件对象中获取:event.data.object.client_reference_idinvoice.paid/invoice.payment_succeeded:invoice本身不会携带client_reference_id,需要先通过event.data.object.checkout_session拿到会话ID,再调用Stripe API查询会话详情获取该字段:const sessionId = event.data.object.checkout_session; const session = await stripe.checkout.sessions.retrieve(sessionId); const hexUid = session.client_reference_id;customer.subscription.created/customer.subscription.updated:需要先关联到最新账单,再关联到会话:const invoiceId = event.data.object.latest_invoice; const invoice = await stripe.invoices.retrieve(invoiceId); const sessionId = invoice.checkout_session; const session = await stripe.checkout.sessions.retrieve(sessionId); const hexUid = session.client_reference_id;
3. 检查十六进制UID的解码逻辑
你传入的是十六进制编码的UID,必须正确解码为原始Firebase用户UID才能查询到用户:
- 假设生成支付链接时用
Buffer.from(originalUid).toString('hex')编码,解码时需用:const originalUid = Buffer.from(hexUid, 'hex').toString('utf8'); - 在云函数中添加日志,打印解码前后的UID值,确认解码后的字符串与Firebase控制台中的用户UID完全匹配。
4. 验证Firebase用户查询逻辑
- 用解码后的UID,直接在Firebase测试控制台的用户列表中搜索,确认该用户确实存在。如果不存在,说明支付流程中用户未正确创建到Firebase,或你使用了错误的项目环境(比如生产环境的云函数查询测试环境的用户)。
- 检查云函数中查询用户的代码,确保调用
admin.auth().getUser(originalUid)时,传入的是正确解码后的UID,且没有额外的字符(比如空格、换行)。
5. 错误处理逻辑优化
你的函数返回了状态码200但报错,说明错误被捕获但未正确处理。建议在捕获“用户不存在”错误时,区分场景:如果是因为client_reference_id未正确获取导致的,可视为无效事件并返回200;如果是用户确实不存在但业务需要处理,需补充对应的创建或告警逻辑。
内容的提问来源于stack exchange,提问作者umop
相关产品推荐
相关产品推荐

