Repository navigation
fix(payments): settle VOD, seedbox and IPTV pass payments from the one CoinPay webhook - #296
Merged
Merged
Conversation
… the one CoinPay webhook CoinPay delivers every event for a business to its single webhook_url (https://bittorrented.com/api/webhooks/coinpayportal). The VOD, seedbox rental and IPTV resale pass checkouts sent a per-payment webhook_url (/vod, /share, /iptv-share) that CoinPay never delivers to, so a paid pass reached the main route, matched no payment_history row, and was never granted. The main route now dispatches on metadata.type (vod, seedbox_share, iptv_share) to the existing grant handlers, after the same signature check (HMAC over t.rawBody, 300 s tolerance), before the translation, session and subscription paths. An unknown grant is a 200 no-op; a handler error is a 500 so CoinPay redelivers. Idempotency: VOD and seedbox markGrantPaid are now conditional (pending or expired -> paid, returning whether it changed), as IPTV's already was, so a redelivery or a confirmed-then-forwarded pair credits provider/share earnings once. The three old routes are thin forwards (re-export of the main POST/GET), and the checkouts now name the main webhook. Tests: grant-routing.test.ts posts really signed, nested CoinPay payloads per kind through the real verifier (paid once, forwarded/redelivery no-op, expired, unknown payment, bad signature 401, old addresses forward, subscription payments still reach the subscription handler). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
ThreatCrush Security Scan97 finding(s) HIGH/CRITICAL: 11 | MEDIUM: 30 | LOW: 56
…and 47 more. Full results in the Security tab. Snippets are redacted; ThreatCrush never prints matched credential material. |
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.
CoinPay only delivers to the business's single
webhook_url(/api/webhooks/coinpayportal), so thevod,shareandiptv-shareroutes never received a delivery and paid passes were never granted.metadata.type(vod/seedbox_share/iptv_share) to the existing grant handlers, after signature verification, ahead of translation/session/subscription handling. Unknown grant: 200 no-op. Handler error: 500 (redelivery).markGrantPaidnow conditional (pending/expired -> paid) and return whether they changed, like IPTV's; earnings count once across confirmed + forwarded + redeliveries.export { POST, GET } from '../route'). Checkouts now name the main webhook.grant-routing.test.tswith really signed nested payloads per kind through the real verifier. Full vitest 3106 pass;next buildok.🤖 Generated with Claude Code