Hosted Checkout Integration
The Payment Gateway provides a fully-hosted, PCI-compliant checkout page that handles card collection and payment processing. This eliminates your PCI compliance burden and provides a secure, optimized payment experience.https://checkout-page-amber.vercel.appBuilt with Next.js 15, React 19, and TypeScriptWhy Use Hosted Checkout?
Zero PCI Compliance Burden
Enterprise-Grade Security
Optimized Conversion
Zero Maintenance
Security Features
PCI-DSS Compliance
Client-Side Security
Client-Side Security
- Luhn algorithm validation (detects typos)
- Expiry date validation (rejects expired cards)
- CVV format validation (3-4 digits)
- Real-time error feedback
- Special characters blocked
- Paste prevention on CVV field
- Numeric-only inputs for card numbers
Transport Security
Transport Security
- TLS 1.3 encryption for all requests
- Strict-Transport-Security headers
- Content-Security-Policy enforcement
- Client secret validation (not API keys)
- One-time use secrets per payment intent
- Automatic expiration after 1 hour
Session Security
Session Security
- Payment intents expire after 1 hour
- Automatic redirect on expiration
- Clear expiration messaging
- Maximum 5 payment attempts per intent
- Progressive delay between attempts
- Automatic intent invalidation after max attempts
Data Protection
Data Protection
- Card data never logged or stored client-side
- Tokenization happens server-side immediately
- Only last 4 digits stored for receipts
- Generic error messages (no sensitive data exposed)
- No card details in error logs
- Rate limiting on validation failures
How It Works
Payment Flow
Integration Steps
Create Payment Intent (Server-Side)
Redirect Customer to Checkout
checkout_url from the response:Customer Completes Payment
- Validates payment intent hasn’t expired
- Displays order summary (amount, currency)
- Collects card details with real-time validation
- Submits payment to API with client_secret
- Shows success animation or error message
- Redirects to your success/cancel URL
Handle Customer Return
Checkout Page Features
User Experience
Responsive Design
Real-Time Validation
Smart Card Detection
Accessibility
Payment Summary Display
The checkout page automatically displays:Supported Payment Methods
- Credit Cards
- Validation Rules
- Test Cards
- All Visa cards supported
- Test card: 4242 4242 4242 4242
- All Mastercard types supported
- Test card: 5555 5555 5555 4444
- 13-19 digit card number
- Valid expiry date (MM/YY format)
- 3-4 digit CVV/CVC code
- Cardholder name
Error Handling
Payment Intent Errors
Intent Expired (410 Gone)
Intent Expired (410 Gone)
- Automatic redirect to
cancel_urlafter 5 seconds - “Return to Merchant” button shown immediately
Invalid Client Secret (401 Unauthorized)
Invalid Client Secret (401 Unauthorized)
Intent Already Completed (422 Unprocessable)
Intent Already Completed (422 Unprocessable)
- Redirect to
success_urlimmediately
- Customer refreshed page after successful payment
- Attempting to pay twice with same intent
Maximum Attempts Reached (410 Gone)
Maximum Attempts Reached (410 Gone)
- Redirect to
cancel_url - Show “Contact Support” button
- 5 failed payment attempts on this intent
Card Validation Errors
Invalid Card Number
- Luhn check fails
- Less than 13 or more than 19 digits
- Non-numeric characters
Expired Card
- Expiry date in the past
- Invalid month (>12)
Invalid CVV
- Less than 3 digits
- Non-numeric characters
Missing Name
- Empty field
- Less than 3 characters
Payment Declined Errors
| Error Code | Displayed Message | Action |
|---|---|---|
| PAYMENT_DECLINED | ”Your card was declined. Please try a different payment method.” | Show retry button |
| INSUFFICIENT_FUNDS | ”Insufficient funds. Please use a different card.” | Show retry button |
| CVV_MISMATCH | ”Security code is incorrect. Please check and try again.” | Highlight CVV field |
| EXPIRED_CARD | ”This card has expired. Please use a different card.” | Highlight expiry field |
Customization Options
URL Configuration
{CHECKOUT_SESSION_ID} to include payment intent IDExample:- Customer clicks “Cancel” button
- Payment intent expires
- Maximum attempts reached
Metadata
Pass custom data that appears on receipts and webhooks:- Returned in webhook events
- Visible in payment dashboard
- Searchable for reporting
- Limited to 50 keys, 500 chars per value
Best Practices
Always Verify Server-Side
Always Verify Server-Side
Handle All Redirect Scenarios
Handle All Redirect Scenarios
- Customer clicked “Cancel” button
- Payment declined after max attempts
- Payment intent expired
- Customer abandoned checkout
Use Webhooks for Critical Logic
Use Webhooks for Critical Logic
Create Intent Per Order
Create Intent Per Order
Set Descriptive Descriptions
Set Descriptive Descriptions
- Checkout page header
- Customer bank statement
- Payment receipts
Browser Support
Desktop Browsers
Mobile Browsers
- ES6+ JavaScript
- CSS Grid & Flexbox
- Fetch API
- Web Crypto API (for validation)
FAQ
Can I customize the checkout page design?
Can I customize the checkout page design?
- Custom logo upload
- Brand color selection
- Custom success messages
What happens if a customer closes the browser?
What happens if a customer closes the browser?
- Payment intent remains in
createdstatus - Customer can return to same checkout URL (if not expired)
- Intent auto-expires after 1 hour
- No money is held or charged
Can I collect billing address on checkout?
Can I collect billing address on checkout?
metadata:How do I test without real cards?
How do I test without real cards?
Can customers save cards for future purchases?
Can customers save cards for future purchases?
Troubleshooting
Checkout page shows 'Invalid payment session'
Checkout page shows 'Invalid payment session'
- Payment intent ID in URL doesn’t exist
- Client secret doesn’t match intent
- Intent was created for different merchant
- Verify
checkout_urlfrom payment intent response is used exactly - Don’t modify URL parameters
- Check API key belongs to correct merchant
'This payment session has expired' error
'This payment session has expired' error
- Create new payment intent
- Reduce time between intent creation and checkout redirect
- Consider creating intent when customer clicks “Checkout” button, not when cart is created
Customer redirected but payment status is 'created'
Customer redirected but payment status is 'created'
- Customer clicked browser back button before completing payment
- Payment was declined but customer was redirected to success_url (shouldn’t happen)
- Always verify payment status server-side (see Best Practices)
- Check for
status: 'authorized'orstatus: 'captured'before fulfilling
Test cards not working
Test cards not working
- Using real card number in test mode
- Incorrect expiry format
- Test card not in supported list
- Use exact test card numbers (4242 4242 4242 4242 for success)
- Use any future expiry date (e.g., 12/2027)
- Use any 3-digit CVV
Next Steps
Payment API Reference
Quick Start Guide
Webhooks Guide
CLI Tool
Questions? Contact support at [email protected]