Skip to main content
POST
/
v1
/
webhooks
Create Webhook
curl --request POST \
  --url https://webhooks.sbx.moduluslabs.io/v1/webhooks \
  --header 'Authorization: Basic <encoded-value>' \
  --header 'Content-Type: application/json' \
  --data '
{
  "webhookAction": "QRPH_SUCCESS",
  "callbackUrl": "https://api.yourcompany.com/webhooks/success"
}
'
{
  "id": "a78efd32-de3b-4854-b599-11ae9f98f97e",
  "webhookAction": "QRPH_SUCCESS",
  "webhookStatus": "ENABLED",
  "callbackUrl": "https://api.yourcompany.com/webhooks/success"
}

Overview

The Create Webhook endpoint allows you to register a new webhook URL that will receive real-time notifications when QR Ph transactions complete. You can specify which transaction events (success or declined) to receive and enable or disable the webhook immediately.
Webhooks are required for QR Ph integration. Without a registered webhook, you cannot receive transaction status updates, which poses significant security risks.

Endpoint

POST https://webhooks.sbx.moduluslabs.io/v1/webhooks

Authentication

This endpoint requires HTTP Basic Authentication using your Secret Key.
Authorization: Basic {base64(secret_key:)}

Request

Headers

HeaderValueRequiredDescription
AuthorizationBasic {base64(secret_key:)}YesHTTP Basic Auth with your secret key
Content-Typeapplication/jsonYesRequest body format
activation-codestringNoMerchant activation code for multi-merchant setups
activation-code
string
Optional activation code to identify which merchant this webhook belongs to. Used for multi-merchant environments where a single platform manages webhooks for multiple merchants.Example: "MERCHANT_ABC_123"When you create a webhook with an activation code, Modulus Labs includes the same activation-code in the header of webhook notifications sent to your endpoint.

Prerequisites

Before creating a webhook, ensure you have:
  • Your Secret Key for HTTP Basic Authentication
See the Encryption Guide to understand how JWE tokens work — you’ll need this to decrypt incoming webhook notifications sent to your endpoint.

Request Payload

The request body must contain a JWE-encrypted token that includes your webhook configuration:
{
  "request": {
    "Token": "eyJhbGciOiJBMjU2S1ciLCJlbmMiOiJBMjU2Q0JDLUhTNTEyIn0."
  }
}

Body Parameters

callbackUrl
string
required
The HTTPS URL where Modulus Labs will send webhook notifications. Must be publicly accessible and use HTTPS.Format: Valid HTTPS URLExample: "https://api.yourcompany.com/webhooks/modulus"Requirements:
  • Must use HTTPS protocol (HTTP not supported in production)
  • Must be publicly accessible from the internet
  • Must respond within 10 seconds
  • Should return 200 OK to acknowledge receipt
webhookAction
string
required
String of webhook actions you want to receive notifications for. Include one or both values:
  • QRPH_SUCCESS - Receive notifications when payments succeed
  • QRPH_DECLINED - Receive notifications when payments are declined
Example: "QRPH_SUCCESS" "QRPH_DECLINED"
We recommend including both actions. Handling declined payments allows you to provide better customer support and offer alternative payment methods.

Request Example

{
  "webhookAction": "QRPH_SUCCESS",
  "callbackUrl": "https://api.yourcompany.com/webhooks/success"
}

Response

Success Response

Status Code: 201 Created Returns the created webhook object with a unique id that you can use to update or delete the webhook later.
id
integer
Unique identifier for the webhook. Save this value - you’ll need it to update or delete the webhook.Example: a78efd32-de3b-4854-b599-11ae9f98f97e
webhookAction
string
String of webhook actions this endpoint will receive.Example: "QRPH_SUCCESS" "QRPH_DECLINED"
webhookStatus
string
Current webhook status: ENABLED or DISABLEDExample: "ENABLED"
callbackUrl
string
The webhook URL you registered.Example: "https://api.yourcompany.com/webhooks/modulus"

Response Example

{
  "id": "a78efd32-de3b-4854-b599-11ae9f98f97e",
  "webhookAction": "QRPH_SUCCESS",
  "webhookStatus": "ENABLED",
  "callbackUrl": "https://api.yourcompany.com/webhooks/success"
}
{
  "id": "a78efd32-de3b-4854-b599-11ae9f98f97e",
  "webhookAction": "QRPH_SUCCESS",
  "webhookStatus": "ENABLED",
  "callbackUrl": "https://api.yourcompany.com/webhooks/success"
}
Save the webhook ID! You’ll need the id value to update or delete this webhook using the Update or Delete endpoints.

Error Responses

Status Code: 400Causes:
  • Invalid webhook URL format
  • Missing required fields
  • Invalid action values
  • Invalid status value
Response Example:
{
  "code": "20000002",
  "error": "Invalid callbackUrl: must be a valid HTTPS URL",
  "referenceNumber": "abc123-def456-ghi789"
}
Solutions:
  • Ensure callbackUrl uses HTTPS protocol
  • Verify all required fields are present
  • Check that actions contain valid values (QRPH_SUCCESS, QRPH_DECLINED)
  • Ensure status is either ENABLED or DISABLED
Status Code: 401Cause: Invalid or missing authentication credentialsSolution:
  • Verify your secret key is correct
  • Ensure Authorization header format: Basic {base64(secret_key:)}
  • Check you’re using the right environment (sandbox vs production)
Status Code: 409Cause: Webhook URL already registered for this merchantResponse Example:
{
  "code": "20000003",
  "error": "Webhook URL already exists",
  "referenceNumber": "abc123-def456-ghi789"
}
Solution:
  • Use a different webhook URL, or
  • Update the existing webhook using Update Webhook API, or
  • Delete the existing webhook and create a new one
Status Code: 500Cause: Unexpected server errorSolution:
  • Retry the request
  • If the issue persists, contact Modulus Labs support with the reference number

Code Examples

curl -X POST https://webhooks.sbx.moduluslabs.io/v1/webhooks \
  -u sk_your_secret_key: \
  -H "Content-Type: application/json" \
  -d '{
  "webhookAction": "QRPH_SUCCESS",
  "callbackUrl": "https://api.yourcompany.com/webhooks/success"
}'

Multi-Merchant Setup

If you manage multiple merchants, use the activation-code header to associate the webhook with a specific merchant:
curl -X POST https://webhooks.sbx.moduluslabs.io/v1/webhooks \
  -u sk_your_secret_key: \
  -H "Content-Type: application/json" \
  -H "activation-code: MERCHANT_ABC_123" \
  -d '{
    "webhookAction": "QRPH_SUCCESS",
    "callbackUrlUrl": "https://api.yourcompany.com/webhooks/modulus"
  }'
When Modulus Labs sends webhook notifications for this merchant, the activation-code header will be included in the request:
app.post('/webhooks/modulus', (req, res) => {
  const activationCode = req.headers['activation-code'];
  // "MERCHANT_ABC_123"

  // Route to appropriate merchant handler
  const merchant = getMerchantByActivationCode(activationCode);
  processWebhook(merchant, req.body);
});

Use Cases

Register a webhook to receive payment notifications for online orders:
const webhook = await createWebhook({
  callbackUrl: 'https://shop.example.com/api/payments/webhook',
  webhookAction: 'QRPH_SUCCESS',
  status: 'ENABLED'
});

// Webhook will notify you instantly when customers complete QR Ph payments
Register a webhook for in-store point-of-sale transactions:
const webhook = await createWebhook({
  callbackUrl: 'https://pos.example.com/webhooks/payment',
  webhookAction: ['QRPH_SUCCESS'],  // Only success events for POS
  status: 'ENABLED'
});
Create a disabled webhook during development, enable it when ready:
// Create disabled webhook for testing
const webhook = await createWebhook({
  callbackUrl: 'https://dev.example.com/webhooks/test',
  webhookAction: 'QRPH_SUCCESS',
  status: 'DISABLED'  // Won't receive notifications yet
});

// Enable later using Update Webhook API
await updateWebhook(webhook.id, { status: 'ENABLED' });

Best Practices

Use HTTPS Only

Always use HTTPS URLs for webhooks. HTTP is insecure and not supported in production.

Save Webhook ID

Store the returned id in your database. You’ll need it to update or delete the webhook.

Test Before Enabling

Create webhooks with DISABLED status during development. Test with the Simulate API before enabling.

Include Both Actions

Register for both QRPH_SUCCESS and QRPH_DECLINED to handle all transaction outcomes.

Unique URLs per Environment

Use different webhook URLs for sandbox and production to avoid mixing test and live data.

Verify Connectivity First

Test your webhook endpoint is accessible before registering it with the API.

Validation Checklist

Before creating a webhook, verify:
1

Webhook Endpoint is Ready

  • Endpoint accepts POST requests
  • Endpoint responds within 10 seconds
  • Endpoint can decrypt JWE payloads
  • Endpoint implements idempotency
2

URL is Accessible

  • URL uses HTTPS protocol
  • URL is publicly accessible from the internet
  • Firewall allows incoming requests
  • SSL certificate is valid
3

Authentication is Configured

  • Secret key is correct
  • Authorization header format is valid
  • Using correct environment (sandbox vs production)
4

Configuration is Correct

  • Webhook URL is a valid HTTPS URL
  • Actions include at least one valid value
  • Status is either ENABLED or DISABLED

What Happens Next?

After creating a webhook:
1

Webhook is Registered

Modulus Labs saves your webhook configuration and begins monitoring for transaction events.
2

Transactions Trigger Notifications

When QR Ph transactions complete, Modulus Labs sends encrypted webhook notifications to your URL.
3

Automatic Retries

If your endpoint doesn’t respond with 200 OK, Modulus Labs automatically retries up to 3 more times at 15-minute intervals.
4

You Process Webhooks

Your endpoint decrypts payloads, updates order status, and fulfills transactions in real-time.

Next Steps

Authorizations

Authorization
string
header
required

HTTP Basic Authentication using your Secret Key as the username and an empty password

Headers

activation-code
string

Optional activation code to identify which merchant this webhook belongs to. Used for multi-merchant environments.

Body

application/json
webhookAction
enum<string>
required

Webhook action to receive notifications for

Available options:
QRPH_SUCCESS,
QRPH_DECLINED
callbackUrl
string<uri>
required

The HTTPS URL where Modulus Labs will send webhook notifications. Must be publicly accessible and use HTTPS.

Response

Webhook created successfully

id
string

Unique identifier for the webhook

webhookAction
enum<string>[]

List of transaction events this webhook receives

Available options:
QRPH_SUCCESS,
QRPH_DECLINED
webhookStatus
enum<string>

Current status of the webhook

Available options:
ENABLED,
DISABLED
webhookUrl
string<uri>

The HTTPS URL where notifications are sent