Pay by Bank (also known as Account to Account or A2A) is a bank transfer payment method. Trust Payments provides Pay by Bank with a processing partner authorised by the financial regulators in the UK and EEA (European Economic Area). When opting to pay with Pay by Bank on your checkout, customers will be redirected to a page hosted by our processing partner, which will prompt them to select their bank. The bank will determine the next steps undertaken by the customer to authorise the payment, but typically the customer will be asked to perform some form of SCA (Strong Customer Authentication), e.g. reviewing and approving the order using a banking app installed on their device. Once they agree to the payment, the customer will finally be redirected back to your website.
Supported customer countries | GB |
Supported currencies | GBP |
Refunds |
Not supported. |
Chargebacks | Payments are not subject to chargebacks. |
Zero-authorisation |
Not supported. |
Recurring payments |
Not supported. |
Configuration
To enable Pay by Bank on your account, please get in touch with your Account Manager.
A test sandbox account will be provided, which you will need when testing your implementation.
We recommend displaying this payment method as "Pay by Bank" on your checkout, as feedback we have received suggests customers are more familiar with this term.
Process overview
-
Initiate the customer
- Customer agrees to a payment using Pay by Bank on the merchant’s website.
- Merchant submits AUTH request to initiate the session, including the returnurl.
- Merchant receives AUTH response, including redirecturl.
-
Redirect to bank login page
- Merchant redirects the customer’s browser to the redirecturl. This is a page hosted by a Trust Payments processing partner, which prompts the customer to select their bank.
- Customer's browser is then redirected to pages hosted by their selected bank, where the customer will be prompted to sign in and review order details.
- If the customer agrees to the payment and the checkout process is successful, their browser is finally redirected to the returnurl, a page hosted by the merchant.
-
Verify the result
- You will then need to process a TRANSACTIONQUERY and check the data included in the response aligns with that submitted in the original AUTH request.
- This is to ensure the data included on the redirect back to the returnurl has not been modified in transit.
-
Payment completion
- Following the TRANSACTIONQUERY, you can determine that the transaction is normally in one of two states, as indicated by the settlestatus:
- 100 ("Settled") - Transaction was authorised and funds have left the customer's account and will be settled into the merchant's bank account in a timeframe determined by the terms agreed with Trust Payments during the onboarding process.
- 3 ("Cancelled") - Transaction was cancelled.
- But there is another case where the transaction is in settlestatus 10 ("Pending"). This means the transaction hasn't yet completed. Typically this resolves to either 100 ("Settled") or 3 ("Cancelled") within a few minutes, although this can take longer.
- Once the above has been completed, you can then display an appropriate message in the customer's browser (e.g. success/error).
- Following the TRANSACTIONQUERY, you can determine that the transaction is normally in one of two states, as indicated by the settlestatus:
1. Initiate the customer
When the customer chooses to pay with Pay by Bank, your system will need to perform an AUTH request and, if successful, redirect the customer’s browser to the URL returned in the response.
Later in this article, we provide recommendations on how to present Pay by Bank on your checkout and tips for improving customer engagement. Click here to scroll there.
AUTH request
The example request below is for a Pay by Bank AUTH request:
#!/usr/bin/python
import securetrading
stconfig = securetrading.Config()
stconfig.username = "webservices@example.com"
stconfig.password = "Password1^"
st = securetrading.Api(stconfig)
auth = {
"requesttypedescription": "AUTH",
"sitereference": "test_site12345",
"accounttypedescription": "ECOM",
"returnurl": "https://www.example.com/success",
"baseamount": "1050",
"currencyiso3a": "EUR",
"paymenttypedescription": "ATA"
}
strequest = securetrading.Request()
strequest.update(auth)
stresponse = st.process(strequest) #stresponse contains the transaction response
<?php
if (!($autoload = realpath(__DIR__ . '/../../../autoload.php')) && !($autoload = realpath(__DIR__ . '/../vendor/autoload.php'))) {
throw new Exception('Composer autoloader file could not be found.');
}
require_once($autoload);
$configData = array(
'username' => 'webservices@example.com',
'password' => 'Password1^'
);
$requestData = array(
'requesttypedescription' => 'AUTH',
'sitereference' => 'test_site12345',
'accounttypedescription' => 'ECOM',
'returnurl' => 'https://www.example.com/success',
'baseamount' => '1050',
'currencyiso3a' => 'EUR',
'paymenttypedescription' => 'ATA'
);
$api = \Securetrading\api($configData);
$response = $api->process($requestData);
var_dump($response->toArray());
?>
curl --user webservices@example.com:Password1^ <DOMAIN>/json/ -H "Content-type: application/json" -H "Accept: application/json" -X POST -d '{
"alias": "webservices@example.com",
"version": "1.00",
"request": [{
"requesttypedescription": "AUTH",
"sitereference": "test_site12345",
"accounttypedescription": "ECOM",
"returnurl": "https://www.example.com/success",
"baseamount": "1050",
"currencyiso3a": "EUR",
"paymenttypedescription": "ATA"
}]
}'
{
"alias":"webservices@example.com",
"version":"1.00",
"request":[{
"requesttypedescription":"AUTH",
"sitereference":"test_site12345",
"accounttypedescription":"ECOM",
"returnurl":"https://www.example.com/success",
"baseamount":"1050",
"currencyiso3a":"EUR",
"paymenttypedescription":"ATA"
}]
}
<requestblock version="3.67" >
<alias>webservices@example.com</alias>
<request type="AUTH">
<operation>
<sitereference>test_site12345</sitereference>
<accounttypedescription>ECOM</accounttypedescription>
</operation>
<merchant>
<returnurl>https://www.example.com/success</returnurl>
</merchant>
<billing>
<amount currencycode="EUR">1050</amount>
<payment type="ATA"/>
</billing>
</request>
</requestblock>
Replace <DOMAIN>
with a supported domain. Click here for a full list.
Field specification
Field | Format | Description | |
accounttypedescription XPath: /operation/accounttypedescription |
Alpha (20) | Only “ECOM” (e-commerce) is supported. | |
baseamount XPath: /billing/amount |
Numeric (13) | The amount of the transaction in base units, with no commas or decimal points, so €10 is submitted as 1000. This value must be greater than zero. (Max length may vary depending on your acquiring bank – Contact your bank for further info) | |
currencyiso3a XPath: /billing/amount/@currencycode |
Alpha (3) |
The currency that the transaction will be processed in (in ISO3A format). For a list of currency codes supported by Pay by Bank, refer to the list found at the top of this page. |
|
paymenttypedescription XPath: /billing/payment/@type |
Alpha (20) | This value must be submitted as “ATA”. | |
requesttypedescription XPath: /@type |
Alpha (20) | The value in the request must be “AUTH”. | |
returnurl XPath: /merchant/returnurl |
URL (2048) | The URL that the customer will be returned to following a successful authorisation. | |
sitereference XPath: /operation/sitereference |
Alphanumeric & underscore (50) |
The site reference relates to your individual account which you received on setup. If you do not know your site reference, please contact our Support Team. | |
orderreference XPath: /merchant/orderreference |
Alphanumeric including symbols (25)
Recommended length 25 characters or less (exact length dependent on acquiring bank). Failure to adhere to this requirement may result in the text being truncated in the transaction. |
Your unique order reference that can be stored on the Trust Payments system. |
AUTH response
{
u'requestreference': u'An3ug1kap',
u'version': u'1.00',
u'responses': [{
u'requesttypedescription': u'AUTH',
u'baseamount': u'1050',
u'currencyiso3a': u'EUR',
u'paymenttypedescription': u'ATA',
u'errorcode': u'0',
u'errormessage': u'Ok',
u'livestatus': u'0',
u'merchantcountryiso2a': u'GB',
u'merchantname': u'Test Merchant',
u'operatorname': u'webservices@example.com',
u'accounttypedescription': u'ECOM',
u'redirecturl': u'https://web-app.sandbox.token.io/app/request-token/rq:xxx:yyy',
u'settleduedate': u'2022-02-09',
u'settlestatus': u'10',
u'transactionstartedtimestamp': u'2022-02-09 15:43:49',
u'transactionreference': u'1-2-345'
}]
}
array(3) {
["requestreference"] => string(9) "A0345jmuw"
["version"] => string(4) "1.00"
["responses"] => array(1) {
[0] => array(16) {
["requesttypedescription"] => string(4) "AUTH"
["baseamount"] => string(4) "1050"
["currencyiso3a"] => string(3) "EUR"
["paymenttypedescription"] => string(3) "ATA"
["errorcode"] => string(1) "0"
["errormessage"] => string(2) "Ok"
["livestatus"] => string(1) "0"
["merchantcountryiso2a"] => string(2) "GB"
["merchantname"] => string(13) "Test Merchant"
["operatorname"] => string(23) "webservices@example.com"
["accounttypedescription"] => string(4) "ECOM"
["redirecturl"] => string(61) "https://web-app.sandbox.token.io/app/request-token/rq:xxx:yyy"
["settleduedate"] => string(10) "2022-02-09"
["settlestatus"] => string(2) "10"
["transactionstartedtimestamp"] => string(20) "2022-02-09 15:43:49"
["transactionreference"] => string(7) "1-2-345"
}
}
}
{
"requestreference":"W23-fjgvn3d9",
"version":"1.00",
"response":[{
"requesttypedescription":"AUTH",
"baseamount":"1050",
"currencyiso3a":"EUR",
"paymenttypedescription":"ATA",
"errorcode":"0",
"errormessage":"Ok",
"livestatus":"0",
"merchantcountryiso2a":"GB",
"merchantname":"Test Merchant",
"operatorname":"webservices@example.com",
"accounttypedescription":"ECOM",
"redirecturl":"https://web-app.sandbox.token.io/app/request-token/rq:xxx:yyy",
"settleduedate":"2022-02-09",
"settlestatus":"10",
"transactionstartedtimestamp":"2022-02-09 15:43:49",
"transactionreference":"1-2-345"
}]
}
<responseblock version="3.67">
<requestreference>Xjhr1mcce</requestreference>
<response type="AUTH">
<billing>
<amount currencycode="EUR">1050</amount>
<payment type="ATA"/>
</billing>
<error>
<code>0</code>
<message>Ok</message>
</error>
<live>0</live>
<merchant>
<merchantcountryiso2a>GB</merchantcountryiso2a>
<merchantname>Test Merchant</merchantname>
<operatorname>webservices@example.com</operatorname>
</merchant>
<operation>
<accounttypedescription>ECOM</accounttypedescription>
</operation>
<other>
<redirecturl>https://web-app.sandbox.token.io/app/request-token/rq:xxx:yyy</redirecturl>
</other>
<settlement>
<settleduedate>2022-02-09</settleduedate>
<settlestatus>10</settlestatus>
</settlement>
<timestamp>2022-02-09 15:43:49</timestamp>
<transactionreference>1-2-345</transactionreference>
</response>
<secrand>WK</secrand>
</responseblock>
Field specification
Field | Format | Description | |
accounttypedescription XPath: /operation/accounttypedescription |
Alpha (20) | The value returned is “ECOM”. | |
baseamount XPath: /billing/amount |
Numeric (13) | The amount of the transaction in base units, with no commas or decimal points, so €10 is returned as 1000. | |
currencyiso3a XPath: /billing/amount/@currencycode |
Alpha (3) |
The currency that the transaction was processed in (in ISO3A format). For a list of currency codes supported by Pay by Bank, refer to the list found at the top of this page. |
|
errorcode XPath: /error/code |
Numeric (1-5) |
The error code should be used to determine if the request was successful or not.
|
|
errormessage XPath: /error/message |
Alphanumeric (255) | This is the corresponding message to the above code. | |
livestatus XPath: /live |
Numeric (1) |
|
|
operatorname XPath: /merchant/operatorname |
Alphanumeric (255) | The value of this field contains the name of the user that processed the request. | |
paymenttypedescription XPath: /billing/payment/@type |
Alpha (20) | This value returned is “ATA”. | |
redirecturl XPath: /other/redirecturl |
URL (255) | Redirect the customer’s browser to this URL, which is hosted by a Trust Payments processing partner, to allow the customer to complete the payment. | |
requesttypedescription XPath: /@type |
Alpha (20) | The value returned is “AUTH”. | |
settleduedate XPath: /settlement/settleduedate |
Date YYYY-MM-DD | The date on which the transaction will be settled. | |
settlestatus XPath: /settlement/settlestatus |
Numeric (3) | This allows you to determine the status of the payment. Refer to the Handling the response section below for information on how to best interpret this field. | |
transactionreference XPath: /transactionreference |
Alphanumeric including hyphens (25) |
A unique reference for the transaction assigned by Trust Payments. | |
transactionstartedtimestamp XPath: /timestamp |
Date time YYYY-MM-DD hh:mm:ss | The time the transaction was processed. | |
errordata XPath: /error/data |
Alphanumeric (255) |
Additional information to help troubleshoot the error. Only returned if there has been an error. |
|
merchantcountryiso2a |
Alpha (2) |
These are details associated with the account used to process the transaction. To amend these fields, please contact our Support Team. Values returned depends on your account configuration.
|
|
merchantname XPath: /merchant/merchantname |
Alphanumeric (255) |
Handling the response
The settlestatus returned in the AUTH response is used to determine the status of the Pay by Bank payment:
If the settlestatus is “10”, the payment is pending settlement
- The funds have not yet been settled into your bank account.
- The next step is to redirect the customer’s browser to the redirecturl to complete the payment.
Funds will not be settled into your account until the customer is redirected to the redirecturl, in order to complete the payment. Read on for further information.
If the settlestatus is “3”, the payment has been cancelled
- The payment has been declined, or has encountered an error.
- To learn more about why the payment was unsuccessful, you will need to look at the errorcode. e.g. “70000” indicates that the payment was declined. Click here for a full list of error codes.
In addition to the above, we also recommend performing additional checks following payment.
2. Redirect to bank login page
Your system will need to redirect the customer’s browser to the redirecturl, which is a page hosted by a Trust Payments processing partner, in order to process the payment.
As part of this, the customer will be further redirected to pages hosted by their bank, where they will be prompted to sign in to their account and authorise the transaction.
Do not display the redirecturl within an iframe. This will prevent the content from being rendered correctly, and can ultimately prevent the payment from being completed successfully.
When testing, you will be displayed the sandbox environment. To complete a test transaction, you will need to follow the instructions displayed on screen. Please contact your account manager for test credentials to enter while on the sandbox.
At a later time, the customer will be redirected back to the returnurl provided in the AUTH request. Your system will be returned a GET request containing the fields described below:
Field | Format | Description | |
orderreference | Alphanumeric including symbols (25) |
Your unique order reference stored on the Trust Payments system. This field is returned blank if omitted from the AUTH request. |
|
settlestatus | Numeric (3) |
A numeric value used to indicate the progress of settlement regarding this transaction. You will need to verify this by performing a TRANSACTIONQUERY request as described below. |
|
transactionreference | Alphanumeric including hyphens (25) |
Unique reference of the transaction, available after a payment request has been processed. You will need to use this in a subsequent TRANSACTIONQUERY request with our Webservices API to establish the current state of the payment, as described below. |
3. Verify the result
At this stage in the process, the customer will have been redirected to the returnurl and your server will need to verify the result by sending a TRANSACTIONQUERY request, as shown in the example below:
Request example
#!/usr/bin/python
import securetrading
stconfig = securetrading.Config()
stconfig.username = "webservices@example.com"
stconfig.password = "Password1^"
st = securetrading.Api(stconfig)
query = {
"requesttypedescriptions": ["TRANSACTIONQUERY"],
"filter":{
"sitereference": [{"value":"test_site12345"}],
"transactionreference": [{"value":"55-9-12345"}]
}
}
strequest = securetrading.Request()
strequest.update(query)
stresponse = st.process(strequest) #stresponse contains the transaction response
<?php
if (!($autoload = realpath(__DIR__ . '/../../../autoload.php')) && !($autoload = realpath(__DIR__ . '/../vendor/autoload.php'))) {
throw new Exception('Composer autoloader file could not be found.');
}
require_once($autoload);
$configData = array(
'username' => 'webservices@example.com',
'password' => 'Password1^',
);
$requestData = array(
'requesttypedescriptions' => array('TRANSACTIONQUERY'),
'filter' => array(
'sitereference' => array(array('value' => 'test_site12345')),
'transactionreference' => array(array('value' => '55-9-12345'))
)
);
$api = \Securetrading\api($configData);
$response = $api->process($requestData);
var_dump($response->toArray());
?>
curl --user webservices@example.com:Password1^ <DOMAIN>/json/ -H "Content-type: application/json" -H "Accept: application/json" -X POST -d '{
"alias": "webservices@example.com",
"version": "1.00",
"request": [{
"requesttypedescriptions": ["TRANSACTIONQUERY"],
"filter":{
"sitereference": [{"value":"test_site12345"}],
"transactionreference": [{"value":"55-9-12345"}]
}
}]
}'
{
"alias":"webservices@example.com",
"version":"1.00",
"request":[{
"requesttypedescriptions":["TRANSACTIONQUERY"],
"filter":{
"sitereference":[{"value":"test_site12345"}],
"transactionreference":[{"value":"55-9-12345"}]
}
}]
}
<requestblock version="3.67">
<alias>webservices@example.com</alias>
<request type="TRANSACTIONQUERY">
<filter>
<sitereference>test_site12345</sitereference>
<transactionreference>55-9-12345</transactionreference>
</filter>
</request>
</requestblock>
Replace <DOMAIN>
with a supported domain. Click here for a full list.
Request field specification
Field | Format | Description | |
sitereference XPath: /filter/sitereference |
Alpha (50) | The site reference that processed the transaction. | |
transactionreference XPath: /filter/transactionreference |
Alphanumeric including hyphens (25) | The unique reference associated with the Pay by Bank transaction. |
Response
When receiving a TRANSACTIONQUERY response, you should first of all be looking at the transactionreference and orderreference, which you can use to correctly identify the transaction, allowing you to update the order in your own records.
Secondly, you should check the value of the settlestatus returned in the TRANSACTIONQUERY response, as this allows you to determine the transaction outcome:
- 100 ("Settled") - The customer approved the Pay by Bank transaction and the acquiring bank subsequently authorised the transfer. Funds will be settled into the merchant's bank account in a timeframe determined by the terms agreed with Trust Payments during the onboarding process.
- 3 ("Cancelled") - The transaction was cancelled.
- 10 ("Pending") - The transaction is pending authorisation and will be later updated to 3 or 100 depending on the whether transaction authorisation was successful.
Finally, it is good practice to look at the other fields included in the TRANSACTIONQUERY response to check they also contain the values you are expecting.
{
"requestreference": "W57-4r9dhbtx",
"version": "1.00",
"response": [
{
"transactionstartedtimestamp": "2021-11-29 14:12:45",
"errormessage": "Ok",
"errorcode": "0",
"records": [
{
"authmethod": "FINAL",
"billingcounty": "Gwynedd",
"transactionstartedtimestamp": "2021-11-29 14:10:04",
"sitereference": "test_site12345",
"billingstreet": "Test Street",
"transactionreference": "57-97-146",
"billingcountryiso2a": "GB",
"billingemail": "test@test.com",
"billingfirstname": "Joe",
"livestatus": "0",
"splitfinalnumber": "1",
"settleduedate": "2021-11-29",
"billingpremise": "123",
"errorcode": "0",
"baseamount": "2000",
"billingtown": "Bangor",
"acquirertransactionreference": "05b3f4d0-feba-4c49-b97f-f126b5871f21",
"billingpostcode": "TR45 6ST",
"merchantname": "Merchant test site",
"paymenttypedescription": "ATA",
"orderreference": "MyOrder123",
"settledtimestamp": "2021-11-29 14:10:04",
"accounttypedescription": "ECOM",
"updatereason": "stgateway",
"requesttypedescription": "AUTH",
"customerip": "1.2.3.4",
"currencyiso3a": "GBP",
"billinglastname": "Bloggs",
"settlebaseamount": "2000",
"errormessage": "Ok",
"interface": "JWT-JWT-JWT",
"operatorname": "webservices@example.com",
"settlestatus": "0",
"customercountryiso2a": "GB",
"customercounty": "Gwynedd",
"customeremail": "test@test.com",
"customerfirstname": "Joe",
"customerlastname": "Bloggs",
"customerpostcode": "TR45 6ST",
"customerpremise": "123",
"customerstreet": "Test Street",
"customertown": "Bangor"
}
],
"found": "1",
"requesttypedescription": "TRANSACTIONQUERY"
}
],
"secrand": "lN"
}
4. Payment completion
Once the customer returns from the pages hosted by their bank to the returnurl hosted on your site, and you have followed the steps above to determine the status of the transaction, you will need to display an appropriate message in the customer's browser (e.g. success or error).
Settlement
The settlement process for Pay by Bank differs from the standard process followed with card payments
Once a payment has been authorised, the settlestatus will be updated to "100". Settlement of funds into your bank account will occur at a later time, as determined by the terms and timelines agreed with Trust Payments during the onboarding process.
In rare cases, a Pay by Bank transaction may not update to settlestatus "100"
In the unlikely event that a payment is still pending settlement after 7 days (settlestatus “10”), this will be scheduled for investigation and we will contact you with further information.
Designing the customer experience
As your customers may be unfamiliar with Pay by Bank, and how it can streamline their checkout experience, we recommend emphasising this on your checkout and highlighting the convenience Pay by Bank can provide, as research has shown that customers are more likely to engage with novel methods of payment.
Specifically, that if your customer is at your checkout on their mobile device, they can complete a purchase using the banking app installed on the mobile device, meaning they do not need to enter card details. The process is as simple as signing into their banking app to authorise the transaction, which typically involves entering a PIN or unlocking using biometric authentication, such as a built-in fingerprint reader or facial recognition.
We also recommend that you advise customers, who have opted to pay using Pay by Bank, that they agree to share their bank details with Trust Payments if prompted to by their bank, in order to help better facilitate back office processes.
Managing your transactions in MyST
As with any other payment method, all Pay by Bank transactions can be viewed and managed within MyST, our online portal. When working with Pay by Bank transactions, please be aware of the following:
- Please be aware that Pay by Bank is often shown in MyST as "Pay by Bank", with a green background. But it can also be shown as "Account to account" (e.g. when in Compact mode).
Testing
You will need to test your solution before you can begin processing live payments. Test transactions are processed through your test Site Reference.
Requirements
You will need to contact our Support Team and request that your test site reference is configured to connect directly to the sandbox environment. Testing frameworks and sandboxes will be arranged individually with each of our participating merchants.
When performing test transactions, the redirect URL returned in the AUTH response will redirect your browser to the sandbox environment to simulate the Pay by Bank checkout process. We will provide you with test credentials needed to proceed through the interface.