Online Data Provisioning API specification
This page describes the technical specification of realtime account data provisioning to SurePay. Based on this specification, the provider of the data should be able to expose a Restful API over HTTP and allow the SurePay solution to access it with required security and performance levels. We suggest creating a POST instead of a GET endpoint so that we won't have to pass sensitive information (the IBAN) in the URL
Which data is mandatory to deliver?
Depending on the accessibility of your data we highly advise to deliver at least the Mandatory fields, as they are required to ensure the service works in a desirable way for the end user (the payer who initiates a transaction). Optional fields are not required for the basic functionality of the IBAN Name check, but could improve the matching quality of the algorithm.
- In a response, we always expect the mandatory information of the bank account requested.
- For Natural Person owned accounts, we expect an object per account holder, as some accounts might have multiple account holders.
- For Organisation owned accounts, we expect only one object.
Endpoints example
Environment | Method | Endpoint URL suggestion (Defined by customer) |
---|---|---|
Acceptance | POST | https://api.acc.yourbank.com/account/matchingdata |
Production | POST | https://api.yourbank.com/account/matchingdata |
What items do we need to establish the connection?
- The exact endpoints for both production and test environment.
- Certificates needed to connect to provided endpoints (SurePay's certificate are signed by DigiCert).
- Client credentials, if needed in order for us to access an Access Token API
- Token endpoint to be used with the above client credentials, to retrieve the access token.
- Postman collection (with both APIs, Data Provisioning and Token APIs). If not possible, a text file containing equivalent “curl” requests.
Headers
- Name
X-Correlation-Id
- Type
- String
- Tag(s)
- Mandatory
- Description
A unique correlation ID should be sent for every request.
- Max. 70 characters
^[a-zA-Z0-9\-]{1,70}
- Name
Content-Type
- Type
- application/json
- Tag(s)
- Mandatory
- Description
Content type and encoding of the request.
- Name
Authorization
- Type
- Bearer
- Tag(s)
- Mandatory
- Description
Oauth 2.0 bearer token. You will also need to create an authentication endpoint where we can fetch and refresh this token.
Request body
- Name
accountId
- Type
- Object
- Tag(s)
- Mandatory
- Description
Object used to send the account information in the request.
- Name
value
- Type
- String
- Tag(s)
- Description
The identifier of the account to be checked. The max. allowed length depends on the type.
- IBAN -
[A-Z]{2,2}[0-9]{2,2}[a-zA-Z0-9]{1,30}
(For IBAN, just capital letters are accepted, without white spaces). - ACCOUNT_NUMBER - 1-140 characters (depending on the country).
- IBAN -
- Name
type
- Type
- enum
- Tag(s)
- Description
Describes the type of the account that needs to be found. For now it can be IBAN for SEPA accounts or ACCOUNT_NUMBER for non SEPA accounts.
- Name
bic
- Type
- String
- Tag(s)
- Description
Only used when
accountId.type = ACCOUNT_NUMBER
Format:[A-Z]{6,6}[A-Z2-9][A-NP-Z0-9]([A-Z0-9]{3,3}){0,1}
Request
{
"accountId": {
"type": "IBAN",
"value": "NL11SRPY1234567890"
}
}
Response body
In case of a successful response, the following parameters are expected to be returned. Most of the data fields are optional, however, the more data you provide, the better our matching algorithm works! In case of an unsuccessful response a meaningful HTTP code and error message is expected, please read the errors chapter.
Suggested response fields
- Name
accountName
- Type
- String
- Tag(s)
- Mandatory
- Description
The name under which the account is officially registered at the bank. Also known as ascription.
- Format: Max. 140 characters
- Name
status
- Type
- Enum
- Tag(s)
- Mandatory
- Description
- ACTIVE - Account is a valid account and supported for checks.
- INACTIVE - Account marked by the account holding bank as an invalid, inactive or non existent. Or it is an account that is not (yet) existing at the bank. This account is not eligable for receiving transfers.
- NOT_FOUND - If the account can not be found by the bank, no other information is required in the response. When certain the bank account does not exist, an INACTIVE is more appropriate.
- Name
startDate
- Type
- Date
- Tag(s)
- Optional (Only used when using FRI)
- Description
The date when the account was opened and registered by the bank. Reflects the real start date of the account. Mandatory when using Fraud Risk Indicator.
- Format: "YYYY-MM-DD".
- Name
bankAccountType
- Type
- Enum
- Tag(s)
- Optional (Only used when using FRI)
- Description
The type of bank account. The possible values are:
- PAYMENTS - A payments account, also known as a checking account.
- SAVINGS - A savings account.
- MORTGAGE - A mortgage account.
- TRUST - Also known as derdengeldenrekening or Escrow account. Used by notary offices, lawyers and bailiffs.
- COLLECTION - Also known as beheer rekening. typically owned by a collection agency or a debt buyer. But can also be used by Collecting Payment Service Providers.
- INVESTMENT - An account used for investing (Also known as brokerage account or beleggingsrekening).
- OTHER - Other products.
- UNKNOWN - Unknown account type.
- Name
personalAccountHolders
- Type
- Array of Objects
- Tag(s)
- Description
N occurrences (for joint accounts).
At least one item is mandatory if the account is a personal account and is not switched, not opted out, and status is Active.- Name
initials
- Type
- String
- Tag(s)
- Mandatory
- Description
Initials of the account holder. The initials should always be separated with a period.
- Example: "F.G."
- Name
allFirstNames
- Type
- String
- Tag(s)
- Mandatory
- Description
All first names as registered in the Passport. Separate with spaces. Does not include the surname.
- Example: "Jane" or "Jane Helena Alexandra".
- Name
primaryFirstName
- Type
- String
- Tag(s)
- Description
The primary first name of the account holder.
Can be used when not usingallFirstNames
.- Example: "Jane"
- Name
middleName
- Type
- String
- Tag(s)
- Description
The middle name is the second, third, fourth, etc name, if any. Limited to one middle name added in this field. Can be used when not using
allFirstNames
.- Example: "Helena" as in "Marie Helena".
- Name
surname
- Type
- String
- Tag(s)
- Description
The account holder’s surname. The surname may include prefixes, suffixes and partnerName if not provided elsewhere.
- Example: "Johnson", "Johnson - Davids Jr.", "van der Sloot - Davids Jr."
- Name
surnamePrefix
- Type
- string
- Tag(s)
- Description
May be included in
surname
field but may also be delivered separately.- Example: “van der”
- Name
surnameSuffix
- Type
- String
- Tag(s)
- Description
May be included in
surname
field but may also be delivered separately.- Example: “Sr.” or “Jr.”
- Name
birthName
- Type
- String
- Tag(s)
- Description
The birth name, as formally registered at the moment of their birth. The birthName may include prefixes & suffixes.
- Example: "Johnson", "Johnson - Davids Jr.".
- Name
birthNamePrefix
- Type
- String
- Tag(s)
- Description
May be included in
birthName
field but may also be delivered separately.- Example: "van der".
- Name
birthNameSuffix
- Type
- String
- Tag(s)
- Description
May be included in
birthName
field but may also be delivered separately.- Example: "Jr."
- Name
partnerName
- Type
- String
- Tag(s)
- Description
The surname of the account holder’s official partner. Validated via a passport check by the ASPSP. Preferrably received seperately but may also be included as part of
surname
field.
- Name
unvalidatedPartnerName
- Type
- String
- Tag(s)
- Description
Name of the account holder’s partner or spouse when not validated via a passport check. Use this field if you don't know if the partnerName is properly validated by your ASPSP. Preferrably received seperately but may also be included as part of
surname
field.
- Name
partnerNamePrefix
- Type
- String
- Tag(s)
- Description
May be included in
partnerName
field but may also be delivered separately.
- Name
unvalidatedPartnerNamePrefix
- Type
- String
- Tag(s)
- Description
May be included in
unvalidatedPartnerName
field but may also be delivered separately.
- Name
shortenedSurname
- Type
- String
- Tag(s)
- Description
A shortened version of the surname.
- Example: “Hdez.” for "Hernandez"
- Name
nameQualificationPrefix
- Type
- String
- Tag(s)
- Description
- Example: "Prof."
- Name
nameQualificationSuffix
- Type
- String
- Tag(s)
- Description
- Example: "MBA", "PhD"
- Name
nobilitySalutation
- Type
- String
- Tag(s)
- Description
- Example: "Lord"
- Name
organisationAccountHolder
- Type
- Object
- Tag(s)
- Description
Mandatory if the account is a organisation owned account and is not switched, not opted out, and status is Active.
- Name
legalName
- Type
- String
- Tag(s)
- Mandatory
- Description
The official, legal company name.
- Name
commercialNames
- Type
- Array of String
- Tag(s)
- Description
An array of trading or commercial names; each name can have max.
- Format: 140 characters.
- Name
companyId
- Type
- Object
- Tag(s)
- Mandatory
- Description
- Name
type
- Type
- Enum
- Tag(s)
- Mandatory
- Description
The CompanyID type.
- NL_KVK - identifying number for a registration in the Netherlands Business Register.
- NL_KVK_BRANCH - identifying number of a branch. It gives the information about the specific branch.
- FR_SIREN - the unique French business identification number.
- FR_SIRET - number that provides information about the location of the business in France. The registration number contains extra 5 digits (added onto the end of the SIREN number makes the full SIRET number).
- EU_VAT - number that allows sending a VAT number associated with an European company. In order to accept its value, the user has to send the country code (belonging to an EU country) plus the VAT number.
- UK_CRN - The unique identifier on the register of the UK's Companies House.
- BE_KBO - The unique business identifier on the Belgium Kruispuntbank van Ondernemingen (KBO)
- ES_CIF - This is the tax ID (CIF - Certificado de Identificacion Fiscal/Fiscal Identification Certificate) for all Spanish companies.
- DE_HRN - The german HandelsRegister Number is a unique identifier used in Germany to identify limited companies.
- Name
value
- Type
- String
- Tag(s)
- Mandatory
- Description
The value of the CompanyID type.
- NL_KVK -
[0-9]{8}
- NL_KVK_BRANCH -
[0-9]{12}
- FR_SIREN -
[0-9]{9}
- FR_SIRET -
[0-9]{14}
- EU_VAT - Multiple Validations depending on country
- UK_CRN -
[SC,OC,SO,NI,R,NC,RC,LP,SL,NL] {2,1}[0-9]{6,7} or [0-9]{8}
- BE_KBO -
[0-9]{10}
- ES_CIF -
[A-Z]{1}[0-9]{8}
- DE_HRN -
[HRA]{6}[0-9] or [HRB]{6}[0-9]{1}[B]
- NL_KVK -
- Name
legalStructure
- Type
- String
- Tag(s)
- Description
The code of the legal form of the organisation as registered at the Chamber of Commerce.
- Example: BV, SARL or Ltd.
- Name
postalAddress
- Type
- Object
- Tag(s)
- Mandatory
- Description
The postal address of the account holder. The account holder could reside in a different country than where the account is opened.
- Name
postalCode
- Type
- String
- Tag(s)
- Description
Postal code of the account holder. Added in case the 'townName' is not available.
- Example: 1057WG.
- Name
countryCode
- Type
- String
- Tag(s)
- Mandatory
- Description
ISO 3166 Alpha-2 country code (NL, DE, FR, etc).
- Name
townName
- Type
- String
- Tag(s)
- Mandatory
- Description
So that we can show the townName together with a nameSugestion in case of a no match on an organisation. This will strenghten the end-user knows they are transferring funds to the intended organisation
Response
{
"accountName": "J.R. van der Werff",
"status": "ACTIVE",
"personalAccountHolders": [
{
"initials": "J.R.",
"allFirstNames": "John Richard",
"surname": "de Jong - van der Werff",
"birthName": "van der Werff"
}
]
}
Status and error codes
We advise the use of industry standard HTTP response codes to provide feedback on the success or failure of an API request. Responses in the 2xx range are indicative of successful transactions, while responses in the 4xx range signify an error related to the provided data, such as a missing parameter or failed charge. In rare cases, responses in the 5xx range indicate an issue with your servers.
Error response body
- Name
- Type
- Array of Objects
- Tag(s)
- Description
- Name
errorCode
- Type
- String
- Tag(s)
- Description
The error code that represents the functional error. All the functional errors are described in the Functional Errors table.
Example - 400 bad request
[
{
"errorCode": "INVALID_IBAN"
}
]
Technical Errors
HTTP Status Code | Description |
---|---|
400 - Bad request | Request has malformed missing or non-compliant JSON body or URL parameters |
401 - Unauthorised | Authorization header missing or invalid token |
403 - Forbidden | Token has incorrect scope or a security policy was violated |
404 - Not Found | We were unable to find the requested resource in any of our available data sources |
429 - Too many requests | IResponse status code indicates the user has sent too many requests in a given amount of time |
500 - Internal server error | Something went wrong on the API gateway or service. In this case the body might contain different details based on the schema that we are connected with |
Error response
[
{
"errorCode": "INVALID_ACCOUNT_ID"
}
]
Functional errors
HTTP 400 - Bad Request
If the client's submitted request does not pass the validations, the service will return an Error Response object with the details of the issue. The possible ‘errorCodes’ are gathered in the following table: Not all codes are mandatory to implement, these are a suggestion.
Functional error | Description |
---|---|
INVALID_IBAN | The IBAN provided ‘accountId.value’ exceeds the maximum length (140 characters) or contains spaces or any of the following special characters !"#$%&' |
INVALID_BANKCODE | The provided bank code in the requested IBAN is not a bank code you are supporting |
INVALID_CORRELATION_ID | A correlation ID is invalid if it does not match the regular expression, if its length is shorter than 1 or its length is longer than 70 characters |
INVALID_ACCOUNT_NUMBER | The value provided for any of the ‘accountId.type’ fields exceeds the maximum length (140 characters) or contains spaces or any unallowed special characters |
HTTP 400 - Bad Request
[
{
"errorCode": "INVALID_IBAN",
}
]