taler-docs

Documentation for GNU Taler components, APIs and protocols
Log | Files | Refs | README | LICENSE

api-corebank.rst (62447B)


      1 ..
      2   This file is part of GNU TALER.
      3 
      4   Copyright (C) 2014-2025 Taler Systems SA
      5 
      6   TALER is free software; you can redistribute it and/or modify it under the
      7   terms of the GNU Affero General Public License as published by the Free Software
      8   Foundation; either version 2.1, or (at your option) any later version.
      9 
     10   TALER is distributed in the hope that it will be useful, but WITHOUT ANY
     11   WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
     12   A PARTICULAR PURPOSE.  See the GNU Affero General Public License for more details.
     13 
     14   You should have received a copy of the GNU Affero General Public License along with
     15   TALER; see the file COPYING.  If not, see <http://www.gnu.org/licenses/>
     16 
     17 .. target audience: developer, core developer
     18 
     19 .. _corebank-api:
     20 
     21 ====================
     22 Taler Core Bank API
     23 ====================
     24 
     25 .. contents:: Table of Contents
     26   :local:
     27 
     28 Introduction
     29 ------------
     30 
     31 The Libeufin bank provides a minimal core banking system.  In addition to that,
     32 it provides features for local/regional currencies.
     33 
     34 Version History
     35 ---------------
     36 
     37 The current protocol version is ``v11``.
     38 
     39 Android cashier app is currently targeting ``v9``.
     40 
     41 **Version history:**
     42 
     43 * ``v11``: Add observability API
     44 * ``v10``: Update two factor authentication API to match Merchant Backend API
     45 
     46 Config
     47 ------
     48 
     49 .. http:get:: /config
     50 
     51   Return the protocol version and configuration information about the bank.
     52   This specification corresponds to ``current`` protocol being version **v11**.
     53 
     54   **Response:**
     55 
     56   :http:statuscode:`200 OK`:
     57     Response is a `Config`.
     58 
     59   **Details:**
     60 
     61   .. ts:def:: Config
     62 
     63     interface Config {
     64       // Name of the API.
     65       name: "taler-corebank";
     66 
     67       // libtool-style representation of the Bank protocol version, see
     68       // https://www.gnu.org/software/libtool/manual/html_node/Versioning.html#Versioning
     69       // The format is "current:revision:age".
     70       version: string;
     71 
     72       // Bank display name to be used in user interfaces.
     73       // For consistency use "Taler Bank" if missing.
     74       // @since **v4**, will become mandatory in the next version.
     75       bank_name?: string;
     76 
     77       // Advertised base URL to use when you sharing an URL with another
     78       // program.
     79       // @since **v4**.
     80       base_url?: string;
     81 
     82       // If 'true' the server provides local currency conversion support
     83       // If 'false' some parts of the API are not supported and return 501
     84       allow_conversion: boolean;
     85 
     86       // If 'true' anyone can register
     87       // If 'false' only admin can
     88       allow_registrations: boolean;
     89 
     90       // If 'true' account can delete themselves
     91       // If 'false' only admin can delete accounts
     92       allow_deletions: boolean;
     93 
     94       // If 'true' anyone can edit their name
     95       // If 'false' only admin can
     96       allow_edit_name: boolean;
     97 
     98       // If 'true' anyone can edit their cashout account
     99       // If 'false' only admin can
    100       allow_edit_cashout_payto_uri: boolean;
    101 
    102       // Default debt limit for newly created accounts
    103       default_debit_threshold: Amount;
    104 
    105       // Currency used by this bank.
    106       currency: string;
    107 
    108       // How the bank SPA should render this currency.
    109       currency_specification: CurrencySpecification;
    110 
    111       // TAN channels supported by the server
    112       supported_tan_channels: TanChannel[];
    113 
    114       // Wire transfer type supported by the bank.
    115       // Defaults to 'iban' is missing
    116       // @since **v4**, will become mandatory in the next version.
    117       wire_type?: string;
    118 
    119       // Wire transfer execution fees. Only applies to bank transactions and withdrawals.
    120       // @since **v4**, will become mandatory in the next version.
    121       wire_transfer_fees?: Amount;
    122 
    123       // Minimum wire transfer amount allowed. Only applies to bank transactions and withdrawals.
    124       // @since **v4**, will become mandatory in the next version.
    125       min_wire_transfer_amount?: Amount;
    126 
    127       // Maximum wire transfer amount allowed. Only applies to bank transactions and withdrawals.
    128       // @since **v4**, will become mandatory in the next version.
    129       max_wire_transfer_amount?: Amount;
    130     }
    131 
    132 
    133 
    134 Authentication
    135 --------------
    136 
    137 Some endpoints requires the client to authenticate using a bearer token. Tokens can be obtained or refreshed using the ``/accounts/$USERNAME/token`` endpoint.
    138 This endpoint support authentication via HTTP Basic auth (RFC 7617). When using Basic authentication, the user-id must be the bank's username, and the password the password of the corresponding user.
    139 
    140 The user ``admin`` is a special, hard-coded username. Some requests require the client to authenticate as administrator.
    141 
    142 .. warning::
    143 
    144   Since **v7** Basic authentication for endpoints other than ``/accounts/$USERNAME/token`` has been deprecated and will no longer be supported in the next release.
    145 
    146 .. http:post:: /accounts/$USERNAME/token
    147 
    148   Create an authentification token.
    149 
    150   **Request:**
    151 
    152   .. ts:def:: TokenRequest
    153 
    154     interface TokenRequest {
    155       // Scope for the token.
    156       scope: "readonly" | "readwrite" | "revenue" | "wiregateway" | "observability";
    157 
    158       // Custom token validity duration
    159       duration?: RelativeTime;
    160 
    161       // Is the token refreshable into a new token during its
    162       // validity?
    163       // Refreshable tokens effectively provide indefinite
    164       // access if they are refreshed in time.
    165       refreshable?: boolean;
    166 
    167       // Optional token description
    168       // @since **v4**
    169       description?: string;
    170     }
    171 
    172   **Response:**
    173 
    174   :http:statuscode:`200 Ok`:
    175     Response is a `TokenSuccessResponse`.
    176   :http:statuscode:`202 Accepted`:
    177     2FA is required for this operation. This returns the `ChallengeResponse` response. @since **v10**
    178   :http:statuscode:`401 Unauthorized`:
    179     Invalid or missing credentials.
    180   :http:statuscode:`403 Forbidden`:
    181     * ``TALER_EC_GENERIC_FORBIDDEN``: missing rights.
    182     * ``TALER_EC_BANK_ACCOUNT_LOCKED``: account is locked and cannot create new token using its password.
    183 
    184   **Details:**
    185 
    186   .. ts:def:: TokenSuccessResponse
    187 
    188     interface TokenSuccessResponse {
    189       // Expiration determined by the server.
    190       // Can be based on the token_duration
    191       // from the request, but ultimately the
    192       // server decides the expiration.
    193       expiration: Timestamp;
    194 
    195       // Opque access token.
    196       access_token: string;
    197     }
    198 
    199 .. http:delete:: /accounts/$USERNAME/token
    200 
    201   Invalidate the access token that is being used to make the request.
    202 
    203   **Authentication:**  The client must authenticate with a valid access token.
    204 
    205   **Response:**
    206 
    207   :http:statuscode:`204 No content`:
    208     The token have been deleted.
    209   :http:statuscode:`401 Unauthorized`:
    210     Invalid or missing credentials.
    211   :http:statuscode:`403 Forbidden`:
    212     Missing rights.
    213 
    214 .. http:get:: /accounts/$USERNAME/tokens
    215 
    216   Retrieve a subset of tokens related to $USERNAME.
    217   @since **v4**
    218 
    219   **Request:**
    220 
    221   :query limit: *Optional.*
    222     At most return the given number of results. Negative for descending by ``token_id``, positive for ascending by ``token_id``. Defaults to ``-20``. Since **v5**.
    223   :query offset: *Optional.*
    224     Starting ``token_id`` for :ref:`pagination <row-id-pagination>`. Since **v5**.
    225   :query delta: *Optional.*
    226     Deprecated since **v5**. Use *limit* instead.
    227   :query start: *Optional.*
    228     Deprecated since **v5**. Use *offset* instead.
    229 
    230   **Response:**
    231 
    232   :http:statuscode:`200 OK`:
    233     Response is a `TokenInfos`.
    234   :http:statuscode:`204 No content`:
    235     No tokens.
    236   :http:statuscode:`401 Unauthorized`:
    237     Invalid or missing credentials.
    238   :http:statuscode:`403 Forbidden`:
    239     Mmissing rights.
    240 
    241   **Details:**
    242 
    243   .. ts:def:: TokenInfos
    244 
    245     interface TokenInfos {
    246       tokens: TokenInfo[];
    247     }
    248 
    249   .. ts:def:: TokenInfo
    250 
    251     interface TokenInfo {
    252       // Time when the token was created.
    253       creation_time: Timestamp;
    254 
    255       // Expiration determined by the server.
    256       // Can be based on the token_duration
    257       // from the request, but ultimately the
    258       // server decides the expiration.
    259       expiration: Timestamp;
    260 
    261       // Scope for the token.
    262       scope: "readonly" | "readwrite" | "revenue" | "wiregateway";
    263 
    264       // Is the token refreshable into a new token during its
    265       // validity?
    266       // Refreshable tokens effectively provide indefinite
    267       // access if they are refreshed in time.
    268       refreshable: boolean;
    269 
    270       // Optional token description
    271       description?: string;
    272 
    273       // Time when the token was last used.
    274       last_access: Timestamp;
    275 
    276       // ID identifying the token
    277       token_id: Integer;
    278 
    279       // deprecated since **v9**. Use *token_id* instead.
    280       row_id: Integer;
    281     }
    282 
    283 .. http:delete:: /accounts/$USERNAME/tokens/$TOKEN_ID
    284 
    285   Delete an access token.
    286 
    287   **Response:**
    288 
    289   :http:statuscode:`204 No content`:
    290     The token have been deleted.
    291   :http:statuscode:`404 Not found`:
    292     Token ``$TOKEN_ID`` was not found.
    293   :http:statuscode:`401 Unauthorized`:
    294     Invalid or missing credentials.
    295   :http:statuscode:`403 Forbidden`:
    296     Missing rights.
    297 
    298 Bank Web UI
    299 -----------
    300 
    301 The web UI for the bank is typically served under ``/``.
    302 
    303 
    304 Account Management
    305 ------------------
    306 
    307 .. _bank-account-register:
    308 
    309 .. http:post:: /accounts
    310 
    311   Create a new bank account.  Depending on the configuration,
    312   the account creation is self-serve, or only restricted to
    313   the administrators.
    314 
    315   **Request:**
    316 
    317   .. ts:def:: RegisterAccountRequest
    318 
    319     interface RegisterAccountRequest {
    320       // Username of the account
    321       // Must match [a-zA-Z0-9\-\._~]{1, 126}
    322       username: string;
    323 
    324       // Password of the account used for authentication
    325       password: string;
    326 
    327       // Legal name of the account owner
    328       name: string;
    329 
    330       // Make this account visible to anyone?
    331       // Defaults to false.
    332       is_public?: boolean;
    333 
    334       // Make this account a taler exchange account?
    335       // If true:
    336       // - incoming transactions to the account that do not
    337       //   have a valid reserve public key are automatically
    338       // - the account provides the taler-wire-gateway-api endpoints
    339       // Defaults to false.
    340       is_taler_exchange?: boolean;
    341 
    342       // Addresses where to send the TAN for protected operations.
    343       contact_data?: ChallengeContactData;
    344 
    345       // Payto URI of a fiat bank account.
    346       // Payments will be sent to this bank account
    347       // when the user wants to convert the regional currency
    348       // back to fiat currency outside bank.
    349       cashout_payto_uri?: string;
    350 
    351       // Simple payto URI of this bank account.
    352       // Used mostly for testing, this field is ignored if the bank payment
    353       // method is not IBAN.
    354       payto_uri?: string;
    355 
    356       // If present, set the max debit allowed for this user
    357       // Only admin can set this property.
    358       debit_threshold?: Amount;
    359 
    360       // If present, set the user conversion rate class
    361       // Only admin can set this property.
    362       // @since **v9**
    363       conversion_rate_class_id?: Integer;
    364 
    365       // @deprecated in **v10**
    366       // If present, enables 2FA and set the TAN channel used for challenges
    367       // Only admin can set this property, other user can reconfig their account
    368       // after creation.
    369       tan_channel?: TanChannel;
    370 
    371       // If present, enables 2FA and set the TAN channels used for challenges
    372       // Only admin can set this property, other user can reconfig their account
    373       // after creation.
    374       // @since **v10**
    375       tan_channels?: TanChannel[];
    376 
    377       // @deprecated in **v9**, use conversion_rate_class_id instead
    378       min_cashout?: Amount;
    379     }
    380 
    381   .. ts:def:: ChallengeContactData
    382 
    383     interface ChallengeContactData {
    384       // E-Mail address
    385       email?: EmailAddress;
    386 
    387       // Phone number.
    388       phone?: PhoneNumber;
    389     }
    390 
    391 
    392   **Response:**
    393 
    394   :http:statuscode:`200 OK`:
    395     Response is a `RegisterAccountResponse`.
    396   :http:statuscode:`400 Bad request`:
    397     Input data was invalid.  For example, the client specified a invalid
    398     phone number or e-mail address.
    399   :http:statuscode:`401 Unauthorized`:
    400     Invalid or missing credentials.
    401   :http:statuscode:`403 Forbidden`:
    402     Missing rights.
    403   :http:statuscode:`409 Conflict`:
    404     * ``TALER_EC_BANK_REGISTER_USERNAME_REUSE`` : username already used.
    405     * ``TALER_EC_BANK_REGISTER_PAYTO_URI_REUSE`` : payto URI already used.
    406     * ``TALER_EC_BANK_UNALLOWED_DEBIT`` : admin account does not have sufficient funds to grant bonus.
    407     * ``TALER_EC_BANK_RESERVED_USERNAME_CONFLICT`` : a reserved username was attempted, like ``admin`` or ``bank``
    408     * ``TALER_EC_BANK_NON_ADMIN_PATCH_DEBT_LIMIT`` : a non-admin user has tried to create an account with a customer debt limit.
    409     * ``TALER_EC_BANK_NON_ADMIN_SET_CONVERSION_RATE_CLASS`` : a non-admin user has tried to create an account with a conversion rate class. Since **v9**
    410     * ``TALER_EC_BANK_NON_ADMIN_SET_TAN_CHANNEL`` : a non-admin user has tried to create an account with 2fa.
    411     * ``TALER_EC_BANK_TAN_CHANNEL_NOT_SUPPORTED``: ``tan_channel`` or one of ``tan_channels`` is not supported, check bank config to find supported ones.
    412     * ``TALER_EC_BANK_MISSING_TAN_INFO``: the user did not share any contact data where to send the TAN via ``tan_channel`` or one of ``tan_channels``.
    413     * ``TALER_EC_BANK_PASSWORD_TOO_SHORT``: password is shorter than 8 characters.
    414     * ``TALER_EC_BANK_PASSWORD_TOO_LONG``: password is longer than 64 characters.
    415     * ``TALER_EC_BANK_CONVERSION_RATE_CLASS_UNKNOWN`` : no conversion rate class found for this id. Since **v9**
    416 
    417   **Details:**
    418 
    419   .. ts:def:: RegisterAccountResponse
    420 
    421     interface RegisterAccountResponse {
    422       // Full payto URI of this bank account.
    423       internal_payto_uri: string;
    424     }
    425 
    426 .. _account-reconfig:
    427 
    428 .. http:patch:: /accounts/$USERNAME
    429 
    430   Allows reconfiguring the account data of ``$USERNAME``.
    431 
    432   **Request:**
    433 
    434   .. ts:def:: AccountReconfiguration
    435 
    436     interface AccountReconfiguration {
    437       // Addresses where to send the TAN for protected operations.
    438       contact_data?: ChallengeContactData;
    439 
    440       // Payto URI of a fiat bank account.
    441       // Payments will be sent to this bank account
    442       // when the user wants to convert the regional currency
    443       // back to fiat currency outside bank.
    444       // Only admin can change this property if not allowed in config
    445       // Sending null will disable cashout
    446       cashout_payto_uri?: string | null;
    447 
    448       // If present, change the legal name associated with $username.
    449       // Only admin can change this property if not allowed in config
    450       name?: string;
    451 
    452       // Make this account visible to anyone?
    453       is_public?: boolean;
    454 
    455       // If present, change the max debit allowed for this user
    456       // Only admin can change this property.
    457       debit_threshold?: Amount;
    458 
    459       // If present, set the user conversion rate class
    460       // Only admin can set this property.
    461       // Sending null will remove the class and switch to default class
    462       // @since **v9**
    463       conversion_rate_class_id?: Integer | null;
    464 
    465       // @deprecated in **v10**
    466       // If present, enables 2FA and set the TAN channel used for challenges
    467       // Sending null will disable 2FA
    468       tan_channel?: TanChannel | null;
    469 
    470       // If present and not empty, enables 2FA and set the TAN channels used for challenges
    471       // Sending null or an empty array will disable 2FA
    472       // @since **v10**
    473       tan_channels?: TanChannel[] | null;
    474 
    475       // @deprecated in **v9**, user conversion rate classes instead
    476       min_cashout?: Amount;
    477     }
    478 
    479   **Response:**
    480 
    481   :http:statuscode:`202 Accepted`:
    482     2FA is required for this operation. This returns the `ChallengeResponse` response. @since **v10**
    483   :http:statuscode:`204 No content`:
    484     Operation successful.
    485   :http:statuscode:`401 Unauthorized`:
    486     Invalid or missing credentials.
    487   :http:statuscode:`403 Forbidden`:
    488     Missing rights.
    489   :http:statuscode:`404 Not found`:
    490     The account pointed by ``$USERNAME`` was not found.
    491   :http:statuscode:`409 Conflict`:
    492     * ``TALER_EC_BANK_NON_ADMIN_PATCH_LEGAL_NAME`` : a non-admin user has tried to change their legal name.
    493     * ``TALER_EC_BANK_NON_ADMIN_PATCH_CASHOUT`` : a non-admin user has tried to change their cashout account.
    494     * ``TALER_EC_BANK_NON_ADMIN_PATCH_DEBT_LIMIT`` : a non-admin user has tried to change their debt limit.
    495     * ``TALER_EC_BANK_NON_ADMIN_SET_CONVERSION_RATE_CLASS`` : a non-admin user has tried to create an account with a conversion rate class. Since **v9**
    496     * ``TALER_EC_BANK_TAN_CHANNEL_NOT_SUPPORTED`` : ``tan_channel`` or one of ``tan_channels`` is not supported, check bank config to find supported ones.
    497     * ``TALER_EC_BANK_MISSING_TAN_INFO`` : the user did not share any contact data where to send the TAN via ``tan_channel`` or one of ``tan_channels``.
    498     * ``TALER_EC_BANK_CONVERSION_RATE_CLASS_UNKNOWN`` : no conversion rate class found for this id. Since **v9**
    499 
    500 
    501 .. _account-password-reconfig:
    502 
    503 .. http:patch:: /accounts/$USERNAME/auth
    504 
    505   Allows changing the account's password.
    506 
    507 
    508   **Request:**
    509 
    510   .. ts:def:: AccountPasswordChange
    511 
    512     interface AccountPasswordChange {
    513       // Old password. If present it need to match the current
    514       // password before updating.
    515       old_password?: string;
    516       // New password.
    517       new_password: string;
    518     }
    519 
    520   **Response:**
    521 
    522   :http:statuscode:`202 Accepted`:
    523     2FA is required for this operation. This returns the `ChallengeResponse` response. @since **v10**
    524   :http:statuscode:`204 No content`:
    525     Operation successful.
    526   :http:statuscode:`404 Not found`:
    527     The account pointed by ``$USERNAME`` was not found.
    528   :http:statuscode:`401 Unauthorized`:
    529     Invalid or missing credentials.
    530   :http:statuscode:`403 Forbidden`:
    531     Missing rights.
    532   :http:statuscode:`409 Conflict`:
    533     * ``TALER_EC_BANK_NON_ADMIN_PATCH_MISSING_OLD_PASSWORD``: a non-admin user has tried to change their password whihout providing the current one.
    534     * ``TALER_EC_BANK_PATCH_BAD_OLD_PASSWORD`` : provided old password does not match current password.
    535     * ``TALER_EC_BANK_PASSWORD_TOO_SHORT``: new password is shorter than 8 characters.
    536     * ``TALER_EC_BANK_PASSWORD_TOO_LONG``: new password is longer than 64 characters.
    537 
    538 
    539 .. _delete-account:
    540 
    541 .. http:delete:: /accounts/$USERNAME
    542 
    543   Delete the account whose username is ``$USERNAME``.  The deletion
    544   succeeds only if the balance is *zero*.  Typically only available to
    545   the administrator, but can be configured to allow ordinary users too.
    546 
    547   **Response:**
    548 
    549   :http:statuscode:`202 Accepted`:
    550     2FA is required for this operation. This returns the `ChallengeResponse` response. @since **v10**
    551   :http:statuscode:`204 No content`:
    552     The account was successfully deleted.
    553   :http:statuscode:`401 Unauthorized`:
    554     Invalid or missing credentials.
    555   :http:statuscode:`403 Forbidden`:
    556     Missing rights.
    557   :http:statuscode:`404 Not found`:
    558     The account pointed by ``$USERNAME`` was not found.
    559   :http:statuscode:`409 Conflict`:
    560     * ``TALER_EC_BANK_RESERVED_USERNAME_CONFLICT`` : a reserved username was attempted, like ``admin`` or ``bank``.
    561     * ``TALER_EC_BANK_ACCOUNT_BALANCE_NOT_ZERO``: the account balance was not zero.
    562 
    563 .. _account-list:
    564 
    565 .. http:get:: /public-accounts
    566 
    567   Show those accounts whose histories are publicly visible.  For example,
    568   accounts from donation receivers.  As such, this request is unauthenticated.
    569 
    570   **Request:**
    571 
    572   :query limit: *Optional.*
    573     At most return the given number of results. Negative for descending by ``row_id``, positive for ascending by ``row_id``. Defaults to ``-20``. Since **v5**.
    574   :query offset: *Optional.*
    575     Starting ``row_id`` for :ref:`pagination <row-id-pagination>`. Since **v5**.
    576   :query filter_name: *Optional.*
    577     Pattern to filter on the account's legal name.  Given
    578     the filter 'foo', all the results will **contain**
    579     'foo' in their legal name.  Without this option,
    580     all the existing accounts are returned.
    581   :query delta: *Optional.*
    582     Deprecated since **v5**. Use *limit* instead.
    583   :query start: *Optional.*
    584     Deprecated since **v5**. Use *offset* instead.
    585 
    586   **Response:**
    587 
    588   :http:statuscode:`200 OK`:
    589     Response is a `PublicAccountsResponse`.
    590   :http:statuscode:`204 No content`:
    591     No public account.
    592 
    593   **Details:**
    594 
    595   .. ts:def:: PublicAccountsResponse
    596 
    597     interface PublicAccountsResponse {
    598       public_accounts: PublicAccount[];
    599     }
    600 
    601   .. ts:def:: PublicAccount
    602 
    603     interface PublicAccount {
    604       // Username of the account
    605       username: string;
    606 
    607       // Full payto URI of this bank account.
    608       payto_uri: string;
    609 
    610       // Current balance of the account
    611       balance: Balance;
    612 
    613       // Is this a taler exchange account?
    614       is_taler_exchange: boolean;
    615 
    616       // Opaque unique ID used for pagination.
    617       // @since **v4**, will become mandatory in the next version.
    618       row_id?: Integer;
    619     }
    620 
    621 .. http:get:: /accounts
    622 
    623   Obtains a list of the accounts registered at the bank.
    624   It returns only the information that this API handles, without
    625   any balance or transactions list.
    626   This request is only available to the administrator.
    627 
    628   **Request:**
    629 
    630   :query limit: *Optional.*
    631     At most return the given number of results. Negative for descending by ``row_id``, positive for ascending by ``row_id``. Defaults to ``-20``. Since **v5**.
    632   :query offset: *Optional.*
    633     Starting ``row_id`` for :ref:`pagination <row-id-pagination>`. Since **v5**.
    634   :query filter_name: *Optional.*
    635     Pattern to filter on the account's legal name.  Given
    636     the filter 'foo', all the accounts will **contain**
    637     'foo' in their legal name.  Without this option,
    638     all the existing accounts are returned.
    639   :query conversion_rate_class_id: *Optional.*
    640     Id of a conversion rate class. Given the filter '1', the accounts will be part of the conversion rate class 1. Given the filter '0', will have no conversion rate class. Without this option all the existing accounts are returned. Since **v9**.
    641   :query delta: *Optional.*
    642     Deprecated since **v5**. Use *limit* instead.
    643   :query start: *Optional.*
    644     Deprecated since **v5**. Use *offset* instead.
    645 
    646   **Response:**
    647 
    648   :http:statuscode:`200 OK`:
    649     At least one account was found.
    650     The server responds with a `ListBankAccountsResponse` object.
    651   :http:statuscode:`204 No Content`:
    652     No accounts were found for the given request.
    653   :http:statuscode:`401 Unauthorized`:
    654     Invalid or missing credentials.
    655   :http:statuscode:`403 Forbidden`:
    656     Missing rights.
    657 
    658   **Details:**
    659 
    660   .. ts:def:: ListBankAccountsResponse
    661 
    662     interface ListBankAccountsResponse {
    663       accounts: AccountMinimalData[];
    664     }
    665 
    666   .. ts:def:: Balance
    667 
    668     interface Balance {
    669       amount: Amount;
    670       credit_debit_indicator: "credit" | "debit";
    671     }
    672 
    673   .. ts:def:: AccountMinimalData
    674 
    675     interface AccountMinimalData {
    676       // Username of the account
    677       username: string;
    678 
    679       // Legal name of the account owner.
    680       name: string;
    681 
    682       // Full payto URI of this bank account.
    683       payto_uri: string;
    684 
    685       // Current balance of the account
    686       balance: Balance;
    687 
    688       // Number indicating the max debit allowed for the requesting user.
    689       debit_threshold: Amount;
    690 
    691       // Custom minimum cashout amount for this account.
    692       // If null or absent, the global conversion fee is used.
    693       // @since **v6**
    694       // @deprecated in **v9**, use conversion_rate_class_id instead
    695       min_cashout?: Amount;
    696 
    697       // Is this account visible to anyone?
    698       is_public: boolean;
    699 
    700       // Is this a taler exchange account?
    701       is_taler_exchange: boolean;
    702 
    703       // Is the account locked.
    704       // Defaults to false.
    705       // @deprecated since **v7**
    706       is_locked?: boolean;
    707 
    708       // Opaque unique ID used for pagination.
    709       // @since **v4**, will become mandatory in the next version.
    710       row_id?: Integer;
    711 
    712       // Current status of the account
    713       // active: the account can be used
    714       // locked: the account can be used but cannot create new tokens
    715       // @since **v7**
    716       // deleted: the account has been deleted but is retained for compliance
    717       // reasons, only the administrator can access it
    718       // Defaults to 'active' is missing
    719       // @since **v4**, will become mandatory in the next version.
    720       status?: "active" | "locked" | "deleted";
    721 
    722       // Conversion rate class of the user
    723       // Only present if conversion is activated on the server
    724       // @since **v9**
    725       conversion_rate_class_id?: Integer;
    726 
    727       // Conversion rate available to the user
    728       // Only present if conversion is activated on the server
    729       // @since **v9**
    730       conversion_rate?: ConversionRate;
    731     }
    732 
    733 .. _bank-account-info:
    734 
    735 .. http:get:: /accounts/$USERNAME
    736 
    737   Obtains information relative to the account owned by
    738   ``$USERNAME``.  The request is available to the administrator
    739   and ``$USERNAME`` itself.
    740 
    741   **Response:**
    742 
    743   :http:statuscode:`200 OK`:
    744     The bank responds with an `AccountData` object.
    745   :http:statuscode:`401 Unauthorized`:
    746     Invalid or missing credentials.
    747   :http:statuscode:`403 Forbidden`:
    748     Missing rights.
    749   :http:statuscode:`404 Not found`:
    750     The account pointed by ``$USERNAME`` was not found.
    751 
    752   **Details:**
    753 
    754   .. ts:def:: AccountData
    755 
    756     interface AccountData {
    757       // Legal name of the account owner.
    758       name: string;
    759 
    760       // Available balance on the account.
    761       balance: Balance;
    762 
    763       // Full payto URI of the account.
    764       payto_uri: string;
    765 
    766       // Number indicating the max debit allowed for the requesting user.
    767       debit_threshold: Amount;
    768 
    769       // Custom minimum cashout amount for this account.
    770       // If null or absent, the global conversion fee is used.
    771       // @since **v6**
    772       // @deprecated in **v9**, use conversion_rate_class_id instead
    773       min_cashout?: Amount;
    774 
    775       // Addresses where to send the TAN for transactions.
    776       // Currently only used for cashouts.
    777       // If missing, cashouts will fail.
    778       // In the future, might be used for other transactions
    779       // as well.
    780       contact_data?: ChallengeContactData;
    781 
    782       // Full 'payto' URI of a fiat bank account where to send cashouts with
    783       // ``name`` as the 'receiver-name'.
    784       // This field is optional
    785       // because not all the accounts are required to participate
    786       // in the merchants' circuit.  One example is the exchange:
    787       // that never cashouts.  Registering these accounts can
    788       // be done via the access API.
    789       cashout_payto_uri?: string;
    790 
    791       // Is this account visible to anyone?
    792       is_public: boolean;
    793 
    794       // Is this a taler exchange account?
    795       is_taler_exchange: boolean;
    796 
    797       // Is the account locked.
    798       // Defaults to false.
    799       // @deprecated since **v7**
    800       is_locked?: boolean;
    801 
    802       // @deprecated in **v10**
    803       // Is 2FA enabled and what channel is used for challenges?
    804       tan_channel?: TanChannel;
    805 
    806       // Is 2FA enabled and what channels are used for challenges?
    807       // @since **v10**
    808       tan_channels?: TanChannel[];
    809 
    810       // Current status of the account
    811       // active: the account can be used
    812       // locked: the account can be used but cannot create new tokens
    813       // @since **v7**
    814       // deleted: the account has been deleted but is retained for compliance
    815       // reasons, only the administrator can access it
    816       // Defaults to 'active' is missing
    817       // @since **v4**, will become mandatory in the next version.
    818       status?: "active" | "locked" | "deleted";
    819 
    820       // Conversion rate class of the user
    821       // Only present if conversion is activated on the server
    822       // @since **v9**
    823       conversion_rate_class_id?: Integer;
    824     }
    825 
    826 Transactions
    827 ------------
    828 
    829 .. http:get:: /accounts/$USERNAME/transactions
    830 
    831   Retrieve a subset of transactions related to $USERNAME.
    832 
    833   **Request:**
    834 
    835   :query limit: *Optional.*
    836     At most return the given number of results. Negative for descending by ``row_id``, positive for ascending by ``row_id``. Defaults to ``-20``. Since **v5**.
    837   :query offset: *Optional.*
    838     Starting ``row_id`` for :ref:`pagination <row-id-pagination>`. Since **v5**.
    839   :query timeout_ms: *Optional.*
    840     Timeout in milliseconds, for :ref:`long-polling <long-polling>`, to wait for at least one element to be shown. Only useful if *limit* is positive. Since protocol **v5**.
    841   :query delta: *Optional.*
    842     Deprecated since **v5**. Use *limit* instead.
    843   :query start: *Optional.*
    844     Deprecated since **v5**. Use *offset* instead.
    845   :query long_poll_ms: *Optional.*
    846     Deprecated since **v5**. Use *timeout_ms* instead.
    847 
    848   **Response:**
    849 
    850   :http:statuscode:`200 OK`:
    851     The bank responds with an `BankAccountTransactionsResponse` object.
    852   :http:statuscode:`204 No content`:
    853     No transaction found.
    854   :http:statuscode:`401 Unauthorized`:
    855     Invalid or missing credentials.
    856   :http:statuscode:`403 Forbidden`:
    857     Missing rights.
    858   :http:statuscode:`404 Not found`:
    859     The account pointed by ``$USERNAME`` was not found.
    860 
    861   **Details:**
    862 
    863   .. ts:def:: BankAccountTransactionsResponse
    864 
    865     interface BankAccountTransactionsResponse {
    866       transactions: BankAccountTransactionInfo[];
    867     }
    868 
    869 .. http:get:: /accounts/$USERNAME/transactions/$TRANSACTION_ID
    870 
    871   Retrieve the transaction whose identifier is ``TRANSACTION_ID``.
    872 
    873   **Response:**
    874 
    875   :http:statuscode:`200 OK`:
    876     The bank responds with an `BankAccountTransactionInfo` object.
    877   :http:statuscode:`401 Unauthorized`:
    878     Invalid or missing credentials.
    879   :http:statuscode:`403 Forbidden`:
    880     Missing rights.
    881   :http:statuscode:`404 Not found`:
    882     The account pointed by ``$USERNAME`` was not found.
    883 
    884   **Details:**
    885 
    886   .. ts:def:: BankAccountTransactionInfo
    887 
    888     interface BankAccountTransactionInfo {
    889       // Full payto URI to identify the receiver of funds.
    890       creditor_payto_uri: string;
    891 
    892       // Full payto URI to identify the sender of funds.
    893       debtor_payto_uri: string;
    894 
    895       // Amount received.
    896       amount: Amount;
    897 
    898       // The direction of the transaction relative to $USERNAME account.
    899       // debit: $USERNAME is the debtor
    900       // credit: $USERNAME is the creditor
    901       direction: "debit" | "credit";
    902 
    903       // The wire transfer subjec
    904       subject: string;
    905 
    906       // Transaction unique ID.  Matches
    907       // $TRANSACTION_ID from the URI.
    908       row_id: Integer;
    909 
    910       // Date of the transaction.
    911       date: Timestamp;
    912     }
    913 
    914 .. http:post:: /accounts/$USERNAME/transactions
    915 
    916   Create a new transaction where the bank account with the label ``USERNAME`` is **debited**.
    917 
    918   **Request:**
    919 
    920   .. ts:def:: CreateTransactionRequest
    921 
    922     interface CreateTransactionRequest {
    923       // Address in the payto format of the wire transfer receiver.
    924       // It needs at least the 'message' query string parameter.
    925       payto_uri: string;
    926 
    927       // Transaction amount (in the $currency:x.y format), optional.
    928       // However, when not given, its value must occupy the 'amount'
    929       // query string parameter of the 'payto' field.  In case it
    930       // is given in both places, the payto_uri's takes the precedence.
    931       amount: string;
    932 
    933       // Nonce to make the request idempotent.  Requests with the same
    934       // ``request_uid`` that differ in any of the other fields
    935       // are rejected.
    936       // @since **v4**, will become mandatory in the next version.
    937       request_uid?: ShortHashCode;
    938     }
    939 
    940   **Response:**
    941 
    942   :http:statuscode:`200 Ok`:
    943     The bank responds with an `CreateTransactionResponse` object.
    944   :http:statuscode:`202 Accepted`:
    945     2FA is required for this operation. This returns the `ChallengeResponse` response. @since **v10**
    946   :http:statuscode:`400 Bad Request`:
    947     The request was invalid or the payto://-URI used unacceptable features.
    948   :http:statuscode:`401 Unauthorized`:
    949     Invalid or missing credentials.
    950   :http:statuscode:`403 Forbidden`:
    951     Missing rights.
    952   :http:statuscode:`404 Not found`:
    953     The account pointed by ``$USERNAME`` was not found.
    954   :http:statuscode:`409 Conflict`:
    955     * ``TALER_EC_BANK_SAME_ACCOUNT`` : creditor account is the same than ``USERNAME``.
    956     * ``TALER_EC_BANK_UNKNOWN_CREDITOR`` : creditor account was not found.
    957     * ``TALER_EC_BANK_UNALLOWED_DEBIT`` : the account does not have sufficient funds or the amount is too low or too high.
    958     * ``TALER_EC_BANK_TRANSFER_REQUEST_UID_REUSED``: an operation with the same ``request_uid`` but different details has been submitted before.
    959 
    960   **Details:**
    961 
    962   .. ts:def:: CreateTransactionResponse
    963 
    964     interface CreateTransactionResponse {
    965       // ID identifying the transaction being created
    966       row_id: Integer;
    967     }
    968 
    969 Account withdrawals
    970 -------------------
    971 
    972 .. http:post:: /accounts/$USERNAME/withdrawals
    973 
    974   Create a withdrawal operation, resulting in a ``taler://withdraw`` URI.
    975 
    976   **Request:**
    977 
    978   The request must be a `BankAccountCreateWithdrawalRequest`.
    979 
    980   **Response:**
    981 
    982   :http:statuscode:`200 Ok`:
    983     The bank responds with an `BankAccountCreateWithdrawalResponse` object.
    984   :http:statuscode:`401 Unauthorized`:
    985     Invalid or missing credentials.
    986   :http:statuscode:`403 Forbidden`:
    987     Missing rights.
    988   :http:statuscode:`404 Not found`:
    989     The account pointed by ``$USERNAME`` was not found.
    990   :http:statuscode:`409 Conflict`:
    991     The account does not have sufficient funds.
    992 
    993   **Details:**
    994 
    995   .. ts:def:: BankAccountCreateWithdrawalRequest
    996 
    997     interface BankAccountCreateWithdrawalRequest {
    998       // Amount to withdraw.  If given, the wallet
    999       // cannot change the amount.
   1000       // Optional since **v6**.
   1001       amount?: Amount;
   1002 
   1003       // Suggested amount to withdraw. The wallet can
   1004       // still change the suggestion.
   1005       // @since **v6**
   1006       suggested_amount?: Amount;
   1007 
   1008       // If true, tell the wallet not to allow the user to
   1009       // specify an amount to withdraw and to not provide
   1010       // any amount when registering with the withdrawal
   1011       // operation. The amount to withdraw will be set
   1012       // by the final ``/withdrawals/$WITHDRAWAL_ID/confirm`` step.
   1013       // @since **v8**
   1014       no_amount_to_wallet?: boolean;
   1015     }
   1016 
   1017   .. ts:def:: BankAccountCreateWithdrawalResponse
   1018 
   1019     interface BankAccountCreateWithdrawalResponse {
   1020       // ID identifying the operation being created
   1021       withdrawal_id: string;
   1022 
   1023       // URI that can be passed to the wallet to initiate the withdrawal
   1024       taler_withdraw_uri: string;
   1025     }
   1026 
   1027 .. http:post:: /accounts/$USERNAME/withdrawals/$WITHDRAWAL_ID/confirm
   1028 
   1029   Confirms ``WITHDRAWAL_ID`` operation.  Has no effect on an already confirmed
   1030   withdrawal operation.  This call is responsible for wiring the funds to the
   1031   exchange.
   1032 
   1033   **Request:**
   1034 
   1035   .. ts:def:: BankAccountConfirmWithdrawalRequest
   1036 
   1037     interface BankAccountConfirmWithdrawalRequest {
   1038 
   1039       // Selected amount to be transferred. Optional if the
   1040       // backend already knows the amount.
   1041       // @since **v6**
   1042       amount?: Amount;
   1043     }
   1044 
   1045 
   1046   **Response:**
   1047 
   1048   :http:statuscode:`202 Accepted`:
   1049     2FA is required for this operation. This returns the `ChallengeResponse` response. @since **v10**
   1050   :http:statuscode:`204 No content`:
   1051     The withdrawal operation has been confirmed.
   1052   :http:statuscode:`401 Unauthorized`:
   1053     Invalid or missing credentials.
   1054   :http:statuscode:`403 Forbidden`:
   1055     Missing rights.
   1056   :http:statuscode:`404 Not found`:
   1057     The operation was not found.
   1058   :http:statuscode:`409 Conflict`:
   1059     * ``TALER_EC_BANK_CONFIRM_ABORT_CONFLICT`` : the withdrawal has been aborted previously and can't be confirmed.
   1060     * ``TALER_EC_BANK_CONFIRM_INCOMPLETE`` : the withdraw operation cannot be confirmed because no exchange and reserve public key selection happened before.
   1061     * ``TALER_EC_BANK_UNALLOWED_DEBIT`` : the account does not have sufficient funds or the amount is too low or too high.
   1062     * ``TALER_EC_BANK_AMOUNT_DIFFERS`` : the specified amount will not work for this withdrawal (since **v6**).
   1063     * ``TALER_EC_BANK_AMOUNT_REQUIRED`` : the backend requires an amount to be specified  (since **v6**).
   1064 
   1065 .. http:post:: /accounts/$USERNAME/withdrawals/$WITHDRAWAL_ID/abort
   1066 
   1067   Aborts ``WITHDRAWAL_ID`` operation.  Has no effect on an already aborted
   1068   operation.
   1069 
   1070   **Response:**
   1071 
   1072   :http:statuscode:`204 No content`:
   1073     The withdrawal operation has been aborted.
   1074   :http:statuscode:`401 Unauthorized`:
   1075     Invalid or missing credentials.
   1076   :http:statuscode:`403 Forbidden`:
   1077     Missing rights.
   1078   :http:statuscode:`404 Not found`:
   1079     The withdrawal operation was not found.
   1080   :http:statuscode:`409 Conflict`:
   1081     The withdrawal operation has been confirmed previously and can't be aborted.
   1082 
   1083 .. http:get:: /withdrawals/$WITHDRAWAL_ID
   1084 
   1085   Retrieve public information about ``WITHDRAWAL_ID`` withdrawal operation.
   1086   Does not require further authentication as knowledge of ``WITHDRAWAL_ID``
   1087   serves as an authenticator.
   1088 
   1089   **Request:**
   1090 
   1091   :query old_state:
   1092     *Optional.* Defaults to "pending".
   1093   :query timeout_ms: *Optional.*
   1094     Timeout in milliseconds, for :ref:`long-polling <long-polling>`, to wait for the operation state to be different from *old_state*. Since **v5**.
   1095   :query long_poll_ms: *Optional.*
   1096     Deprecated since **v5.** Use *timeout_ms* instead.
   1097 
   1098   **Response:**
   1099 
   1100   :http:statuscode:`200 Ok`:
   1101     The bank responds with an `WithdrawalPublicInfo` object.
   1102   :http:statuscode:`404 Not found`:
   1103     The operation was not found.
   1104 
   1105   **Details:**
   1106 
   1107   .. ts:def:: WithdrawalPublicInfo
   1108 
   1109     interface WithdrawalPublicInfo {
   1110       // Current status of the operation
   1111       // pending: the operation is pending parameters selection (exchange and reserve public key)
   1112       // selected: the operations has been selected and is pending confirmation
   1113       // aborted: the operation has been aborted
   1114       // confirmed: the transfer has been confirmed and registered by the bank
   1115       status: "pending" | "selected" | "aborted" | "confirmed";
   1116 
   1117       // Amount that will be withdrawn with this operation
   1118       // (raw amount without fee considerations).  Only
   1119       // given once the amount is fixed and cannot be changed.
   1120       // Optional since **v6**.
   1121       amount?: Amount;
   1122 
   1123       // Suggestion for the amount to be withdrawn with this
   1124       // operation.  Given if a suggestion was made but the
   1125       // user may still change the amount.
   1126       // Optional since **v6**.
   1127       suggested_amount?: Amount;
   1128 
   1129       // If true, the wallet must not allow the user to
   1130       // specify an amount to withdraw and to not provide
   1131       // any amount when registering with the withdrawal
   1132       // operation. The amount to withdraw will be set
   1133       // by the final ``/withdrawals/$WITHDRAWAL_ID/confirm`` step.
   1134       // @since **v8**
   1135       no_amount_to_wallet?: boolean;
   1136 
   1137       // Account username
   1138       username: string;
   1139 
   1140       // Reserve public key selected by the exchange,
   1141       // only non-null if ``status`` is ``selected`` or ``confirmed``.
   1142       selected_reserve_pub?: string;
   1143 
   1144       // Exchange account selected by the wallet
   1145       // only non-null if ``status`` is ``selected`` or ``confirmed``.
   1146       selected_exchange_account?: string;
   1147     }
   1148 
   1149 Cashouts
   1150 --------
   1151 
   1152 .. _account-cashout:
   1153 
   1154 .. http:post:: /accounts/$USERNAME/cashouts
   1155 
   1156   Initiates a conversion to fiat currency.  The fiat
   1157   bank account to be
   1158   credited is the one specified at registration time via the
   1159   *cashout_payto_uri* parameter.  The regional bank account
   1160   is specified via ``$USERNAME``.
   1161 
   1162   .. note::
   1163 
   1164     Consult the `cashout rates call <cashout-rates_>`_ to learn
   1165     about any applicable fee or exchange rate.
   1166 
   1167 
   1168   **Request:**
   1169 
   1170   .. ts:def:: CashoutRequest
   1171 
   1172     interface CashoutRequest {
   1173       // Nonce to make the request idempotent.  Requests with the same
   1174       // ``request_uid`` that differ in any of the other fields
   1175       // are rejected.
   1176       request_uid: ShortHashCode;
   1177 
   1178       // Optional subject to associate to the
   1179       // cashout operation.  This data will appear
   1180       // as the incoming wire transfer subject in
   1181       // the user's fiat bank account.
   1182       subject?: string;
   1183 
   1184       // That is the plain amount that the user specified
   1185       // to cashout.  Its $currency is the (regional) currency of the
   1186       // bank instance.
   1187       amount_debit: Amount;
   1188 
   1189       // That is the amount that will effectively be
   1190       // transferred by the bank to the user's fiat bank
   1191       // account.
   1192       // It is expressed in the fiat currency and
   1193       // is calculated after the cashout fee and the
   1194       // exchange rate.  See the /cashout-rate call.
   1195       // The client needs to calculate this amount
   1196       // correctly based on the amount_debit and the cashout rate,
   1197       // otherwise the request will fail.
   1198       amount_credit: Amount;
   1199     }
   1200 
   1201   **Response:**
   1202 
   1203   :http:statuscode:`200 OK`:
   1204     The cashout request was correctly created.
   1205     This returns the `CashoutResponse` response.
   1206   :http:statuscode:`202 Accepted`:
   1207     2FA is required for this operation. This returns the `ChallengeResponse` response. @since **v10**
   1208   :http:statuscode:`401 Unauthorized`:
   1209     Invalid or missing credentials.
   1210   :http:statuscode:`403 Forbidden`:
   1211     Missing rights.
   1212   :http:statuscode:`404 Not found`:
   1213     The account pointed by ``$USERNAME`` was not found.
   1214   :http:statuscode:`409 Conflict`:
   1215     * ``TALER_EC_BANK_TRANSFER_REQUEST_UID_REUSED``: an operation with the same ``request_uid`` but different details has been submitted before.
   1216     * ``TALER_EC_BANK_BAD_CONVERSION``: exchange rate was calculated incorrectly by the client.
   1217     * ``TALER_EC_BANK_BANK_CONVERSION_AMOUNT_TO_SMALL``: the amount of the cashout is too small.
   1218     * ``TALER_EC_BANK_UNALLOWED_DEBIT``: the account does not have sufficient funds or the amount is too low or too high.
   1219     * ``TALER_EC_BANK_CONFIRM_INCOMPLETE``: the user did not share any cashout payto to uri where to wire funds.
   1220   :http:statuscode:`501 Not Implemented`:
   1221     * ``TALER_EC_BANK_TAN_CHANNEL_NOT_SUPPORTED``: the chosen ``tan_channel`` or one of ``tan_channels`` is not currently supported.
   1222     * This server does not support conversion, client should check config response.
   1223 
   1224   **Details:**
   1225 
   1226   .. ts:def:: CashoutResponse
   1227 
   1228     interface CashoutResponse {
   1229       // ID identifying the operation being created
   1230       cashout_id: Integer;
   1231     }
   1232 
   1233 .. _circuit-cashout-details:
   1234 
   1235 .. http:get:: /accounts/$USERNAME/cashouts/$CASHOUT_ID
   1236 
   1237   Returns information about the status of the ``$CASHOUT_ID`` operation.
   1238   The request is available to the administrator and the account owner.
   1239 
   1240   **Response:**
   1241 
   1242   :http:statuscode:`200 OK`:
   1243     Response is a `CashoutStatusResponse`.
   1244   :http:statuscode:`401 Unauthorized`:
   1245     Invalid or missing credentials.
   1246   :http:statuscode:`403 Forbidden`:
   1247     Missing rights.
   1248   :http:statuscode:`404 Not found`:
   1249     The cashout operation was not found.
   1250   :http:statuscode:`501 Not implemented`:
   1251     This server does not support conversion, client should check config response.
   1252 
   1253   **Details:**
   1254 
   1255   .. ts:def:: CashoutStatusResponse
   1256 
   1257     interface CashoutStatusResponse {
   1258       // Amount debited to the regional bank account.
   1259       amount_debit: Amount;
   1260 
   1261       // Amount credited to the fiat bank account.
   1262       amount_credit: Amount;
   1263 
   1264       // Transaction subject.
   1265       subject: string;
   1266 
   1267       // Time when the cashout was created.
   1268       creation_time: Timestamp;
   1269     }
   1270 
   1271 .. _circuit-cashouts:
   1272 
   1273 .. http:get:: /accounts/$USERNAME/cashouts
   1274 
   1275   Returns the list of all cash-out operations for an account.
   1276 
   1277   **Request:**
   1278 
   1279   :query limit: *Optional.*
   1280     At most return the given number of results. Negative for descending by ``cashout_id``, positive for ascending by ``cashout_id``. Defaults to ``-20``. Since **v5**.
   1281   :query offset: *Optional.*
   1282     Starting ``cashout_id`` for :ref:`pagination <row-id-pagination>`. Since **v5**.
   1283   :query delta: *Optional.*
   1284     Deprecated since **v5**. Use *limit* instead.
   1285   :query start: *Optional.*
   1286     Deprecated since **v5**. Use *offset* instead.
   1287 
   1288   **Response:**
   1289 
   1290   :http:statuscode:`200 OK`:
   1291     Response is a `Cashouts`.
   1292   :http:statuscode:`204 No Content`:
   1293     No cash-out operations were found.
   1294   :http:statuscode:`401 Unauthorized`:
   1295     Invalid or missing credentials.
   1296   :http:statuscode:`403 Forbidden`:
   1297     Missing rights.
   1298   :http:statuscode:`501 Not implemented`:
   1299     This server does not support conversion, client should check config response.
   1300 
   1301   **Details:**
   1302 
   1303   .. ts:def:: Cashouts
   1304 
   1305     interface Cashouts {
   1306       // Every string represents a cash-out operation ID.
   1307       cashouts: CashoutInfo[];
   1308     }
   1309 
   1310   .. ts:def:: CashoutInfo
   1311 
   1312     interface CashoutInfo {
   1313       cashout_id: Integer;
   1314     }
   1315 
   1316 .. http:get:: /cashouts
   1317 
   1318   Returns the list of all cash-out operations for **all** accounts.
   1319 
   1320   Can only be used by the administrators.
   1321 
   1322   **Request:**
   1323 
   1324   :query limit: *Optional.*
   1325     At most return the given number of results. Negative for descending by ``cashout_id``, positive for ascending by ``cashout_id``. Defaults to ``-20``. Since **v5**.
   1326   :query offset: *Optional.*
   1327     Starting ``cashout_id`` for :ref:`pagination <row-id-pagination>`. Since **v5**.
   1328   :query delta: *Optional.*
   1329     Deprecated since **v5**. Use *limit* instead.
   1330   :query start: *Optional.*
   1331     Deprecated since **v5**. Use *offset* instead.
   1332 
   1333   .. note::
   1334 
   1335     We might want to add a filter in the future to only
   1336     query pending cashout operations.
   1337 
   1338   **Response:**
   1339 
   1340   :http:statuscode:`200 OK`:
   1341     Response is a `GlobalCashouts`.
   1342   :http:statuscode:`204 No Content`:
   1343     No cash-out operations were found.
   1344   :http:statuscode:`401 Unauthorized`:
   1345     Invalid or missing credentials.
   1346   :http:statuscode:`403 Forbidden`:
   1347     Missing rights.
   1348   :http:statuscode:`501 Not implemented`:
   1349     This server does not support conversion, client should check config response.
   1350 
   1351   **Details:**
   1352 
   1353   .. ts:def:: GlobalCashouts
   1354 
   1355     interface GlobalCashouts {
   1356       cashouts: GlobalCashoutInfo[];
   1357     }
   1358 
   1359   .. ts:def:: GlobalCashoutInfo
   1360 
   1361     interface GlobalCashoutInfo {
   1362       cashout_id: Integer;
   1363       username: string;
   1364     }
   1365 
   1366 Conversion rate class
   1367 ---------------------
   1368 
   1369 .. http:post:: /conversion-rate-classes
   1370 
   1371   Create a new conversion rate classe.
   1372 
   1373   Only available to the administrator.
   1374 
   1375   Since protocol **v9**.
   1376 
   1377   **Request:**
   1378 
   1379   .. ts:def:: ConversionRateClassInput
   1380 
   1381     interface ConversionRateClassInput {
   1382       // The name of this class
   1383       name: string;
   1384 
   1385       // A description of the class
   1386       description?: string;
   1387 
   1388       // Minimum fiat amount authorised for cashin before conversion
   1389       cashin_min_amount?: Amount;
   1390 
   1391       // Exchange rate to buy regional currency from fiat
   1392       cashin_ratio?: DecimalNumber;
   1393 
   1394       // Regional amount fee to subtract after applying the cashin ratio.
   1395       cashin_fee?: Amount;
   1396 
   1397       // Rounding mode used during cashin conversion
   1398       cashin_rounding_mode?: "zero" | "up" | "nearest";
   1399 
   1400       // Minimum regional amount authorised for cashout before conversion
   1401       cashout_min_amount?: Amount;
   1402 
   1403       // Exchange rate to sell regional currency for fiat
   1404       cashout_ratio?: DecimalNumber;
   1405 
   1406       // Fiat amount fee to subtract after applying the cashout ratio.
   1407       cashout_fee?: Amount;
   1408 
   1409       // Rounding mode used during cashout conversion
   1410       cashout_rounding_mode?: "zero" | "up" | "nearest";
   1411     }
   1412 
   1413   **Response:**
   1414 
   1415   :http:statuscode:`200 OK`:
   1416     The conversion rate class request was correctly created.
   1417     This returns the `ConversionRateClassResponse` response.
   1418   :http:statuscode:`401 Unauthorized`:
   1419     Invalid or missing credentials.
   1420   :http:statuscode:`403 Forbidden`:
   1421     Missing rights.
   1422   :http:statuscode:`409 Conflict`:
   1423     * ``TALER_EC_BANK_NAME_REUSE`` : name already used.
   1424   :http:statuscode:`501 Not implemented`:
   1425     This server does not support conversion, client should check config response.
   1426 
   1427   **Details:**
   1428 
   1429   .. ts:def:: ConversionRateClassResponse
   1430 
   1431     interface ConversionRateClassResponse {
   1432       // ID identifying the conversion rate class being created
   1433       conversion_rate_class_id: Integer;
   1434     }
   1435 
   1436 .. http:patch:: /conversion-rate-classes/{CLASS_ID}
   1437 
   1438   Edit an existing conversion rate class.
   1439 
   1440   Only available to the administrator.
   1441 
   1442   Since protocol **v9**.
   1443 
   1444   **Request:**
   1445 
   1446   `ConversionRateClassInput`
   1447 
   1448   **Response:**
   1449 
   1450   :http:statuscode:`204 No Content`:
   1451     The conversion rate class request was correctly edited.
   1452   :http:statuscode:`401 Unauthorized`:
   1453     Invalid or missing credentials.
   1454   :http:statuscode:`403 Forbidden`:
   1455     Missing rights.
   1456   :http:statuscode:`404 Not Found`:
   1457     The conversion rate class was not found.
   1458   :http:statuscode:`409 Conflict`:
   1459     * ``TALER_EC_BANK_NAME_REUSE`` : name already used.
   1460   :http:statuscode:`501 Not implemented`:
   1461     This server does not support conversion, client should check config response.
   1462 
   1463 .. http:delete:: /conversion-rate-classes/{CLASS_ID}
   1464 
   1465   Delete an existing conversion rate class.
   1466 
   1467   Only available to the administrator.
   1468 
   1469   Since protocol **v9**.
   1470 
   1471   **Response:**
   1472 
   1473   :http:statuscode:`204 No Content`:
   1474     The conversion rate class request was correctly deleted.
   1475   :http:statuscode:`401 Unauthorized`:
   1476     Invalid or missing credentials.
   1477   :http:statuscode:`403 Forbidden`:
   1478     Missing rights.
   1479   :http:statuscode:`404 Not Found`:
   1480     The conversion rate class was not found.
   1481   :http:statuscode:`409 Conflict`:
   1482     * ``TODO_LINKED_ACCOUNT`` : some accounts belongs to this class.
   1483   :http:statuscode:`501 Not implemented`:
   1484     This server does not support conversion, client should check config response.
   1485 
   1486 .. http:get:: /conversion-rate-classes/{CLASS_ID}
   1487 
   1488   Get an existing conversion rate class.
   1489 
   1490   Only available to the administrator.
   1491 
   1492   Since protocol **v9**.
   1493 
   1494   **Response:**
   1495 
   1496   :http:statuscode:`200 OK`:
   1497     Response is a `ConversionRateClass`.
   1498   :http:statuscode:`401 Unauthorized`:
   1499     Invalid or missing credentials.
   1500   :http:statuscode:`403 Forbidden`:
   1501     Missing rights.
   1502   :http:statuscode:`404 Not Found`:
   1503     The conversion rate class was not found.
   1504   :http:statuscode:`501 Not implemented`:
   1505     This server does not support conversion, client should check config response.
   1506 
   1507   **Details:**
   1508 
   1509   .. ts:def:: ConversionRateClassResponse
   1510 
   1511     interface ConversionRateClass {
   1512       // The name of this class
   1513       name: string;
   1514 
   1515       // A description of the class
   1516       description?: string;
   1517 
   1518       // Class unique ID
   1519       conversion_rate_class_id: Integer;
   1520 
   1521       // Number of users affected to this class
   1522       num_users: Integer;
   1523 
   1524       // Minimum fiat amount authorised for cashin before conversion
   1525       cashin_min_amount?: Amount;
   1526 
   1527       // Exchange rate to buy regional currency from fiat
   1528       cashin_ratio?: DecimalNumber;
   1529 
   1530       // Regional amount fee to subtract after applying the cashin ratio.
   1531       cashin_fee?: Amount;
   1532 
   1533       // Rounding mode used during cashin conversion
   1534       cashin_rounding_mode?: "zero" | "up" | "nearest";
   1535 
   1536       // Minimum regional amount authorised for cashout before conversion
   1537       cashout_min_amount?: Amount;
   1538 
   1539       // Exchange rate to sell regional currency for fiat
   1540       cashout_ratio?: DecimalNumber;
   1541 
   1542       // Fiat amount fee to subtract after applying the cashout ratio.
   1543       cashout_fee?: Amount;
   1544 
   1545       // Rounding mode used during cashout conversion
   1546       cashout_rounding_mode?: "zero" | "up" | "nearest";
   1547     }
   1548 
   1549 .. http:get:: /conversion-rate-classes
   1550 
   1551   Returns the list of all conversion rate classes.
   1552 
   1553   Only available to the administrator.
   1554 
   1555   Since protocol **v9**.
   1556 
   1557   **Request:**
   1558 
   1559   :query limit: *Optional.*
   1560     At most return the given number of results. Negative for descending by ``conversion_rate_class_id``, positive for ascending by ``conversion_rate_class_id``. Defaults to ``-20``.
   1561   :query offset: *Optional.*
   1562     Starting ``conversion_rate_class_id`` for :ref:`pagination <row-id-pagination>`.
   1563   :query filter_name: *Optional.*
   1564     Pattern to filter on the class name.  Given
   1565     the filter 'foo', all the classes will **contain**
   1566     'foo' in their name.  Without this option,
   1567     all the existing classes are returned.
   1568 
   1569   **Response:**
   1570 
   1571   :http:statuscode:`200 OK`:
   1572     Response is a `ConversionRateClasses`.
   1573   :http:statuscode:`401 Unauthorized`:
   1574     Invalid or missing credentials.
   1575   :http:statuscode:`403 Forbidden`:
   1576     Missing rights.
   1577   :http:statuscode:`404 Not Found`:
   1578     The conversion rate class was not found.
   1579   :http:statuscode:`501 Not implemented`:
   1580     This server does not support conversion, client should check config response.
   1581 
   1582   **Details:**
   1583 
   1584   .. ts:def:: ConversionRateClasses
   1585 
   1586     interface ConversionRateClasses {
   1587       classes: ConversionRateClass[];
   1588     }
   1589 
   1590 
   1591 Two Factor Auth
   1592 ---------------
   1593 
   1594 202 Challenge Responses
   1595 ^^^^^^^^^^^^^^^^^^^^^^^
   1596 
   1597 Various APIs generate ``202 Accepted`` HTTP status codes when multi-factor
   1598 authentication (MFA) is required.  In this case, the response will be a
   1599 `ChallengeResponse`.  In these cases, the client must first request and solve
   1600 one or more challenges before repeating the request. When repeating the
   1601 request, they must include a list of comma-separated challenge IDs of the
   1602 solved challenges in an ``Taler-Challenge-Ids`` HTTP header. The body must
   1603 remain absolutely unchanged.
   1604 
   1605 .. note::
   1606 
   1607   If all allowed attempts to solve the MFA challenge(s) fail, the endpoint
   1608   may start to return ``403 Forbidden`` until the issued challenges expire,
   1609   preventing the request from being completed for a while.  In this case,
   1610   repeating the request with a different body may still be allowed!
   1611 
   1612 .. ts:def:: ChallengeResponse
   1613 
   1614   // @since v10
   1615   interface ChallengeResponse {
   1616     // List of challenge IDs that must be solved before the
   1617     // client may proceed.
   1618     challenges: Challenge[];
   1619 
   1620     // True if **all** challenges must be solved (AND), false if
   1621     // it is sufficient to solve one of them (OR).
   1622     combi_and: boolean;
   1623   }
   1624 
   1625 .. ts:def:: Challenge
   1626 
   1627   // @since v10
   1628   interface Challenge {
   1629     // Unique identifier of the challenge to solve to run this protected
   1630     // operation.
   1631     challenge_id: string;
   1632 
   1633     // Channel that will be used to transmit the challenge.
   1634     tan_channel: TanChannel;
   1635 
   1636     // Hint to show to the user as to where the challenge will be
   1637     // sent or what to use to solve the challenge. May not
   1638     // contain the full address for privacy.
   1639     tan_info: string;
   1640   }
   1641 
   1642 .. ts:def:: TanChannel
   1643 
   1644   enum TanChannel {
   1645     SMS = "sms",
   1646     EMAIL = "email"
   1647   }
   1648 
   1649 Requesting challenges
   1650 ^^^^^^^^^^^^^^^^^^^^^
   1651 
   1652 .. http:post:: /accounts/$USERNAME/challenge/$CHALLENGE_ID
   1653 
   1654   Send TAN code for the ``CHALLENGE_ID`` challenge.
   1655 
   1656   This request can be posted several times to trigger TAN retransmission when the current code has expired or too many confirmation attempts have been made.
   1657 
   1658   This endpoint is not authenticated. @since **v10**
   1659 
   1660   **Request:**
   1661 
   1662   The request body must be empty.
   1663 
   1664   **Response:**
   1665 
   1666   :http:statuscode:`200 Ok`:
   1667     The TAN code has been sent. The body will be a `ChallengeRequestResponse`.
   1668   :http:statuscode:`404 Not Found`:
   1669     * ``TALER_EC_BANK_TAN_CHANNEL_SCRIPT_FAILED``: TAN transmition failed.
   1670     * ``TALER_EC_BANK_TAN_CHALLENGE_EXPIRED``: TAN transmition failed.
   1671     The challenge was not found.
   1672   :http:statuscode:`410 Gone`:
   1673     The challenge was already solved.
   1674   :http:statuscode:`429 Too many requests`:
   1675     Too many challenges are active right now, you must wait or confirm current challenges.
   1676   :http:statuscode:`502 Bad Gateway`:
   1677     * ``TALER_EC_BANK_TAN_CHANNEL_SCRIPT_FAILED``: TAN transmition failed.
   1678 
   1679   **Details:**
   1680 
   1681   .. ts:def:: ChallengeRequestResponse
   1682 
   1683     interface ChallengeRequestResponse {
   1684       // How long does the client have to solve the
   1685       // challenge.
   1686       solve_expiration: Timestamp;
   1687 
   1688       // What is the earlist time at which the client
   1689       // may request a new challenge to be transmitted?
   1690       earliest_retransmission: Timestamp;
   1691     }
   1692 
   1693 Solving challenges
   1694 ^^^^^^^^^^^^^^^^^^
   1695   
   1696 .. http:post:: /accounts/$USERNAME/challenge/$CHALLENGE_ID/confirm
   1697 
   1698   Solves the ``CHALLENGE_ID`` challenge and allows performing the protected operation.
   1699 
   1700   When the challenge is confirmed, you can call the protected endpoint again with ``CHALLENGE_ID`` in the ``Taler-Challenge-Ids`` HTTP header and an the original request body.
   1701 
   1702   This endpoints is not authenticated. Too many unsuccessful attempts to confirm token creation challenges block the account.
   1703 
   1704   **Request:**
   1705 
   1706   .. ts:def:: ChallengeSolve
   1707 
   1708     interface ChallengeSolve {
   1709       // The TAN code that solves $CHALLENGE_ID
   1710       tan: string;
   1711     }
   1712 
   1713   **Response:**
   1714 
   1715   :http:statuscode:`204 No Content`:
   1716     The challenge is confirmed.
   1717   :http:statuscode:`404 Not Found`:
   1718     * ``TALER_EC_BANK_TRANSACTION_NOT_FOUND`` : unknown challenge TAN.
   1719     * ``TALER_EC_BANK_TAN_CHALLENGE_EXPIRED`` : expired challenge.
   1720   :http:statuscode:`409 Conflict`:
   1721     * ``TALER_EC_BANK_TAN_CHALLENGE_FAILED`` : wrong TAN.
   1722     * ``TALER_EC_BANK_TAN_CHALLENGE_EXPIRED`` : expired TAN.
   1723   :http:statuscode:`429 Too many requests`:
   1724     Too many failed confirmation attempts, a new TAN must be requested.
   1725 
   1726 
   1727 Monitor
   1728 -------
   1729 
   1730 .. http:get:: /monitor
   1731 
   1732   When the bank provides conversion between the local currency and an
   1733   external one, this call lets the bank administrator monitor the cashin
   1734   and cashout operations that were made from and to the external currency.
   1735   It shows as well figures related to internal payments made by a Taler
   1736   exchange component to internal bank accounts. Timeframes are in UTC.
   1737 
   1738   **Request:**
   1739 
   1740   :query timeframe: *Optional*.
   1741     This parameter admits one of the following values. Defaults to 'hour'.
   1742 
   1743     * hour
   1744     * day
   1745     * month
   1746     * year
   1747 
   1748   :query date_s: *Optional*.
   1749     Non-negative date in seconds after the UNIX Epoch. Defaults to current time.
   1750     @since **v4**
   1751 
   1752   :query which: *Optional*.
   1753     This parameter points at a particular element of the *timeframe* parameter.
   1754     Following are the admitted values for each one.
   1755     Defaults to the last snapshot taken of the *timeframe* parameter.
   1756     @deprecated since **v4**
   1757 
   1758     * hour: from 00 to 23
   1759     * day: from 1 to the last day of the current month.
   1760     * month: from 1 to 12
   1761     * year: Gregorian year in the YYYY format.
   1762 
   1763   **Response:**
   1764 
   1765   :http:statuscode:`200 OK`:
   1766     The bank responds with `MonitorResponse`.
   1767   :http:statuscode:`400 Bad Request`:
   1768     This error may indicate that the *which* parameter is not appropriate for the selected *timeframe*.  For example, timeframe=month and which=20 would result in this error.
   1769   :http:statuscode:`401 Unauthorized`:
   1770     Invalid or missing credentials.
   1771   :http:statuscode:`403 Forbidden`:
   1772     Missing rights.
   1773 
   1774   **Details:**
   1775 
   1776   .. note::
   1777 
   1778     API consumers may combine the values in the response with other
   1779     factors to serve different views to their users.
   1780 
   1781   .. ts:def:: MonitorResponse
   1782 
   1783     // Union discriminated by the "type" field.
   1784     type MonitorResponse =
   1785       | MonitorNoConversion
   1786       | MonitorWithConversion;
   1787 
   1788   .. ts:def:: MonitorNoConversion
   1789 
   1790     // Monitoring stats when conversion is not supported
   1791     interface MonitorNoConversion {
   1792       type: "no-conversions";
   1793 
   1794       // How many payments were made to a Taler exchange by another
   1795       // bank account.
   1796       talerInCount: Integer;
   1797 
   1798       // Overall volume that has been paid to a Taler
   1799       // exchange by another bank account.
   1800       talerInVolume: Amount;
   1801 
   1802       // How many payments were made by a Taler exchange to another
   1803       // bank account.
   1804       talerOutCount: Integer;
   1805 
   1806       // Overall volume that has been paid by a Taler
   1807       // exchange to another bank account.
   1808       talerOutVolume: Amount;
   1809     }
   1810 
   1811   .. ts:def:: MonitorWithConversion
   1812 
   1813     // Monitoring stats when conversion is supported
   1814     interface MonitorWithConversion {
   1815       type: "with-conversions";
   1816 
   1817       // How many cashin operations were confirmed by a
   1818       // wallet owner. Note: wallet owners
   1819       // are NOT required to be customers of the libeufin-bank.
   1820       cashinCount: Integer;
   1821 
   1822       // Overall regional currency that has been paid by the regional admin account
   1823       // to regional bank accounts to fulfill all the confirmed cashin operations.
   1824       cashinRegionalVolume: Amount;
   1825 
   1826       // Overall fiat currency that has been paid to the fiat admin account
   1827       // by fiat bank accounts to fulfill all the confirmed cashin operations.
   1828       cashinFiatVolume: Amount;
   1829 
   1830       // How many cashout operations were confirmed.
   1831       cashoutCount: Integer;
   1832 
   1833       // Overall regional currency that has been paid to the regional admin account
   1834       // by fiat bank accounts to fulfill all the confirmed cashout operations.
   1835       cashoutRegionalVolume: Amount;
   1836 
   1837       // Overall fiat currency that has been paid by the fiat admin account
   1838       // to fiat bank accounts to fulfill all the confirmed cashout operations.
   1839       cashoutFiatVolume: Amount;
   1840 
   1841       // How many payments were made to a Taler exchange by another
   1842       // bank account.
   1843       talerInCount: Integer;
   1844 
   1845       // Overall volume that has been paid to a Taler
   1846       // exchange by another bank account.
   1847       talerInVolume: Amount;
   1848 
   1849       // How many payments were made by a Taler exchange to another
   1850       // bank account.
   1851       talerOutCount: Integer;
   1852 
   1853       // Overall volume that has been paid by a Taler
   1854       // exchange to another bank account.
   1855       talerOutVolume: Amount;
   1856     }
   1857 
   1858 
   1859 Endpoints for Integrated Sub-APIs
   1860 ---------------------------------
   1861 
   1862 .. http:any:: /taler-integration/*
   1863 
   1864   All endpoints under this prefix are specified by the.
   1865   :doc:`GNU Taler bank integration API </core/api-bank-integration>`.
   1866   This API handles the communication with Taler wallets.
   1867 
   1868 
   1869 .. http:any:: /accounts/$USERNAME/taler-wire-gateway/*
   1870 
   1871   All endpoints under this prefix are specified
   1872   by the :doc:`GNU Taler wire gateway API </core/api-bank-wire>`.
   1873 
   1874   The endpoints are only available for accounts configured with ``is_taler_exchange=true``.
   1875 
   1876 
   1877 .. http:any:: /accounts/$USERNAME/taler-revenue/*
   1878 
   1879   All endpoints under this prefix are specified
   1880   by the :doc:`GNU Taler Revenue API </core/api-bank-revenue>`.
   1881 
   1882 .. http:any:: /accounts/$USERNAME/conversion-info/*
   1883 
   1884   User custom rates, public for accounts configured with ``is_taler_exchange=true`` else private. Since **v9**
   1885 
   1886   All endpoints under this prefix are specified
   1887   by the :doc:`GNU Taler Conversion Info API </core/api-bank-conversion-info>`.
   1888 
   1889 .. http:any:: /conversion-rate-classes/$CLASS_ID/conversion-info/*
   1890 
   1891   Conversion rate conversion infos, admin only. Since **v9**
   1892 
   1893   All endpoints under this prefix are specified
   1894   by the :doc:`GNU Taler Conversion Info API </core/api-bank-conversion-info>`.
   1895 
   1896 .. http:any:: /conversion-info/*
   1897 
   1898   Global conversion rate infos.
   1899 
   1900   All endpoints under this prefix are specified
   1901   by the :doc:`GNU Taler Conversion Info API </core/api-bank-conversion-info>`.
   1902 
   1903 .. http:any:: /taler-observability/*
   1904 
   1905   Since **v11**
   1906 
   1907   All endpoints under this prefix are specified
   1908   by the :doc:`GNU Taler Observability API </core/api-observability>`.