Fiat Funding Onramp

API guide for Partners to offer fiat funding service with Bakkt

Introduction

Bakkt provides a set of APIs that enable Partners to support fiat funding on behalf of their consumers by linking their existing bank accounts and allowing deposit or withdrawal operations. In doing so, Partners can leverage adding fiat currency to the consumer’s fiat account at Bakkt in their ecosystem. Bakkt's platform is designed to adhere to all applicable regulatory requirements, in addition to supporting brand innovation around fiat money movement.

Prerequisites

During the Partner on-boarding process, you will need to supply Bakkt with: 

  • Partner Name 
  • Support email address

Bakkt has two environments, PTR and production. PTR can be used to build and test integration with Bakkt (e.g. CI, if desired). The email address is required for both environments. Bank account information is also needed for both environments, but only needs to be real for production. Bakkt will provide the client ID and client secret to access Bakkt Fiat APIs in each environment. Client ID and secret are persistent ongoing but may be rotated upon request.

Requirements

The APIs will have the following characteristics. 

  • Supports only secured access (HTTPS) 
  • Supports Web Service REST API with JSON as request and response formats 
  • API parameter names are case sensitive 
  • Other than the token end point, a bearer token is required to access Bakkt Fiat APIs

Operations

The following API operations are supported. 

  • Partner Connectivity 
    • Heartbeat: End point that can be used to determine if Bakkt is available 
    • Authenticate Partner: Generates token 
  • Partner Party Funding
    • URL for linking fiat account
    • Transfer fiat currency
    • Unlink a fiat account
    • Link a fiat account
    • Retrieve a Transaction
    • Retrieve all Transactions

Common Fields

There are a number of fields that are common across several of the Bakkt Fiat API operations. 

  • idempotencyKey The idempotencyKey must be unique. Bakkt will use the idempotencyKey to look up prior requests to see if the Partner has made the request before and ensure idempotency works as expected.  If idempotencyKey is reused a 409 error will be returned.  The original response content will be included when the idempotencyKey is reused on the same endpoint. 
  • partnerPartyRef Partner’s identifier to a party on their side expected to be unique at the Partner. 
  • partnerId Bakkt’s unique identifier of a Partner. 
  • partnerTransactionRef Partner’s identifier for a given transaction operation, expected to be unique at Partner.

Idempotency Key

  • Bakkt uses idempotency keys to correctly handle duplicate requests. Bakkt will use the idempotency key to look up prior requests to see if the Partner has made that request before and prevent accidentally performing the same operation twice.
  • Bakkt's idempotency works by saving the resulting body of the first successful request made for any given idempotency key. Subsequent requests with the same key will return the same response informing that the idempotency key is in use.
  • A typical scenario where the same request is sent more than once is when a Partner application makes an API request which is processed at Bakkt but the HTTP connection is dropped due to some network issue (timeout, connection dropped, etc) and the Partner application does not receive a response.
  • Idempotency Key value for new requests must be unique. Every new request should have a new idempotency key value.If a Partner sent a request and received a status code other than 5xx then they shouldn't send the same request with the same idempotency key again.
  • If a Partner sent a request and did not receive a status code (success) from Bakkt or received a 5xx status code, then they should retry the request again with the same idempotency key.
  • Bakkt will keep track of an idempotency key up to 10 days, after which it is removed from our platform.

Related Links


Partner Connectivity

Authenticate

The first step for a Partner is to authenticate against Bakkt. This will return a bearer token (JWT) that can be used for subsequent operations. It’s expected that the Partner will cache the token (an in-process cache would be sufficient) and only refresh it when it's nearing its expiration date or has expired (expiration date is in the token as well as the returned response).

Related Specification

 'https://gql-gw.mkt.ptr.bakkt.com/partner/v1/oauth2/token' \
 --header 'Authorization: Basic TOKEN' \
 --data-urlencode 'grant_type=client_credentials'

Heartbeat

This operation can be used by the Partner to determine if Bakkt is up and available.

Related Specification


Partner Party Linking

Related Webhook Events

Link a Bank Account Using a Plaid Processor Token

Related Specification

A Partner can send a Plaid processor token which Bakkt will use to call Plaid services and complete fiat account linking.

Unlink Fiat Account

Related Specification

A Partner can unlink a consumer fiat account on behalf of the consumer.


Transfer Fiat Currency

Related Specification

Related Webhook Events

📘

Asynchronous API Flow

  1. Deposit/withdraw request is sent to Bakkt
    1. Bakkt replies with 200
    2. A fiat event webhook with pending status is sent
  2. In the case of decline, a fiat event webhook will be sent indicating the error status and reason(ACH Deposit Declined)
    1. In the case of connectivity issues, you will get a 500
    2. In the case of a field validation error, you will get 400
  3. In the case of success a fiat event webhook will be sent
    1. For ACH Deposit, webhook is sent once the transaction transitions to complete(in T+n days)
    2. For ACH Withdraw, webhook is sent shortly after the initial request
    3. For WIRE Deposit/Withdraw, webhook is sent once the wire is processed

A Partner can initiate an ACH or Wire deposit/withdraw on behalf of the consumer. ACH requires a previously linked fiat account.

Party Balance

Related Specification

A partner can retrieve the fiat account balance of a consumer.


Fiat Webhooks

Bakkt uses webhooks to monitor and manage fiat funding processes such as transactions, linking bank accounts, and more fiat related activities. For details and examples on webhooks work related to fiat onramping, see the Webhooks section.


PARTY_EVENT Reason Codes

Reason CodeDescription
ACCOUNT_CLOSURE_REQUESTEDCustomer requested account closure.
MAX_ACH_RETURNSParty suspended due to ACH returns.
COMPLIANCE_LOCKEDAccount suspended by Compliance.
LIQUIDATE_ACCOUNTParty is only able to sell crypto or withdraw funds.
OTHEROther unspecified reason for suspension.
TAX_ID_MAX_RETRIESThe party has reached the maximum number of attempts to verify their tax ID.
CLOSEDThe party has been closed.
ENROLLMENTThe party has been enrolled.
RISK_KYCThe party has failed CIP check.
RISK_OFACThe party has failed OFAC screening.
PENDING_REVIEWThe party has entered a manual review queue with the Compliance team
DOCUMENT_VERIFICATIONThe party is required to provide additional documents for identity validation