An internal direct debit moves funds between balance accounts within your platform. For example, to collect monthly or subscription fees from your users without triggering strong customer authentication (SCA) or payment fees, you can initiate an internal debit, where your liable balance account send a debit request to your user's balance account. As a platform, you can also initiate internal direct debits between the balance accounts of two different users.
Before you begin
- Make sure that your server can receive and accept webhooks, and that you subscribed to the Transfer webhooks in your Customer Area.
- Ask our Support Team to enable transfers for the balance account that debits funds.
- Make sure that your account holders have the following capabilities:
- The account holder of the balance account that initiates the direct debit must have the sendToBalanceAccount capability.
- The account holder of the balance account that received the request must have the receiveFromBalanceAccount capability.
Initiate an internal direct debit
To initiate an internal direct debit, make a POST /transfers request.
In the body of the request, include the following fields:
Parameter | Required | Description |
---|---|---|
amount | An object containing the currency and value of the transfer. | |
balanceAccountId | The unique identifier of the source balance account: the balance account that initiates the direct debit. | |
counterparty.balanceAccountId | The unique identifier of the target balance account: the balance account that receives the debit request. | |
category | Set to internal. | |
type | Set to internalDirectDebit to debit the funds from the counterparty balance account. | |
description | Your description of the transfer. You can use this to identify the transfer in the webhooks that you receive. | |
reference | Your unique reference for the transfer. You can use this to identify the transfer in the webhooks that you receive. | |
referenceForBeneficiary | Text to inform the recipient about the push or pull transfer. This reference is also included in all webhooks. Supported characters: a-z, A-Z, 0-9. |
The following example shows how to pull USD 25 from your user's balance account to your liable balance account.
In the response, note the following:
id
: the unique ID of the transfer.status
: the result of the transfer.reason
: an explanation of the status. Check this field if the status is not authorised.
For example, the reason for a refused status can be notEnoughBalance.
Get status updates
For every internal transfer request, Adyen sends multiple webhooks to your server: a series of webhooks for the balance account where the transfer is an outgoing request, and a series of webhooks for the balance account where the transfer is an incoming request.
Using these webhooks, you can track the status of the transfer: received, then authorised, and finally booked. The webhooks also inform you if the transfer failed.
You can also view the transfer details in your Customer Area. Each transfer of funds between balance accounts appears in the Customer Area as two transfer entries: one for the balance account that is credited, and one for the balance account that is debited.
When you initiate an internal direct debit is triggered between balance accounts in your platform, Adyen sends two kinds of webhooks:
- balancePlatform.transfer.created, that informs your server that funds will be transferred between the balance accounts.
- balancePlatform.transfer.updated, that informs your server of changes in the status of the fund transfer.
For each event you receive two sets of webhooks:
- Webhooks for the source balance account, where you initiate the direct debit an outgoing request.
- Webhooks for the target balance account, that received the direct debit as an incoming request.
You can identify transfer webhooks triggered by internal direct debit requests by the following values:
Parameter | Description | Value |
---|---|---|
category | The category of the transfer. | internal |
direction | The direction of the transfer request. | outgoing for the source balance account incoming for the target balance account |
type | The type of internal transfer. | internalDirectDebit |
For an internal direct debit, you receive webhooks for the following events:
- The transfer is initiated.
- The transfer is authorized. This indicates that the funds are reserved.
- The transfer is booked.
Expand the sections below to see the webhooks you would receive for the example direct debit request above.
1. Internal direct debit initiated
When you initiate an internal direct debit, we send you a balancePlatform.transfer.created webhook with status
received, to inform your server that funds will be transferred between balance accounts in your platform.
2. Internal direct debit authorized
When the scheduled or on-demand internal pull transfer is authorized, Adyen sends balancePlatform.transfer.updated webhooks with status
authorised, to inform your server that the funds have been reserved on the source and target balance accounts.
3. Internal direct debit booked
When the scheduled or on-demand internal pull transfer is booked, Adyen sends balancePlatform.transfer.updated webhooks with status
booked, to inform your server that the funds have been pulled from the target balance account to the source balance account.