fix(pay): actionable webhook.verify errors for the raw-body mistake - #36
Merged
Conversation
The #1 reason merchants "can't verify webhooks" is passing a parsed/re-serialized body instead of the raw request bytes (e.g. `req.body` after `express.json()`), which the SDK stringified to `[object Object]` and surfaced as a generic "signature does not match payload". They had no way to know what was wrong. - Reject a non-string/Buffer payload up front with a message that names the received type and shows the fix (`express.raw({ type: 'application/json' })`). - Add a raw-body hint to the signature-mismatch error, mirroring Stripe's "Are you passing the raw request body you received?". No change to the verification algorithm. Adds 3 tests (parsed object → helpful error, null → helpful error, mismatch → hints at raw body); 15/15 pass, tsc + biome clean. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
The most common "I can't verify AgentaOS webhooks" report is not a signing bug — it's integrators passing a parsed body instead of the raw request bytes (e.g.
req.bodyafter a globalexpress.json()). The SDK stringified that object to"[object Object]"and surfaced a generic "Signature does not match payload", giving no clue what was wrong.Verified against a real production webhook: signing is correct,
webhooks.verify()is correct, and the docs already showexpress.raw(). The gap was purely the error message — so people file tickets instead of self-diagnosing.Change (messages only — algorithm unchanged)
Tests
+3 cases in
webhooks.test.ts(parsed object → helpful error incl.express.raw,null→ helpful error, genuine mismatch → hints at raw body). 15/15 pass,tsc --noEmit+ biome clean. Changeset included (@agentaos/paypatch).🤖 Generated with Claude Code