SaySwitch Inline Checkout
Inline Checkout lets you start a payment directly from your frontend website or frontend-only app using only your SaySwitch public key. It works for normal websites built with HTML, CSS, and JavaScript, and also works in frontend frameworks such as React, Vue, Angular, Svelte, and similar tools. It does not require a backend server to initialize the payment.
Never add your secret key to frontend code. Your secret key should not be placed in HTML files, JavaScript files, browser storage, or any code that runs in a customer’s browser.
When to Use Inline Checkout
Use Inline Checkout when:
- You are building with plain HTML, CSS, and JavaScript
- You are building with a frontend framework such as React, Vue, Angular, or Svelte
- You do not have a backend server for payment initialization
- You want customers to click a button and complete payment on the SaySwitch checkout page
Endpoint
POST https://backendapi.sayswitchgroup.com/api/inline/public/transaction/initialize
Authentication
Inline Checkout uses your public key only. You can send the public key in either of these ways:
- In the request body as
public_key - In the request header as
x-pub-key
Do not use your secret key for Inline Checkout requests from a browser.
Required Payload
{
"public_key": "pk_live_xxx",
"reference": "unique_transaction_reference",
"amount": "100.00",
"currency": "NGN",
"email": "customer@example.com",
"name": "Customer Name",
"callback_url": "https://your-domain.com/payment/callback"
}| Parameter | Type | Required | Description |
|---|---|---|---|
| public_key | string | Yes, unless sent as x-pub-key | Your SaySwitch public key |
| reference | string | Yes | Your unique payment reference |
| amount | string | Yes | Amount to charge, for example "100.00" |
| currency | string | Yes | Payment currency, for example NGN |
| string | Yes | Customer’s email address | |
| name | string | Yes | Customer’s name |
| callback_url | string | Yes | URL to redirect the customer to after checkout |
Use callback_url as the callback field name. Do not use callback, redirect_url, or other aliases unless SaySwitch has explicitly confirmed support for them.
Optional Payload
{
"phone": "2348012345678",
"payment_options": ["card", "bank_transfer", "momo"]
}| Parameter | Type | Description |
|---|---|---|
| phone | string | Customer’s phone number |
| payment_options | array | Payment methods to show for this checkout |
Full Native JavaScript Example
Add this to your checkout page. When the customer clicks Pay Now, your website or frontend app creates a payment session and redirects the customer to SaySwitch checkout.
A SaySwitch CDN helper for Inline Checkout is coming soon. For now, use the native JavaScript fetch method shown below.
<script>
async function startPayment() {
const reference = 'SSW_DEMO_' + Date.now();
const response = await fetch('https://backendapi.sayswitchgroup.com/api/inline/public/transaction/initialize', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
public_key: 'pk_live_xxx',
reference: reference,
amount: '100.00',
currency: 'NGN',
email: 'customer@example.com',
name: 'Customer Name',
callback_url: 'https://your-domain.com/payment/callback',
payment_options: ['card', 'bank_transfer']
})
});
const result = await response.json();
if (!result.success) {
alert(result.message || 'Payment could not be initialized');
return;
}
window.location.href = result.data.authorization_url;
}
</script>
<button onclick="startPayment()">Pay Now</button>Replace the sample values with your own values before going live:
| Sample value | Replace with |
|---|---|
pk_live_xxx | Your SaySwitch public key |
customer@example.com | The customer’s email address |
Customer Name | The customer’s name |
"100.00" | The amount you want to charge, sent as a string |
SSW_DEMO_ + Date.now() | Your unique order or payment reference |
https://your-domain.com/payment/callback | Your own callback page URL |
If the customer enters details on your page, you can bind the values from your form fields. Convert the amount to a formatted string before sending it.
<input id="customerName" type="text" placeholder="Customer name" />
<input id="customerEmail" type="email" placeholder="Customer email" />
<input id="paymentAmount" type="number" step="0.01" placeholder="Amount" />
<button onclick="startPayment()">Pay Now</button>
<script>
async function startPayment() {
const name = document.getElementById('customerName').value;
const email = document.getElementById('customerEmail').value;
const amount = Number(document.getElementById('paymentAmount').value).toFixed(2);
const reference = 'SSW_DEMO_' + Date.now();
const response = await fetch('https://backendapi.sayswitchgroup.com/api/inline/public/transaction/initialize', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
public_key: 'pk_live_xxx',
reference: reference,
amount: amount,
currency: 'NGN',
email: email,
name: name,
callback_url: 'https://your-domain.com/payment/callback'
})
});
const result = await response.json();
if (!result.success) {
alert(result.message || 'Payment could not be initialized');
return;
}
window.location.href = result.data.authorization_url;
}
</script>You can also send your public key as a request header:
headers: {
'Content-Type': 'application/json',
'x-pub-key': 'pk_live_xxx'
}Success Response
{
"success": true,
"message": "Authorization URL created",
"data": {
"authorization_url": "https://checkout.sayswitchgroup.com/pay/SSW_DEMO_1789394233792",
"access_code": "ACCESS_CODE",
"reference": "SSW_DEMO_1789394233792",
"payment_options": ["card", "bank_transfer"]
}
}Redirect the customer to data.authorization_url to continue payment on the SaySwitch checkout page. The checkout URL uses this format:
https://checkout.sayswitchgroup.com/pay/{reference}
Validation Errors
If the request is incomplete or uses the wrong data type, SaySwitch returns a failed response with validation details.
Missing Reference
{
"success": false,
"message": "Incomplete request",
"error": {
"reference": ["The reference field is required."]
}
}Amount Sent as a Number
Send amount as a string, for example "100.00". Numeric values are rejected.
{
"success": false,
"message": "Incomplete request",
"error": {
"amount": ["The amount must be a string."]
}
}Invalid Public Key
{
"success": false,
"message": "Invalid public key"
}Duplicate Reference
{
"success": false,
"message": "Transaction reference already exists"
}Unsupported Currency
{
"success": false,
"message": "Unsupported currency"
}Invalid Callback URL
{
"success": false,
"message": "The callback URL must be a valid http or https URL"
}Handling the Callback Redirect
After payment, SaySwitch redirects the customer back to the callback_url you supplied during initialization. The redirect can include query parameters such as:
?reference=REFERENCE&status=successUse the callback query parameters to identify the payment and show the customer that payment processing has returned to your website.
<!DOCTYPE html>
<html>
<head>
<title>Payment Status</title>
</head>
<body>
<h2>Checking payment status...</h2>
<p id="status"></p>
<script>
const params = new URLSearchParams(window.location.search);
const reference = params.get('reference');
const status = params.get('status');
const statusBox = document.getElementById('status');
if (reference) {
statusBox.innerText = 'Payment returned with status: ' + status + '. Reference: ' + reference;
} else {
statusBox.innerText = 'Payment returned. Please confirm your transaction status.';
}
</script>
</body>
</html>The exact callback query parameters depend on the checkout response. Always use the reference to identify the payment.
Verify the Transaction
Do not rely only on the callback query parameters for final confirmation. After receiving the callback, verify the transaction by reference before showing final success or failure to the customer.
Use the Get Transaction by Reference documentation to confirm the transaction status with the reference returned from Inline Checkout.
The verification endpoint uses your secret key, so do not call it directly from frontend code. If you have a backend, verify the transaction from your backend. If you are running a frontend-only setup, confirm the transaction from your SaySwitch dashboard before fulfilling the order.
Important Notes
- Always use a unique
referencefor every payment. - Send
amountas a string, for example"100.00". - Use your test public key for test payments and your live public key for live payments.
- Do not expose secret keys in frontend code.
- Use
callback_urlas the callback field name. - The callback URL must be a valid
httporhttpsURL. - Verify the transaction by reference before fulfilling the order.
Payment Flow
- Customer clicks Pay Now on your website.
- Your frontend calls the Inline Checkout initialize endpoint with a unique
reference. - SaySwitch returns
data.authorization_url. - Customer is redirected to
https://checkout.sayswitchgroup.com/pay/{reference}. - Customer completes payment.
- SaySwitch redirects the customer back to your
callback_urlwith query parameters such asreferenceandstatus. - You verify the transaction by reference.
- After verification, you show the final payment status to the customer and fulfill the order if payment was successful.