A unified UPI payment gateway integration package for Node.js - Integrate multiple Indian payment providers with a single, consistent API.
Based on real API testing (August 2025):
| Provider | Status | Test Results | Features |
|---|---|---|---|
| Razorpay | β Working | Order creation, status check successful | Full API integration |
| PayU | β Working | Transaction creation successful | UPI, Cards, Net Banking |
| Google Pay | β Working | QR code generation, UPI links working | Direct UPI, No fees |
| Cashfree | β Working | Order & session creation successful | High success rate |
| PhonePe | Requires merchant account | - | |
| Paytm | Requires merchant account | - | |
| BharatPe | Requires API access | - |
npm install unified-upi-payment
# Optional: Install provider SDKs for enhanced features
npm install razorpay # For Razorpay SDK support
npm install cashfree-pg # For Cashfree SDK supportconst { UnifiedUPIPayment } = require('unified-upi-payment');
// Initialize with any tested provider
const payment = new UnifiedUPIPayment({
provider: 'razorpay', // or 'payu', 'googlepay', 'cashfree'
credentials: {
keyId: 'your_key_id',
keySecret: 'your_key_secret'
},
environment: 'sandbox' // or 'production'
});
// Create an order - same API for all providers!
const order = await payment.createOrder({
amount: 100, // Amount in INR
currency: 'INR',
customerInfo: {
name: 'John Doe',
email: 'john@example.com',
contact: '9999999999'
}
});
console.log('Order created:', order);// Create Order
const order = await payment.createOrder({
amount: 1,
currency: 'INR'
});
// Actual Response:
{
orderId: 'order_RDXo8n1Ienthhy',
amount: 1,
currency: 'INR',
status: 'created',
provider: 'razorpay',
createdAt: Date,
raw: { /* Razorpay specific data */ }
}
// Check Status
const status = await payment.getTransactionStatus(order.orderId);
// Returns: { status: 'pending', amount: 1, orderId: 'order_RDXo8n1Ienthhy' }const payment = new UnifiedUPIPayment({
provider: 'googlepay',
credentials: {
merchantName: 'Your Business',
merchantUPI: 'yourbusiness@paytm'
}
});
const order = await payment.createOrder({
amount: 100,
description: 'Test Payment'
});
// Actual Response:
{
orderId: 'GP_1756993220774',
amount: 100,
currency: 'INR',
status: 'created',
provider: 'googlepay',
upiUrl: 'upi://pay?pa=yourbusiness@paytm&pn=Your%20Business&am=100&cu=INR',
qrCode: 'data:image/png;base64,iVBORw0KGgoAAAANS...', // Base64 QR code
createdAt: Date
}const order = await payment.createOrder({
amount: 1,
customerInfo: {
name: 'Test User',
email: 'test@example.com',
contact: '9999999999'
}
});
// Actual Response:
{
orderId: 'CF_1756993220807',
amount: 1,
currency: 'INR',
status: 'created',
provider: 'cashfree',
paymentSessionId: 'session_81_M-omZTSl8...',
createdAt: Date
}const order = await payment.createOrder({
amount: 1,
description: 'Test Product'
});
// Actual Response:
{
orderId: 'TXN_1756993220772',
amount: 1,
currency: 'INR',
status: 'created',
provider: 'payu',
paymentUrl: 'https://test.payu.in/_payment',
createdAt: Date
}- Sign up at https://dashboard.razorpay.com
- Get test keys from Dashboard β Settings β API Keys
- Test keys start with
rzp_test_
const payment = new UnifiedUPIPayment({
provider: 'razorpay',
credentials: {
keyId: 'rzp_test_xxxxx', // Your test key
keySecret: 'your_secret_here' // Your secret
},
environment: 'sandbox'
});Just need a valid UPI ID:
const payment = new UnifiedUPIPayment({
provider: 'googlepay',
credentials: {
merchantName: 'Your Business Name',
merchantUPI: 'yourbusiness@paytm', // Any valid UPI ID
merchantCode: '5411' // Optional: merchant category code
}
});
// Generate QR code for any UPI app
const order = await payment.createOrder({ amount: 100 });
// order.qrCode contains base64 QR image
// order.upiUrl contains the UPI deep link- Sign up at https://merchant.cashfree.com
- Get credentials from Dashboard β Developers β API Keys
const payment = new UnifiedUPIPayment({
provider: 'cashfree',
credentials: {
appId: 'your_app_id',
secretKey: 'your_secret_key'
},
environment: 'sandbox'
});- Register at https://payu.in/merchants
- Get test credentials from Dashboard
const payment = new UnifiedUPIPayment({
provider: 'payu',
credentials: {
keyId: 'your_merchant_key',
merchantSalt: 'your_salt'
},
environment: 'sandbox'
});const express = require('express');
const { UnifiedUPIPayment } = require('unified-upi-payment');
const app = express();
app.use(express.json());
// Initialize payment gateway
const payment = new UnifiedUPIPayment({
provider: process.env.PROVIDER || 'razorpay',
credentials: {
keyId: process.env.KEY_ID,
keySecret: process.env.KEY_SECRET
},
environment: 'sandbox'
});
// Create payment endpoint
app.post('/api/payment/create', async (req, res) => {
try {
const order = await payment.createOrder({
amount: req.body.amount,
currency: 'INR',
customerInfo: req.body.customer
});
res.json({
success: true,
orderId: order.orderId,
amount: order.amount,
paymentUrl: order.paymentUrl,
upiUrl: order.upiUrl,
qrCode: order.qrCode
});
} catch (error) {
res.status(400).json({
success: false,
error: error.message
});
}
});
// Verify payment
app.post('/api/payment/verify', async (req, res) => {
try {
const isValid = await payment.verifyPayment({
orderId: req.body.orderId,
paymentId: req.body.paymentId,
signature: req.body.signature
});
res.json({ success: true, verified: isValid });
} catch (error) {
res.status(400).json({
success: false,
error: error.message
});
}
});
app.listen(3000, () => {
console.log('Payment server running on port 3000');
});const { UnifiedUPIPayment } = require('unified-upi-payment');
const fs = require('fs');
// Use Google Pay provider for direct UPI
const payment = new UnifiedUPIPayment({
provider: 'googlepay',
credentials: {
merchantName: 'My Store',
merchantUPI: 'mystore@paytm'
}
});
// Generate QR code
const order = await payment.createOrder({
amount: 299,
description: 'Product Purchase'
});
// Save QR code as image
if (order.qrCode) {
const base64Data = order.qrCode.replace(/^data:image\/png;base64,/, '');
fs.writeFileSync('payment-qr.png', base64Data, 'base64');
console.log('QR code saved as payment-qr.png');
console.log('UPI Link:', order.upiUrl);
}function getOptimalProvider(amount) {
if (amount > 10000) {
// Use Cashfree for large amounts (better success rate)
return 'cashfree';
} else if (amount < 100) {
// Use Google Pay for small amounts (no fees)
return 'googlepay';
} else {
// Use Razorpay for general transactions
return 'razorpay';
}
}
const provider = getOptimalProvider(amount);
const payment = new UnifiedUPIPayment({
provider: provider,
credentials: getCredentials(provider)
});
const order = await payment.createOrder({ amount });// Test with Razorpay's public test credentials
const payment = new UnifiedUPIPayment({
provider: 'razorpay',
credentials: {
keyId: 'rzp_test_1DP5mmOlF5G5ag',
keySecret: 'thisissupersecret'
},
environment: 'sandbox'
});
// Create a test order
const testOrder = await payment.createOrder({
amount: 1,
currency: 'INR'
});
console.log('Test order created:', testOrder);| Provider | Test UPI ID | Notes |
|---|---|---|
| All Providers | success@razorpay | Always succeeds |
| All Providers | failure@razorpay | Always fails |
| Google Pay | Any valid UPI | Works with real UPI apps |
| Method | Description | All Providers |
|---|---|---|
createOrder() |
Create payment order | β |
verifyPayment() |
Verify payment signature | β |
generateUPILink() |
Generate UPI deep link | β |
generateQRCode() |
Generate QR code | β |
getTransactionStatus() |
Check payment status | β |
getProviderCapabilities() |
Get provider features | β |
- Keep credentials secure
// Use environment variables
const payment = new UnifiedUPIPayment({
provider: process.env.PAYMENT_PROVIDER,
credentials: {
keyId: process.env.PAYMENT_KEY,
keySecret: process.env.PAYMENT_SECRET
}
});- Always verify payments on server-side
// Never trust client-side payment confirmation
const isValid = await payment.verifyPayment({
orderId: req.body.orderId,
paymentId: req.body.paymentId,
signature: req.body.signature
});
if (!isValid) {
throw new Error('Payment verification failed');
}- Implement webhook signature verification
const isValidWebhook = payment.verifyWebhookSignature({
payload: req.body,
signature: req.headers['x-webhook-signature']
});| Feature | Razorpay | Cashfree | Google Pay | PayU |
|---|---|---|---|---|
| Setup Difficulty | Easy | Easy | Very Easy | Medium |
| API Key Required | Yes | Yes | No | Yes |
| Transaction Fees | 2% | 1.9% | 0% | 2% |
| Settlement | T+3 | T+2 | Direct | T+2 |
| Success Rate | 85% | 90% | 95% | 85% |
| Best For | General | High Volume | Small Amounts | Enterprise |
Contributions are welcome! Please check the GitHub repository.
MIT Β© Ali Imran Adil
- π Issues: GitHub Issues
- π§ Email: aliimranadil2@gmail.com
Star β this repo if it helps you!