Work / Payment orchestration
PayHub
UPI-first payment orchestration over Razorpay and Cashfree. One unified API, decline-code-aware failover between processors, and webhook events from different providers normalized into a single internal schema.
- Status
- built
- Period
- Sandbox only
- Stack
- TypeScriptNode.jsMongoDBBullMQRazorpayCashfree
- The crux
- Knowing when not to retry: a decline scoped to the customer’s own bank can never be fixed by switching processor.
What it is, and isn’t
A portfolio-scale reimplementation of real orchestration patterns, not a claim to invent the category — Hyperswitch, Orchestra and Kill Bill already do this at production scale. PayHub is not a gateway or a bank: no licenses, no direct NPCI or card-network connectivity, and it never touches raw credentials.
The differentiation
Most orchestrators treat UPI as one payment method among hundreds bolted onto a global-first routing engine. PayHub routes on a decline taxonomy grounded in NPCI’s own response categories, and on where the decline happened: the processor’s own infrastructure, NPCI’s shared network, the customer’s bank or VPA, or something only the customer can act on.
Only the first two trigger failover. The rest fail fast with an explanation, because every processor reaches the exact same issuing bank through NPCI — retrying can never succeed and only degrades the customer’s experience. That decision is one independently testable function rather than a branch buried in a request handler.
The architectural bet
Every processor adapter exposes the same three-method interface, so the core contains no processor-specific branching outside the adapter and webhook folders. That is the single most important decision in the codebase, and it paid off concretely: when the originally specified second processor turned out to be invite-only in India, swapping in a different one cost an adapter and no changes to the routing engine.
Handle classification — mapping a VPA suffix to the customer’s UPI app — is reasoning, not control. No merchant-side backend can move a customer between UPI apps mid-transaction. What it buys is an honest, specific explanation instead of a generic failure.
Testing
Adapters run against injected fake clients: no network, fully deterministic. Integration tests run against an in-memory MongoDB and cover the idempotency guarantee, a scripted failover where the primary times out and the event timeline shows the whole story, and handle-aware fail-fast where a bank-scoped decline never fails over even with a healthy fallback available.
Next — Jewellery Billing