Error Handling

Several errors or unexpected states can occur when communicating with banks. Information about the error will be provided in the XS2A API. The list of possible errors consists of six main groups: USER, BANK, TECHNICAL, NOT_SUPPORTED, MAINTENANCE, CONSENT. These top-level categories can be arbitrarily extended with subcategories to provide more detailed information.

The top-level categories are always provided. The sub-categories are optional, however, the error is described as precisely as possible. For example: If the bank provides the information that the consumer entered an incorrect password, the error category would be USER.ACCESS_DENIED.CREDENTIALS. If the information provided by the bank does not allow for such a specific mapping the error category USER.ACCESS_DENIED or maybe even only USER is used if that is what can be deducted from the current state and context.

It is recommended to implement at least the top-level category in order to have a fallback value for subcategories that might be added in the future.

Error categories in the responses of the endpoints for the XS2A App & Auth API are reduced to the top-level categories for TECHNICAL, NOT_SUPPORTED and MAINTENANCE. For these, we don't want to expose the detailed error to the consumers. The full error category can be fetched via the flow API. All other errors are returned with subcategories.

Errors occuring during a regular Session


An error that was caused by the consumer happened.


The consumer aborted the process.


Access was denied.


  • If the account is a business or corporate account with different access rights, it can be that the user logging is does not have the right to access the requested account or initiate a transfer.


Access was denied, because the consumer provided incorrect credentials.


Access was denied, because the consumer's account is blocked by the bank.


The consumer has to manually log into their account, because the bank expects some kind of configuration.


The consumer has to allow transfers to unknown beneficiaries as this is not configured by default.


The consumer has to manually log into their account and confirm that she/he has read an information message.


The consumer has to manually log into their account and perform configurations related to their account.


The account was recently opened and needs to be activated.


The consumer has to manually log into their account and perform configurations related to authentication methods.


An error occurred that is related to the consumer's session.


The consumer took too long to proceed in the session.


The consumer has logged into their bank account on a different device or browser window and thus blocks Open banking. by Klarna from accessing the account.


The transfer was denied, because of unspecified reasons related to the consumer.


The transfer was denied, because the consumer did not have sufficient funds.


The transfer was denied, because the type of transfer is not possible.


An error that was caused by the bank happened.


The transfer was denied by the bank.


The transfer was denied by the bank, because it duplicates a recent transfer.


The transfer was denied, because the bank prevents sending money to the recipient's account.


The transfer was denied, because the bank does not support set currency.


A technical error caused by the bank happened.


The bank's server took too long to respond.


A technical error happened.


The requested action is not supported.


The requested action is not supported, because a transfer would have to be confirmed by a second accessor of the account.


An account of an underaged holder was selected and requires a separate confirmation by the respective supervisor.


The requested date range is not supported for this bank. For some banks, only transactions from the last 90 days may be fetched.


The requested date range is set like this:

from_date: <the date 101 days before today>

to_date: <the date 91 days before today>

While this configuration requests only a 10-day range it contains days that are more than 90 days in the past. However, the bank only allows up to 90 days and as a result no transactions are retrievable.


The requested action is not supported, because the consumer's account is a business account.


The requested action is not supported, because there are no applicable accounts to execute this action.


  • An account of account_type CREDITCARD was used to initiate a transfer. Creditcard accounts can’t be used for bank transfers. That is also indicated by the transfer_type of the account which would be set to NONE.

  • The user has selected a SAVINGS account to receive the transaction history and the bank does not allow transactions to be fetched for accounts with account_type set to SAVING.

  • There was no account found matching the selection criteria specified when starting the flow (e.g. neither the provided account_id nor the iban could be matched to an account of the user).


The requested action is not supported, because of an unsupported authentication method.


The requested action is not supported, because the authentication method is not allowed for the mobile device the consumer is using.


The consumer uses their banking application and their OTP app on the same device. This is not compliant with SCA (Strong Customer Authentication) regulations as it requires separate devices to be used.

The user has to scan a QR-code from the same device they use for the authentication which is almost always physically impossible.


One or more of the services involved are undergoing maintenance.


The bank's service is undergoing maintenance.


The bank's service is undergoing maintenance that affects the consumer's account.


The bank's service is undergoing maintenance that affects doing transfers.


Open banking. by Klarna is undergoing maintenance.

A general error when using a consent that can not be specified in detail.

This could also be an expired, revoked or limit exceeded issue but the bank does not specify it as such.


Treat this as a temporary error since it could be caused by a temporary issue at the bank. Try again later with the latest consent_token avaliable to you. Note that the error response might contain the latest token.

If the error persists over a period of time, you have to ask the user to grant a new consent resulting in a new consent_token.


The consent lifetime has expired.


The consent token expired. Start a new session and ask the user to grant a new consent resulting in a new consent_token.


The consent has been revoked by the user. This can also be that not the latest consent_token was used.


  • The user has revoked the consent in their online banking.

  • The user has granted a consent to their account to another provider/license holder other than Klarna. This can cause any existing consents to automatically get revoked.


The consent_token could have been one from a previous request. Check that you always use the latest consent_token. Otherwise start a new session and ask the user to grant a new consent resulting in a new consent_token.


The daily limit of the consent usage has been exceeded.


Some banks allow only a certain number of requests per day for a given consent. Typically the limit is 4 requests per day per consent.


Wait for the next day. Typically time is set to the timezone of the issuing bank.


The requested resource is no longer granted or available.


  • Bank randomizes their account ids on each session

  • After re-authentication a user granted access to fewer accounts than before

  • Some accounts might no longer exist


Clear the accounts cache and do a fresh accounts call to acquire an up-to-date list of the consumer’s bank accounts.


There are currently three different types of timeouts which are present in the XS2A-API as well as in the Auth API:

  • Request timeout:
    • The XS2A-API has an internal timeout of 130 seconds for each request. Requests reaching the timeout will return a BANK.API_TIMEOUT error code (see reference above).
  • XS2A Session timeout:
    • Sessions from the XS2A-API time out after 30 minutes of inactivity.
    • Once the 30 minutes have passed, the session can not be interacted with anymore, meaning all data (such as flow results) has to be fetched before the timeout.
  • Bank Session timeout:
    • The connection to the bank times out after 5 minutes of inactivity. This will return a USER.SESSION.TIMEOUT error code (see reference above).
    • It is not possible to do further actions once the bank session has timed out, however, data (such as flow results) can still be fetched.

Invalid Requests

All responses with a response code >=400 should be handled as an error with the format described in this section.

    "error": {
        "code": String,
        "message": String,
        "errors": ?Array<ErrorDetails>

error_code String, always present

The error_code property indicates the type of the error.

error_message String, always present

The error_message contains the error message.

error_details ErrorDetails[], optional

Provides more information about the error(s).


    "code": ?String,
    "message": ?String,
    "location": ?String

code String, optional

The error_code property indicates a more detailed code of the error.

message String, optional

As message a more detailed error message can be provided.

location String, optional

The location shows line (and column) of the error, if applicable.

Error Examples

Request is missing parameters

HTTP 400 Bad request
    "error": {
        "code": "bad_request",
        "message": "IntendedReport is missing required parameters fromDate and toDate."

Validation error in request

HTTP 400 Bad request
    "error": {
        "code": "bad_request",
        "message": "Bad Request",
        "errors": [
                "message": "must not be null",
                "location": "insights_consumer_id"

API token is invalid

HTTP 403 Forbidden
    "error": {
        "code": "forbidden",
        "message": "HTTP 403 Forbidden"

API token is missing

HTTP 403 Forbidden
    "error": {
        "code": "illegalAuthorizationHeader",
        "message": "Authorization header not found or in wrong format"

results matching ""

    No results matching ""