Razorpay integration
You can integrate your Yellow.ai platform with your Razorpay account, enabling you to accept payments from your end users. Additionally, this integration allows you to perform various other actions, including:
- Generate a payment link and receive the status (success/failure) of the payment.
- Generate a payment link to receive partial payments and receive the status (success/failure) of the payments.
- Initiate refund process.
- Check refund status.
- Collect payments inside a WhatsApp conversation using WhatsApp Pay.
- Send order status updates for a WhatsApp Pay order.
1. Connect Razorpay with Yellow.ai
Connect your Yellow.ai platform with your Razorpay account by following the below-mentioned steps.
1.1 Generate API keys on Razorpay dashboard
-
Log into your Razorpay account and select the mode (Test/Live) for which you want to generate the API key.

- Test Mode: The test mode is a simulation mode in which you can test your integration flow. Your customers cannot make payments in this mode. Check out this video to know more.
- Live Mode: When your integration is complete, switch to Live mode and generate live mode API keys. Replace test mode keys with live mode keys in the integration to accept payments from customers.Check out this video to know more.
-
To generate API keys for a specific mode**, navigate to Settings > API Keys > Generate Key to generate key for the selected mode.

-
The Key Id and Key Secret will appear on the following page. Downalod them to use in your Yellow.ai platform.

1.2 Integrate Razorpay with yellow.ai platform
In a two-tier environment, you can connect an integration app in the Development environment. In a three-tier environment, you can connect the integration app either in Staging or Sandbox. All connected integrations are available in the live environment.
To connect your Stripe account with Yellow.ai, follow these steps:
-
Navigate to the Development/Staging environment and go to Extensions > Integrations > Payment > Razorpay. You can also search for Razorpay in the search box.

-
In Give account name, enter a unique name for the integration. You can use only lowercase alphanumeric characters and underscores (_).
-
In Key ID and Key secret, enter the respective values that you downloaded using the steps mentioned in the previous section.
-
CLick Connect.

-
To add another account, click + Add account and proceed with the previous steps. You can add a maximum of 15 accounts.
1.3 Configure webhook URL in Razorpay Dashboard
The Webhook URL serves as a callback URL where Razorpay can send notifications or data updates to your AI agent.
-
Copy the webhook URL and the API key mentioned in the Instructions section of the Razorpay Integration Card. Append the region of your AI agent to the domain of the webhook url. r1/r2/r3/r4/r5 are the regions of your AI agent, you can refer the following list for the same. (r1 = MEA, r2 = Jakarta, r3 = Singapore, r4= USA, r5 = Europe)
For example, if the domain is https://cloud.yellow.ai, you need to change it to https://r1.cloud.yellow.ai if the region of the AI agent is MEA. If the AI agent belongs to India, you can use origin domain itself.
-
Log into the Razorpay Dashboard and navigate to Settings → Webhooks.
-
Click + Add New Webhook on the right corner.

-
In the Webhook Setup pop-up, enter the URL in which you'd like to receive the webhook payload when an event is triggered. We recommend using a HTTPS URL. Ensure you enable all the events shown in the screenshot below.
You can set upto 10 URLs to receive Webhook notifications. Webhooks can only be delivered to public URLs. If you attempt to save a localhost endpoint as part of a webhook setup, you will encounter an error.
- Enter a Secret for the webhook endpoint. This secret will be used to validate whether the webhook is from RazorPay. Do not expose this secret publicly. Click here to know more validating webhooks.
- In the Alert Email field, enter the email address to which the notifications should be sent in case there's a webhook failure.
- Select the required events from the list of Active Events.
- Click Create Webhook. After you set a webhook, it appears on the list of webhooks.
To modify the webhook further, you can select the webhook and click Edit. You can refer this video as well.
Enable Razorpay events in your AI agent
Enable Razorpay events in your AI agent to trigger flows based on event occurrences, allowing seamless integration of payment processes with AI agent functionalities.
- In Development/Staging environment, go to Automation > Event > Integrations.
- Activate the event, Razorpay Payment Status. Click on the more options icon and select Activate. If there are multiple accounts, you need to activate for each account separately.

-
A journey with its trigger point as this event should be created in Automation. Based on the received event data, an appropriate message will be displayed to the end user.
If you have added multiple accounts in your platform, enable events for each of those accounts.
Generate Razorpay payment Link from AI agent conversation
The following are the use-cases that are supported in this integration.
When multiple accounts are added, select the appropriate account for each node, allowing you to leverage the unique functionalities of each account for their intended purposes.
-
Go to Development/Staging environment and navigate to Automation > Build > Select the flow where you want to Generate payment link.
-
Click Add node > Integrations > Razorpay payment gateway. In the Automation flow builder, select the Integrations node and click Razorpay from the list of integrations that have been enabled for that AI agent.
-
In the first drop-down choose Generate Payment Link.
-
Configure all the required fields. The table below contains sample values, data types, and descriptions for these fields.
| Field name | Sample value | Data type | Description |
|---|---|---|---|
| Amount | 100 | String | The amount that should be collected using payment link. This must be in the smallest unit of the currency. For example, if you want to receive a payment of ₹299.95, you must enter the value 29995. |
| Currency | INR | String | Default is INR, we also accept payments in international currencies. |
| Description | Test | String | A brief description of the payment link. |
| IsUPILinkedEnabled | true | Boolean | Indicates if the payment link is a UPI payment link. true: A UPI payment link has been created. false: It is a standard payment link and not a UPI payment link. |
CustomerObject { "contact": "+919999999999", "email": "[email protected]", "name": "Gaurav Kumar" }, | Object | Customer details | |
| Notes | { "policy_name": "Jeevan Bima" } | Object | Set of key-value pairs that can be used to store additional information. You can enter a maximum of 15 key-value pairs, with each value having a maximum limit of 256 characters. |
| NotifyOptions | { "email": true, "sms": true } | object | Defines who handles the payment link notifications. |
| CallbackUrl | https://example-callback-url.com/ | String | if specified it adds a redirect URL to the payment link. Once a customer completes the payment, they will be redirected to the specified URL. |
| CallbackMethod | get | String | If callback_url parameter is passed, callback_method must be passed with the value get. |
| EnableRemindertrue | Boolean | This is used to send reminders for the payment link. Possible values: true: To send reminders. false: To disable reminders. | |
| CustomOptions | Reference details | Object | Custom options |
Sample success response:
{
"accept_partial": false,
"amount": 1000,
"amount_paid": 0,
"callback_method": "get",
"callback_url": "https://example-callback-url.com/",
"cancelled_at": 0,
"created_at": 1591097057,
"currency": "INR",
"customer": {
"contact": "+919999999999",
"name": "Gaurav Kumar"
},
"description": "Payment for policy no #23456",
"expire_by": 1691097057,
"expired_at": 0,
"first_min_partial_amount": 100,
"id": "plink_ExjpAUN3gVHrPJ",
"notes": {
"policy_name": "Jeevan Bima"
},
"notify": {
"email": true,
"sms": true
},
"payments": null,
"reference_id": "TS1989",
"reminder_enable": true,
"reminders": [],
"short_url": "https://rzp.io/i/nxrHnLJ",
"status": "created",
"updated_at": 1591097057,
"user_id": ""
}
Sample response in case of fallback:
{
"error": {
"code": "BAD_REQUEST_ERROR",
"description": "The api key provided is invalid",
"source": "NA",
"step": "NA",
"reason": "NA",
"metadata": {}
}
}
To use this Integration Action Node in an app.yellow.ai AI agent, refer the following example:
app.executeIntegrationAction({
"integrationName": "razorpay",
"action": "Generate Payment Link - Partial Payments”,
"dynamicParams": {
"amount": "500",
"currency": "INR",
"description": "test",
"isUPILinkEnabled": true,
"customerObject": { "name": "GaurarKumar", "contact": "+919999999999", "email": "[email protected]" },
"notes": {
"policy_name": "Jeevan Bima"
},
"notifyOptions": {
"sms": true,
"email": true
},
"callbackUrl": "https://example-callback-url.com/",
"callbackMethod": "get",
"enableReminder": "true",
"customOptions": {
"test":"testing"
}
}
}).then((res) => {
console.log("response from action node", res);
app.log(res, '||Response from action node||')
}).catch((err) => {
console.log("Error in action node", err);
app.log(err, '||Error in action node||')
})
Event payload for Payment status
{
"id": "rfnd_FS8TWyPrCsa0OB",
"entity": "payment",
"amount": 50000,
"currency": "INR",
"payment_id": "pay_FPoJKWQQ8lK13n",
"notes": {
"comment": "Customer Notes for Webhooks."
},
"receipt": null,
"acquirer_data": {
"arn": null
},
"created_at": 1597734071,
"batch_id": null,
"status": "processed",
"speed_processed": "normal",
"speed_requested": "optimum"
}
Generate Payment Link for Partial Payments
-
In the Automation flow builder, select the Integrations node and click Razorpay from the list of integrations that have been enabled for that AI agent.
-
After clicking Razorpay,an Integration Action Node will be added to the flow builder. When you click that node, you will see all use-cases of this integration in a drop-down. Choose Generate Payment Link from them.
-
Fill in all the mandatory fields. The below-mentioned table consists of the sample value,data type and description for all these fields.
| Field name | Sample value | Data type | Description |
|---|---|---|---|
| Text | Text | Text | |
| Amount | 100 | String | The amount that should be the payment link. This must be in the smallest unit of the currency. For example, if you want to receive a payment of ₹299.95, you must enter the value 29995. |
| Currency | INR | String | Default is INR, we also accept payments in international currencies. |
| Description | Test | String | A brief description of the payment link. |
| IsUPILinkedEnabled | true | Boolean | Indicates if the payment link is a UPI payment link. true: A UPI payment link has been created. false: It is a standard payment link and not a UPI payment link. |
| CustomerObject | { "contact": "+919999999999", "email": "[email protected]", "name": "Gaurav Kumar" }, | Object | Customer details |
| Notes | { "policy_name": "Jeevan Bima" } | Object | Set of key-value pairs that can be used to store additional information. You can enter a maximum of 15 key-value pairs, with each value having a maximum limit of 256 characters. |
| NotifyOptions | { "email": true, "sms": true } | object | Defines who handles the payment link notifications. |
| CallbackUrl | https://example-callback-url.com/ | String | if specified it adds a redirect URL to the payment link. Once a customer completes the payment, they will be redirected to the specified URL. |
| CallbackMethod | get | String | If callback_url parameter is passed, callback_method must be passed with the value get. |
| EnableRemindertrue | Boolean | This is used to send reminders for the payment link. Possible values: true: To send reminders. false: To disable reminders. | |
| CustomOptions | Reference details | Object | Custom options |
| isPartialPaymentAccepted | true | Boolean | Indicates whether customers can make partial payments using the payment link. Possible values: true: Customer can make partial payments. false (default): Customer cannot make partial payments. |
Sample response in case of success:
{
"accept_partial": false,
"amount": 1000,
"amount_paid": 0,
"callback_method": "get",
"callback_url": "https://example-callback-url.com/",
"cancelled_at": 0,
"created_at": 1591097057,
"currency": "INR",
"customer": {
"contact": "+919999999999",
"name": "Gaurav Kumar"
},
"description": "Payment for policy no #23456",
"expire_by": 1691097057,
"expired_at": 0,
"first_min_partial_amount": 100,
"id": "plink_ExjpAUN3gVHrPJ",
"notes": {
"policy_name": "Jeevan Bima"
},
"notify": {
"email": true,
"sms": true
},
"payments": null,
"reference_id": "TS1989",
"reminder_enable": true,
"reminders": [],
"short_url": "https://rzp.io/i/nxrHnLJ",
"status": "created",
"updated_at": 1591097057,
"user_id": ""
}
Sample response in case of fallback:
{
"error": {
"code": "BAD_REQUEST_ERROR",
"description": "The api key provided is invalid",
"source": "NA",
"step": "NA",
"reason": "NA",
"metadata": {}
}
}
To use this Integration Action Node in an app.yellow.ai AI agent, refer the following example:
app.executeIntegrationAction({
"integrationName": "razorpay",
"action": "Generate Payment Link",
"dynamicParams": {
"amount": "500",
"isPartialPaymentAccepted":true,
"currency": "INR",
"description": "test",
"isUPILinkEnabled": true,
"customerObject": { "name": "GaurarKumar", "contact": "+919999999999", "email": "[email protected]" },
"notes": {
"policy_name": "Jeevan Bima"
},
"notifyOptions": {
"sms": true,
"email": true
},
"callbackUrl": "https://example-callback-url.com/",
"callbackMethod": "get",
"enableReminder": "true",
"customOptions": {
"test":"testing"
}
}
}).then((res) => {
console.log("response from action node", res);
app.log(res, '||Response from action node||')
}).catch((err) => {
console.log("Error in action node", err);
app.log(err, '||Error in action node||')
})
Intiate refund
-
In the Automation flow builder, select the Integrations node and click Razorpay from the list of integrations that have been enabled for that AI agent.
-
After clicking Razorpay,an Integration Action Node will be added to the flow builder. When you click that node, you will see all use-cases of this integration in a drop-down. Choose Generate Payment Link from them.
-
Fill in all the mandatory fields. The below-mentioned table consists of the sample value,data type and description for all these fields.
| Field Name | Sample value | Data type | Description |
|---|---|---|---|
| Amount | 100 | String | The amount to be refunded (in the smallest unit of currency). For example, refund in INR, a value of 100 means 100 paise (equivalent to ₹1). |
| paymentId | pay_FgR9UMzgmKDJRi | String | The unique identifier of the payment for which a refund is initiated |
| refundType | normal | String | Speed at which the refund should be processed. Possible values: normal: Indicates that the refund will be processed at a normal speed i.e. within 5-7 working days. optimum: Indicates that the refund will be processed at an optimal speed based on Razorpay's internal fund transfer logic. If the refund has to be processed instantly, Razorpay will do so irrespective of the payment method. If an instant refund is not possible, Razorpay will initiate a refund at the normal speed. For example, in case of payments made using debit cards, netbanking or unsupported credit cards. |
| notes | object | Key-value store for storing your reference data. A maximum of 15 key-value pairs can be included. |
- The Generate Payment Link Integration Action Node has two outcomes, success or failure. Based on the success/failure of the execution of the Integration Action Node, the flow will proceed to success or fallback branches respectively.
Success Response:
{
"id": "rfnd_FgRAHdNOM4ZVbO",
"entity": "refund",
"amount": 10000,
"currency": "INR",
"payment_id": "pay_FgR9UMzgmKDJRi",
"notes": {
"notes_key_1": "Beam me up Scotty.",
"notes_key_2": "Engage"
},
"receipt": null,
"acquirer_data": {
"arn": "10000000000000"
},
"created_at": 1600856650,
"batch_id": null,
"status": "processed",
"speed_processed": "normal",
"speed_requested": "normal"
}
To use this Integration Action Node in an app.yellow.ai AI agent, refer the following example:
app.executeIntegrationAction({
"integrationName": "razorpay",
"action": "Generate Payment Link",
"dynamicParams": {
"amount": "500",
"refundType":"normal",
"paymentId":"pay_FgR9UMzgmKDJRi",
"notes": {
"policy_name": "Jeevan Bima"
}
}
}).then((res) => {
console.log("response from action node", res);
app.log(res, '||Response from action node||')
}).catch((err) => {
console.log("Error in action node", err);
app.log(err, '||Error in action node||')
})
Accept payments on WhatsApp (WhatsApp Pay)
Apart from payment links, the Razorpay integration can collect payments inside the WhatsApp conversation using WhatsApp Pay. Instead of sending a URL, the AI agent sends an order details card that lists the items, tax, discount and total. The customer taps Review and pay, completes the payment through Razorpay without leaving WhatsApp, and your flow is notified through the Razorpay Payment Status event. You can then keep the customer updated by pushing an order status card (processing, shipped, completed, and so on) against the same order.
Here, Razorpay acts as the payment gateway configured on your WhatsApp Business Account (WABA), so settlement, refunds and reconciliation continue to happen in your Razorpay account.
WhatsApp Pay is available for India (INR) only. The currency is always sent as INR, so the currency field is not configurable on these nodes.
Prerequisites
Complete all of the following before you use the WhatsApp Pay nodes:
- A WhatsApp Business number is connected to your AI agent, and WhatsApp Pay is enabled on that WABA in WhatsApp Manager.
- Razorpay is added as the payment gateway for that number. Yellow.ai must have the following mapped against the WhatsApp number: the payment configuration name created in WhatsApp Manager, the importer name, the gateway type (
razorpay), and the registered business address (required for WhatsApp Cloud API numbers). This mapping is not self-serve — raise a request with Yellow.ai support. If it is missing, the node fails withpaymentConfigNotFoundorAddress is required. - Razorpay is connected on the platform as described in Connect Razorpay with Yellow.ai, using the Key ID and Key secret of the same Razorpay account that is linked to the payment configuration in WhatsApp Manager. If the accounts differ, the payment succeeds on WhatsApp but the status event never reaches your flow.
- In the Razorpay dashboard webhook, the
payment.capturedandpayment.failedevents are subscribed. WhatsApp Pay does not create a payment link, so thepayment_link.*events are never fired for these payments. - The Razorpay Payment Status event is activated for the account, as described in Enable Razorpay events in your AI agent.
1. Send the order details card
- Go to the Development/Staging environment and navigate to Automation > Build and open the flow in which you want to collect the payment.
- Click Add node > Integrations > Razorpay payment gateway.
- In the action drop-down, choose WhatsApp Pay.
- Configure the fields listed below.
Node fields
| Field name | Sample value | Data type | Required | Description |
|---|---|---|---|---|
| Reference ID | ORD-10093 | String | Yes | Your unique identifier for this order. It is recorded as the transaction ID for the payment and is sent to Razorpay in notes.reference_id, which is how the payment status event is matched back to this conversation. Use a fresh value for every order. |
| Total amount | 1150 | Number | Yes | Amount payable, in rupees. Must be exactly Sub total + Tax - Discount. |
| Message | Please review your order and pay to confirm it. | String | Yes | Body text shown above the order card. |
| From | 919876543210 | String | Yes | The WhatsApp business number connected to the AI agent (country code, no + or spaces). This is the number whose WhatsApp Pay configuration is used. |
| Order details | See Order details | Object | Yes | Items, tax, discount and expiry of the order. |
| Type | physical-goods | String | Yes | Nature of what is being sold. Allowed values: Digital goods (digital-goods) or Physical goods (physical-goods). |
| Receipt | rcpt-10093 | String | Yes | Your receipt number. Passed through to Razorpay as the receipt for the payment, and is useful for reconciliation. |
| Notes | { "policy_name": "Jeevan Bima" } | Object | Yes | Extra key-value pairs stored against the Razorpay payment. Yellow.ai always adds reference_id to this object, so do not send a reference_id key of your own — it is overwritten by the Reference ID field. |
| Vpa name | merchant@upi | String | No | Overrides the payment configuration name mapped to the WhatsApp number. Leave it empty to use the mapped configuration. |
| Image url | https://example.com/product-image.jpg | String | No | Public image URL shown as the header of the order card. |
Unlike Generate Payment Link (which expects the smallest currency unit), every amount on the WhatsApp Pay node is in rupees. The platform converts it to paise before calling WhatsApp. For example, to collect ₹1,150.00 enter 1150, not 115000.
All amount and quantity fields must also be sent as actual numbers. If you map a variable that holds a numeric string (for example "1150"), the request is rejected during validation.
Order details
| Field name | Sample value | Data type | Required | Description |
|---|---|---|---|---|
| Sub total | 1000 | Number | Yes | Sum of all line items, in rupees. Must exactly equal the sum of the Amount (or Sale Amount) of every item. |
| Tax | 180 | Number | Yes | Tax on the order, in rupees. Send 0 if there is no tax. |
| Items | See Items | Array | Yes | The line items shown on the card. |
| Expiration | See Expiration | Object | Yes | How long the card stays payable. |
| Discount | 30 | Number | No | Discount on the order, in rupees. When sent, it is subtracted while validating Total amount. |
| Discount Description | Festive offer | String | No | Text shown against the discount on the card. Applies only when Discount is sent. |
| Discount program name | DIWALI25 | String | No | Name of the discount program shown on the card. Applies only when Discount is sent. |
| Type of payment | payment_gateway:razorpay | String | No | Only for on-premise (biparty) WhatsApp numbers, where it must be set to payment_gateway:razorpay. Leave it empty for WhatsApp Cloud API numbers — the gateway is picked up from the payment configuration. |
Items
Each entry in the Items array describes one line on the order card.
| Field name | Sample value | Data type | Required | Description |
|---|---|---|---|---|
| Item name | Wireless charger | String | Yes | Product name shown on the card. |
| Retailer Id | SKU-4471 | String | Yes | Your SKU or catalogue ID for the product. |
| Amount | 700 | Number | Yes | Amount for this line, in rupees. This is both the price shown against the item and the value added up for the Sub total check. |
| Quantity | 1 | Number | Yes | Number of units shown against the item. It is not multiplied into the sub-total check. |
| Sale Amount | 650 | Number | No | Discounted price for the line. When present, it is shown as the sale price and replaces Amount in the sub-total check. |
Expiration
| Field name | Sample value | Data type | Required | Description |
|---|---|---|---|---|
| Minutes | 30 | Number | Yes | Minutes from now until the card expires. Must be greater than 5. |
| Expiration message | This payment request expires in 30 minutes. | String | Yes | Text shown to the customer when the card has expired. |
- Sum of all items (using Sale Amount when present, otherwise Amount) must equal Sub total, else the node fails with
subTotalAmountMismatch. Quantity is not multiplied in — if you sell more than one unit of an item, make sure the amounts you send still add up to Sub total, for example by listing the units as separate items or by sending the line total as Amount. - Total amount must equal
Sub total + Tax - Discount. When Discount is not sent, it must equalSub total + Tax. Otherwise the node fails withtotalAmountMismatch. - Minutes must be greater than
5, else the node fails withfailedToSetExpirationTime. - A Reference ID can be re-sent only while its order is still unpaid (
pending). Once the order moves to any other status, sending the same Reference ID again fails withsentAlready.
Sample success response:
{
"success": true,
"message": "Success",
"data": {
"referenceId": "ORD-10093",
"status": "pending",
"to": "919999999999",
"number": "919876543210",
"messageId": "wamid.HBgMOTE5OTk5OTk5OTk5FQIAERgS",
"createdDate": "2025-09-02T09:15:22.481Z",
"updatedDate": "2025-09-02T09:15:22.481Z"
}
}
The order is created with status: pending. It is not a confirmation of payment — the payment outcome arrives later through the Razorpay Payment Status event.
Sample response in case of fallback:
{
"success": false,
"message": "Failed",
"data": {
"status": "totalAmountMismatch",
"message": "Sum of tax and subtotal must be equal to total Amount"
}
}
For this node, the request body shown in the node execution logs is the actual payload sent to the WhatsApp Cloud API (interactive.type: order_details), not the node inputs. Use it to confirm the payment configuration, the computed expiry timestamp and the per-item amounts that WhatsApp received. It is logged for failures as well.
To use this Integration Action Node in an app.yellow.ai AI agent, refer the following example:
app.executeIntegrationAction({
"integrationName": "razorpay",
"action": "WhatsApp Pay",
"dynamicParams": {
"referenceId": "ORD-10093",
"from": "919876543210",
"message": "Please review your order and pay to confirm it.",
"type": "physical-goods",
"totalAmount": 1150,
"receipt": "rcpt-10093",
"notes": {
"policy_name": "Jeevan Bima"
},
"imageUrl": "https://example.com/product-image.jpg",
"order": {
"subTotal": 1000,
"tax": 180,
"discount": 30,
"discountDescription": "Festive offer",
"expiration": {
"minutes": 30,
"expirationMessage": "This payment request expires in 30 minutes."
},
"items": [
{
"itemName": "Wireless charger",
"retailerId": "SKU-4471",
"amount": 700,
"quantity": 1
},
{
"itemName": "Braided USB-C cable",
"retailerId": "SKU-4472",
"amount": 300,
"quantity": 1
}
]
}
}
}).then((res) => {
console.log("response from action node", res);
app.log(res, '||Response from action node||')
}).catch((err) => {
console.log("Error in action node", err);
app.log(err, '||Error in action node||')
})
2. Receive the payment status in your flow
When the customer pays, Razorpay sends a webhook to Yellow.ai. The platform reads notes.reference_id from the payload, matches it against the transaction that was recorded when the card was sent, and raises the Razorpay Payment Status event on the same conversation.
| Razorpay event | What it means for the order |
|---|---|
payment.captured | Payment succeeded. The payload status is captured. |
payment.failed | Payment failed. The payload status is failed. |
Build a flow whose trigger is the Razorpay Payment Status event and branch on the payment status to confirm or retry the order. The paths that carry the details you need are:
| Detail | Path in the event payload |
|---|---|
| Your order reference | payload.payment.entity.notes.reference_id |
| Payment status | payload.payment.entity.status |
| Payment method | payload.payment.entity.method |
| Amount paid (in paise) | payload.payment.entity.amount |
Sample event payload (trimmed to the relevant fields):
{
"entity": "event",
"event": "payment.captured",
"contains": ["payment"],
"payload": {
"payment": {
"entity": {
"id": "pay_FPoJKWQQ8lK13n",
"entity": "payment",
"amount": 115000,
"currency": "INR",
"status": "captured",
"method": "upi",
"receipt": "rcpt-10093",
"notes": {
"policy_name": "Jeevan Bima",
"reference_id": "ORD-10093"
}
}
}
},
"created_at": 1597734071
}
If payment.captured is not subscribed in the Razorpay webhook, the customer is charged but your flow never learns about it. Verify this subscription before going live.
3. Update the order status
Once the payment is done, use the Update WhatsApp Pay order status action to send an order status card so the customer can track fulfilment inside the chat. The status you send is also stored against the order on the platform.
- In the flow, click Add node > Integrations > Razorpay payment gateway.
- In the action drop-down, choose Update WhatsApp Pay order status.
- Configure the fields listed below.
| Field name | Sample value | Data type | Required | Description |
|---|---|---|---|---|
| Reference Id | ORD-10093 | String | Yes | The same Reference ID used while sending the order details card. |
| From | 919876543210 | String | Yes | The WhatsApp business number that sent the order card. |
| Card description | Your order has been shipped. | String | Yes | Body text shown on the order status card. |
| Order status details | { "status": "shipped", "description": "Arriving by 5 September" } | Object | Yes | The new status and a short description shown to the customer. |
Order status details accepts the following values for status:
| Option in the drop-down | Value sent | Use it when |
|---|---|---|
| processing | processing | The order is confirmed and being prepared. |
| Partially shipped | partially_shipped | Some of the items have shipped. |
| Shipped | shipped | All items have shipped. |
| Completed | completed | The order is delivered or fulfilled. |
| Cancelled | canceled | The order is cancelled. |
The order must already exist for that Reference Id and From number. If the order details card was never sent (or a different reference is used), the node fails with No Order found for reference Id: <referenceId> and number: <number>.
Sample success response:
{
"success": true,
"message": "Success",
"data": {
"referenceId": "ORD-10093",
"status": "shipped",
"to": "919999999999",
"number": "919876543210",
"messageId": "wamid.HBgMOTE5OTk5OTk5OTk5FQIAERgS",
"createdDate": "2025-09-02T09:15:22.481Z",
"updatedDate": "2025-09-02T11:42:07.309Z"
}
}
To use this Integration Action Node in an app.yellow.ai AI agent, refer the following example:
app.executeIntegrationAction({
"integrationName": "razorpay",
"action": "Update WhatsApp Pay order status",
"dynamicParams": {
"referenceId": "ORD-10093",
"from": "919876543210",
"message": "Your order has been shipped.",
"order": {
"status": "shipped",
"description": "Arriving by 5 September"
}
}
}).then((res) => {
console.log("response from action node", res);
app.log(res, '||Response from action node||')
}).catch((err) => {
console.log("Error in action node", err);
app.log(err, '||Error in action node||')
})
For more details on how these cards behave on WhatsApp, refer to the Meta documentation on the order details message and the order status message.
Troubleshooting WhatsApp Pay
| Status or message | Cause | Fix |
|---|---|---|
paymentConfigNotFound | The WhatsApp number has no payment configuration name or importer name mapped for WhatsApp Pay. | Share the WhatsApp number, payment configuration name and importer name with Yellow.ai support to get the mapping added. |
Address is required | A WhatsApp Cloud API number is missing the business address needed for the importer details. | Get the registered business address added to the number's WhatsApp Pay mapping. |
subTotalAmountMismatch | Sum of the items does not equal Sub total. | Recompute Sub total by adding up the item amounts only — Quantity is not a multiplier, and Sale Amount replaces Amount when it is present. |
totalAmountMismatch | Total amount does not equal Sub total + Tax - Discount. | Recompute Total amount. Send Tax as 0 rather than leaving it empty. |
failedToSetExpirationTime | Minutes is 5 or less. | Set Minutes to a value greater than 5. |
sentAlready | An order with the same Reference ID exists and is no longer pending. | Generate a new Reference ID for every order attempt. |
No Order found for reference Id | Update WhatsApp Pay order status was called with a reference or number that has no order card against it. | Use the same Reference Id and From number that were used to send the card. |
| Validation error on an amount or quantity | A numeric field received a string. | Convert the variable to a number before mapping it to the node. |
| Card is paid but the flow never continues | payment.captured is not subscribed, or the connected Razorpay keys belong to a different account than the payment configuration. | Subscribe payment.captured in the Razorpay webhook and confirm the Key ID/Key secret belong to the same Razorpay account. |