Trustly Risk Decline Override
Trustly Risk Decline Override allows you to manage, override, and approve declined Trustly transactions.
When you approve a declined transaction, it becomes a non-guaranteed capture. This means you combine the benefits of guaranteed and non-guaranteed payments, and this gives you full control to manage risk according to your own criteria.
The following are a few of the key features of Trustly Risk Decline Override:
- Trustly Integration: Direct integration with the Trustly payment system.
- Risk Data Access: Retrieve detailed risk data for transactions.
- Custom Risk Management: Make decisions based on your own risk appetite and policies.
- Override Capability: Approve transactions that Trustly has flagged for potential override, making them non-guaranteed.
Workflow
The following is the Trustly Risk Decline Override workflow:
- Receive the Trustly declined or failed transaction notification. This notification includes extended reason codes and a flag that indicates if you can override the transaction.
- When an override is possible, call the Get Risk Data API to override and convert the Trustly decline. Use this data to decide whether to approve the transaction.
- When your risk assessment approves the transaction, call the Approve Transaction API. This action overrides Trustly risk decline and converts the transaction into a non-guaranteed transaction.
- Process returned transactions for the non-guaranteed transactions. Trustly offers Representment as a Service that you can enable for these returns to help reduce your losses.
API reference
Use the information provided here to retrieve risk data and execute a risk decline override.
Declined transaction notification parameters
The following table lists the parameters provided by Trustly when a transaction is denied:
| Parameter | Type | Description |
|---|---|---|
merchantId | string | Unique identifier for the merchant. |
merchantReference | string | Unique transaction identifier. |
paymentType | string | Type of payment. |
transactionType | string | Type of transaction. |
eventId | string | Unique identifier for the event. |
eventType | string | Type of event (e.g., "Deny"). |
objectId | string | Unique identifier for the object. |
objectType | string | Type of object (e.g., "Transaction"). |
message | string | Message describing the reason for denial. |
timeZone | string | Time zone of the event. |
createdAt | string | Timestamp of the event. |
errorCode | string | Error code for the denial. |
isOverridePossible | boolean | Indicates if a transaction override is possible. |
shouldOverrideBeAvoided | boolean | Indicates if a transaction override should be avoided (due to the extended reasons provided). |
paymentProviderTransaction.reasonCode | string | Reason code from the payment provider. |
paymentProviderTransaction.reasonCodeMessage | string | Message corresponding to the reason code. |
paymentProviderTransaction.status | string | Status of the transaction from the payment provider. |
paymentProviderTransaction.statusMessage | string | Status message from the payment provider. |
paymentProviderTransaction.extendedReason.code | repeated string | Extended reason codes. |
status | string | Status of the transaction. |
statusMessage | string | Message corresponding to the transaction status. |
Sample notification request
The following is an example of the notification you'll receive from Trustly when a transaction is declined.
POST /{notification path}
Authorization: Basic TThSYUhnRWpCRTU0enVGWU1SUXE6RVlOM0dYYXNyVlUxdlExdXlZejIyTk5RZHk0PQ==
merchantId=00123&merchantReference=my+reference&paymentType=2&transactionType=3&eventId=1030845856&eventType=Deny&objectId=1025228290&objectType=Transaction&message=Not+enough+balance&createdAt=1714503865362&errorCode=331&isOverridePossible=true&shouldOverrideBeAvoided=true&paymentProviderTransaction.reasonCode=12&paymentProviderTransaction.reasonCodeMessage=Not+enough+balance&paymentProviderTransaction.status=SW021&paymentProviderTransaction.statusMessage=Not+enough+balance&paymentProviderTransaction.extendedReason.code=10000&paymentProviderTransaction.extendedReason.code=11000&status=8&statusMessage=Denied
See Payment Decline Codes and Reason Codes for more information about the decline reason codes shared by Trustly.
Get risk data
To request risk data from Trustly, you must define the following parameters in your API request definition:
- Endpoint:
/api/v1/transactions/{transactionId}/risk - Method:
GET - Description: Retrieves risk data for the specified declined capture transaction.
transactionId(string): A unique identifier for the transaction.
Sample request
The following is an example of the API request definition you'll send to Trustly.
GET /api/v1/transactions/1006755981/risk
Host: trustly.one
Authorization: Basic TThSYUhnRWpCRTU0enVGWU1SUXE6RVlOM0dYYXNyVlUxdlExdXlZejIyTk5RZHk0PQ==
Response
The following table lists the response you will receive from Trustly when you request risk data.
| Field | Type | Description |
|---|---|---|
responseCode | string | Response code for the risk data request. |
reasonCode | integer | Reason code for the transaction denial. |
isOverridePossible | boolean | Indicates if you can override the denial. |
shouldOverrideBeAvoided | boolean | Indicates if you should avoid the override. |
extendedReasons | array | Detailed reasons for the transaction denial. |
code | integer | Extended reason code. |
description | string | Description of the extended reason. |
hasEnoughBalance | optional boolean | Indicates if the bank account has enough balance to cover the capture transaction on the settlement date. Considers all pending Automated Clearing House (ACH) transactions and predicted future deposits (like W2 income). |
suggestedRetryAmount | optional string | Suggested retry amount for the transaction. |
velocity | optional array | Array of velocity objects detailing transaction activity. |
period | integer | Period in days. |
customer.captures | integer | Number of captures for the customer. |
customer.deposits | integer | Number of deposits for the customer. |
device.captures | integer | Number of captures for the device. |
device.deposits | integer | Number of deposits for the device. |
account.captures | integer | Number of captures for the account. |
account.deposits | integer | Number of deposits for the account. |
overall.captures | integer | Overall number of captures. |
overall.deposits | integer | Overall number of deposits. |
predictedReturnRisk | optional object | Predicted return risk data. |
customerInitiated | object | Risk of returns initiated by customers. For example, unauthorized ACH returns, stop payment ACH returns). |
minRate | integer | Minimum return rate (in basis points). |
maxRate | integer | Maximum return rate (in basis points). |
bankInitiated | object | Risk of returns initiated by financial institutions. For example, NSFs and administrative returns. |
minRate | integer | Minimum return rate (in basis points). |
maxRate | integer | Maximum return rate (in basis points). |
combinedReturnRisk | object | Overall return risk assessment combining customer-initiated and bank-initiated risks. |
minRate | integer | Combined minimum return rate (in basis points). |
maxRate | integer | Combined maximum return rate (in basis points). |
Sample response
The following is an example of the response you'll receive from Trustly when you request risk data.
{
"responseCode": "SW021",
"reasonCode": 1,
"isOverridePossible": true,
"shouldOverrideBeAvoided": false,
"extendedReasons": [
{
"code": 10000,
"description": "Exceeded thresholds"
},
{
"code": 11072,
"description": "Exceeded 72 hours consumer amount velocity limit"
}
],
"hasEnoughBalance": true,
"suggestedRetryAmount": "230.00",
"velocity": [
{
"period": 30,
"customer": {
"captures": 2,
"deposits": 3
},
"device": {
"captures": 3,
"deposits": 4
},
"account": {
"captures": 4,
"deposits": 5
},
"overall": {
"captures": 4,
"deposits": 5
}
},
{
"period": 90,
"customer": {
"captures": 3,
"deposits": 3
},
"device": {
"captures": 3,
"deposits": 4
},
"account": {
"captures": 4,
"deposits": 5
},
"overall": {
"captures": 4,
"deposits": 5
}
}
],
"predictedReturnRisk": {
"customerInitiated": {
"minRate": 0,
"maxRate": 50
},
"bankInitiated": {
"minRate": 100,
"maxRate": 300
},
"minRate": 100,
"maxRate": 350
}
}
See Payment Decline Codes and Reason Codes for more information about the decline reason codes shared by Trustly.
Approve transaction
To approve a declined Trustly transaction, the following parameters must be defined in your API request definition:
- Endpoint:
/api/v1/transactions/{transactionId}/approve - Method:
POST - Description: Approves the specified transaction, overriding the Trustly risk engine and converting it to a non-guaranteed transaction. If a return happens for this non-guaranteed transaction, its status changes to Reversed, and the payment provider transaction status shows the return code. For example, R03.
transactionId(string): Unique identifier for the transaction.
Sample request
The following is an example of the API request definition you'll send to Trustly.
POST /api/v1/transactions/1006755981/approve
Host: trustly.one
Authorization: Basic TThSYUhnRWpCRTU0enVGWU1SUXE6RVlOM0dYYXNyVlUxdlExdXlZejIyTk5RZHk0PQ==
Sample response
The following is an example of the response you'll receive when you approve a transaction. The transaction (object) is returned with its including status.
{
"transaction": {
"transactionId": "1025319672",
"transactionType": 3,
"originalTransactionId": "1025319406",
"payment": {
"paymentId": "1024188827",
"paymentType": 2,
"system": 1,
"country": "US",
"merchant": {
"merchantId": "1076"
},
"merchantReference": "A8791F6165148D27",
"merchantId": "1076",
"customer": {
"customerId": "1024101150"
},
"fingerprint": "ICaCEX7AjYCt14TvsQp6DBwi8T8=",
"verification": {
"status": 3,
"mode": 3,
"verifyCustomer": false
},
"account": {
"name": "Demo Checking Account",
"type": 1,
"profile": 1,
"country": "US",
"accountNumber": "6576",
"routingNumber": "124003116",
"verified": true,
"verification": {
"verified": true,
"type": 2,
"hasEnoughFunds": false
},
"source": 1,
"virtualAccountRoutingPair": false
},
"description": "Globex Demo",
"currency": "USD",
"amount": "0.00",
"paymentProvider": {
"paymentProviderId": "200005501",
"type": 1,
"subtype": 1000,
"name": "Demo Bank",
"country": "US"
},
"paymentProviderSubtype": 1000,
"auth": {
"token": "1B8F4NF3O086",
"status": 2,
"message": "Authorized"
},
"authorization": "1B8F4NF3O086",
"authorizationStatus": 2,
"authorizationStatusMessage": "Authorized",
"pending": "0.00",
"paid": "2.00",
"refunded": "0.00",
"reversed": "0.00",
"balance": "2.00",
"createdAt": 1719836931223,
"updatedAt": 1719851444167,
"recordVersion": 10,
"paymentFlow": 79,
"allowedPaymentProviderSubType": [
1000,
2000
]
},
"currency": "USD",
"amount": "1.00",
"pending": "0.00",
"paid": "1.00",
"refunded": "0.00",
"reversed": "0.00",
"balance": "1.00",
"paymentProviderTransaction": {
"paymentProviderTransactionId": "ptx-fBQgeemdGzcWSE0QxqA60G8M-sbx",
"signature": "46401",
"status": 118,
"statusMessage": "Settled",
"paymentProcessor": {
"paymentProcessorId": "100000016"
},
"instantSettle": false,
"statementId": "1K8T",
"reasonCode": -1
},
"status": 4,
"statusMessage": "Completed",
"ip": "177.53.170.106",
"createdAt": 1719851400859,
"processedAt": 1719851443780,
"completedAt": 1719851444167,
"updatedAt": 1719851444172,
"ppTrxId": "ptx-fBQgeemdGzcWSE0QxqA60G8M-sbx",
"merchantReference": "A8791F6165148D27",
"automaticRepresentment": false,
"paymentProcessorType": "ACH",
"statusCode": "AC118",
"forgiven": "0.00",
"kycType": -1,
"recordVersion": 7
}
}Receive ACH return notifications from Trustly
When an ACH return occurs on a transaction whose risk decline you overrode, the resulting non-guaranteed transaction's status changes to Reversed. The payment provider transaction status shows the specific ACH return code. For example, R01.
Additionally, Trustly places a hold on the consumer, automatically declining all their subsequent transactions. To enable the consumer to authorize new transactions, you must call the Remove Debt Block API.
Trustly sends webhook notifications to make you aware of ACH returns. The following table lists the parameters that are included in a an ACH return notification.
| Field | Type | Description |
|---|---|---|
merchantId | string | Unique identifier for the merchant. |
merchantReference | string | Unique transaction identifier. |
paymentType | string | Type of payment. |
transactionType | string | Type of transaction. |
eventId | string | Unique identifier for the event. |
eventType | string | Type of event. For example, Reverse. |
objectId | string | Unique identifier for the object. |
objectType | string | Type of object. For example, Transaction. |
message | string | Message describing the reason for reversal. |
timeZone | string | Time zone of the event. |
createdAt | string | Timestamp of the event. |
paymentProviderTransaction.status | string | Status of the transaction from the payment provider. |
paymentProviderTransaction.statusMessage | string | Status message from the payment provider. |
reversedAmount | string | The reversed amount. |
status | string | Status of the transaction. |
statusMessage | string | Message corresponding to the transaction status. |
Sample notification request
The following is an example of the ACH notification request you'll send to Trustly.
POST /{notification path}
Authorization: Basic TThSYUhnRWpCRTU0enVGWU1SUXE6RVlOM0dYYXNyVlUxdlExdXlZejIyTk5RZHk0PQ==
merchantId=00123&merchantReference=my+reference&paymentType=2&transactionType=3&eventId=1030845856&eventType=Reverse&objectId=1025228290&objectType=Transaction&message=US_ACH_CROSSRIVER+returned+transaction+with+message%3A+R01&createdAt=1714503865362&paymentProviderTransaction.status=R01&paymentProviderTransaction.statusMessage=Insufficient+Funds&reversedAmount=37.99&status=10&statusMessage=Reversed
Remove debt block
To remove a debt block, the following parameters must be defined in your API request definition:
- Endpoint:
/api/v1/transactions/{transactionId}/removeDebtBlock - Method:
POST - Description: Removes any holds that may have been placed by Trustly on the consumer due to an ACH return on an overridden transaction. If there are no other transactions with debt blocks, the consumer can successfully authorize new transactions.
transactionId(string): Unique identifier for the transaction that has received an ACH return.
Sample request
The following is an example of the remove debt block request you'll send to Trustly.
POST /api/v1/transactions/1006755981/removeDebtBlock
Host: trustly.one
Authorization: Basic TThSYUhnRWpCRTU0enVGWU1SUXE6RVlOM0dYYXNyVlUxdlExdXlZejIyTk5RZHk0PQ==
Sample response
The following is an example of the response you'll receive after submitting a request to remove a remove debt block.
{}Updated 1 day ago