This document describes the REST API and resources provided by the Compliance Suite. The REST APIs are for developers who want to integrate the Compliance Suite into other applications.
Compliance Suiteās REST API provide access to all suite resources via URI paths. To use a REST API, your application will make an HTTP request and parse the response. The response format is JSON. Your methods will be the standard HTTP methods like GET, PUT, POST and DELETE.
Because the REST API is based on open standards, you can use any web development language to access the API.
The Compliance Suite API uses a Jason Web Token to secure all data requests. Each one of the request needs to contain the JWT which has an expiration of 30 minutes and needs to be refreshed after that period of time.
To request a JWT it is necessary to make a POST request to /auth/token
with the credentials previously facilitated by ZenLedger.
This same resource will be used to refresh the token after expiration.
Here is an example in javascript of how to request a JWT:
const clientId = 'provided_client_id';
const clientSecret = 'provided_secret';
const tokenEndpoint = 'https://zenledger.io/auth/token';
const requestOptions = {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
client_id: clientId,
client_secret: clientSecret,
grant_type: 'client_credentials',
}),
};
fetch(tokenEndpoint, requestOptions)
.then((response) => {
if (!response.ok) {
throw new Error('Failed to obtain JWT token');
}
return response.json();
})
.then((data) => {
const token = data.access_token;
console.log('JWT Token:', token);
// You can now use the token for further requests or store it for future use.
})
.catch((error) => {
console.error('Error:', error);
});
Once the JWT is created you can use it for every other request to the API:
const jwtToken = 'your-jwt-token';
const apiUrl = 'https://zenledger.io/compliance/api/v1/companies';
fetch(apiUrl, {
method: 'GET',
headers: {
'Content-Type': 'application/json'
'Authorization': 'Bearer ${jwtToken}''
}
})
.then(response => response.json())
.then(response_data => {
// Handle the response data (list of companies)
console.log('companies list:', response_data.data);
})
.catch(error => {
// Handle any errors
console.error('Error:', error);
});
The server response can vary based on the validity of the provided POST body:
Content-Type
, Cache-Control
, Expires
, and more.access_token
, token_type
, expires_in
, and scope
fields. The access_token
is the JWT that should be included in the Authorization
header for subsequent API requests.Content-Type
, Cache-Control
, Expires
, and more.error
and error_description
fields, indicating an invalid client or failed authentication.Content-Type
, Cache-Control
, Expires
, and more.error
and error_description
fields, indicating an invalid request.Key | Value | Description |
---|---|---|
Content-Type | application/json |
The Companies API resource enable management of company data within the application, including the creation, retrieval, updating and deletion of company details.
Create Company Endpoint: This POST endpoint allows for the creation of new companies, requiring authentication via a bearer token.
Get Companies Endpoint: This GET endpoint retrieves a list of all companies in the system, with optional filtering by company reference. Authentication is requiredā.
Update Company Details Endpoint: This PUT endpoint facilitates the updating of a specific company details. It requires the company’s unique identifier in the URL and authentication details in the requestā.
Delete Company Endpoint: This DELETE endpoint facilitates the deletion of a specific company. It requires the company’s unique identifier in the URL and authentication details in the requestā.
These endpoints form the basis of company data management in the application, adhering to standard HTTP protocols and returning appropriate status codes based on the request’s success or failure.
Returns a list of all active companies that exist in the system by making a GET request to the path /compliance/api/v1/companies
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Returns the details of the requested company by making a GET request to the path /compliance/api/v1/companies/{company_reference}
on the base URL
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Creates a new company which is linked to the enterprise by making a POST request to the /compliance/api/v1/companies/
endpoint is used to create a new company in the system.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
NONE
*In JSON format
name (optional)
string
Legal name of the companyreference
string
Own company referenceimport_notification_url (optional)
string
if set, Webhook notifications will be sent here after each import completed
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Deletes a company which is linked to the enterprise by making a DELETE request to the /compliance/api/v1/companies/{company_reference}
endpoint.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Updates the details of a company by making a PUT request to the path /compliance/api/v1/companies/{company_reference}
on the base URL
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
NONE
*In JSON format
name (optional)
string
Legal name of the companyimport_notification_url (optional)
string
if set, Webhook notifications will be sent here after each import completed
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
This folder is dedicated to managing user-related operations within the Compliance API. It contains endpoints that enable retrieving, updating and deleting user information within specific companies.
Please note that for all the endpoints, the {{jwt_token}}
, {{base_url}}
, {{company_reference}}
, and {{user_id}}
placeholders should be replaced with the actual values based on the context and environment in which the requests are made.
Returns a list of all active users that exist in the system for a specific company by making a GET request to the path /companies/{company_reference}/users
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
companyReference
string
The ID of a specific company
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Returns the details of a specific user by making a GET request to the path /companies/{company_reference}/users/{user_id}
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
companyReference
string
The ID of a specific companyuserId
string
The ID of a specific user
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Creates a new company user which is linked to the company by making a POST request to the /compliance/api/v1/companies/{company_reference}/users
endpoint is used to create a new user in the system.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
companyReference
string
The ID of a specific company
NONE
*In JSON format
string
Email address of the userfirst_name (optional)
string
First name of the userlast_name (optional)
string
Last name of the user
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Updates the details of a user by making a PUT request to the path /compliance/api/v1/companies/{company_reference}/users/{user_id}
on the base URL
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
companyReference
string
The ID of a specific companyuserId
string
The ID of a specific user
NONE
*In JSON format
email (optional)
string
Email address of the userfirst_name (optional)
string
First name of the userlast_name (optional)
string
Last name of the user
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Deletes a user which is linked to the company by making a DELETE request to the /compliance/api/v1/companies/{company_reference}/users/{user_id}
endpoint.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
companyReference
string
The ID of a specific companyuserId
string
The ID of a specific user
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
This folder contains endpoints related to retrieving transaction information for a user within the Compliance API. These endpoints allow you to fetch transactions for a user based on various criteria, such as user ID, date range, and currency.
Returns a list of the user’s transactions by making a GET request to the path /companies/{company_reference}/users/{user_id}/transactions
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
*Results paginated with 100 elements per page
companyReference
string
The ID of a specific companyuserId
string
The ID of a specific user
currency_code
string
Filter transactions by currency codedate_from
string
Specific cut-off date for the transactions list (beginning of the list)date_to
string
Specific cut-off date for the transactions list (end of the list)page
number
Specific page requested for the paginated results
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Returns a list of all the users of a company with all their transactions by making a GET request to the path /companies/{company_reference}/transactions
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
*Results paginated with 100 elements per page
companyReference
string
The ID of a specific company
currency_code
string
Filter transactions by currency codedate_from
string
Specific cut-off date for the transactions list (beginning of the list)date_to
string
Specific cut-off date for the transactions list (end of the list)page
number
Specific page requested for the paginated results
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
This folder all different types of transactions that can be found in both transactions
and holdings
resources.
The property that contains this values is called transaction_type
.
There are three different short of transactions and each one of them have different types which are described below:
A deposit transaction is any transaction where a crypto asset enters your account that is not paired as a trade with another crypto asset. For example, if a friend sent you 50 USDC that would be a Deposit transaction (subtype Incoming). Also, if you purchased 50 USDC for 50 USD this would also be a Deposit transaction (subtype Buy).
Here are all of the Deposit transaction subtypes:
Key | Value | Description |
---|---|---|
Airdrop | Crypto assets freely given to an account through Airdrop. | |
Buy | Purchasing a crypto asset with fiat (USD). Example, buying 1 BTC with 20,000 USD. | |
Dividend Received | This is a type of reward associated with receiving dividends, reported as income and receives cost basis at the time of acquisition. | |
Forks | Forks are essentially another type of reward, reported as income and receives cost basis at the time of acquisition. This occurs when a blockchain forks, and effectively the user now has assets duplicated on another chain (the fork and the original). | |
Gifts Received | Cost basis is determined when the asset is received, but it is not reported as income. | |
Incoming | This type is used if crypto assets are received from an external source that is not one of the added accounts. For example, if an unknown third party sent the account 50 USDC it would be an incoming transaction. | |
Interest Received | Another type of reward associated with earning interest, reported as income and receives cost basis at the time of acquisition. | |
Masternode | A type of income/reward associated with setting up a master node, reported as income and receives cost basis at the time of acquisition. | |
Mined | Another type of income/reward associated with mining cryptocurrency, reported as income and receives cost basis at the time of acquisition. | |
Misc Reward | Another type of reward if other categories donāt properly describe it, reported as income and receives cost basis at the time of acquisition. | |
NFT Mint | The process of minting (creating) an NFT. If there were assets spent to form the mint, the cost basis will be the value of those assets (in the case of multiple mints simultaneously, the basis is evenly distributed to all of the NFTs minted). If nothing was used to mint the NFT, the cost basis will generally be 0. Not reported as income. | |
Payments | Crypto assets received as income. Basis is determined at the time of acquisition. | |
Staking Return | Staked assets returning to the userās account. The assets will keep their original basis and holding periods, and are not reported as income. Effectively not a taxable event. | |
Staking Reward | Any rewards associated with staking an asset. This is reported as income, with basis determined at the time of acquisition. |
Trades are transactions that involve the trading crypto assets for other crypto assets. For example, trading 1 BTC for 10 ETH is reported as a trade.
These are not to be confused as Deposits/Withdrawal transactions, where a user may buy or sell crypto assets for fiat (ex: USD) currency.
Here are all of the Trade transaction subtypes:
Key | Value | Description |
---|---|---|
Liquidity Pool | Liquidity Pools that return LP tokens are effectively treated as trades, with the cost basis of the received asset determined by the proceeds of the assets leaving the account in the trade. | |
Margin Trading | Trading with borrowed assets. Effectively handled identically to normal trading. | |
NFT Mint | Trading crypto assets to create/mint NFTs. The resulting NFT(s) will receive basis according to the proceeds of the assets traded. In the case of multiple mints simultaneously, the basis will be evenly distributed among all NFTās minted. | |
NFT Trade | Any trade that involves an NFT will also be labeled as an NFT trade. This is handled identically to normal trading. |
Withdrawal transactions include any transaction where a crypto asset leaves the userās account without receiving a crypto asset in return. For example, if the user send 500 USDC to an unknown address, this would be a Withdrawal transaction (subtype Outgoing). Additionally, if a user sells 500 USDC for 500 USD, this would also be a Withdrawal transaction (subtype Sell). If a user trades 500 USDC for 1 ETH, that is not a Withdrawal transaction: that is a trade.
Here are all of the Withdraw transaction subtypes:
Key | Value | Description |
---|---|---|
Donation 501c3 | Assets leaving the account. Gains are set to 0, regardless of basis/proceeds. | |
Fee | Sometimes fees are reported separately from transactions. | |
Gifts Sent | Assets leaving the account. Gains are set to 0, regardless of basis/proceeds. | |
Outgoing | Sending assets to unknown parties or accounts that donāt belong to the user. | |
Purchases | Using cryptocurrency to purchase something else. | |
Sell | Selling cryptocurrency for fiat (ex: USD). | |
Staking Lockup | Assets leaving a userās account going into a staking system. |
This folder contains endpoints related to retrieving holdings information for users of a company. Holdings represent the assets held by users in their uploaded accounts. The endpoints in this folder allow retrieving holdings based on different criteria such as source ID and user ID.
Returns a list of the user holdings by making a GET request to the path /companies/{company_reference}/users/{user_id}/holdings
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
*Results paginated with 20 elements per page
companyReference
string
The ID of a specific companyuserId
string
The ID of a specific user
currency_code
string
Filter transactions by currency codedate_from
string
Specific cut-off date for the transactions list (beginning of the list)date_to
string
Specific cut-off date for the transactions list (end of the list)page
number
Specific page requested for the paginated results
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Returns the holdings of a specific source of a user by making a GET request to the path /companies/{company_reference}/users/{user_id}/holdings/{source_id}
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
companyReference
string
The ID of a specific companyuserId
string
The ID of a specific usersourceId
string
The ID of a specific source
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Deletes a user’s source along with its transactions by making a DELETE request to the /compliance/api/v1/companies/{company_reference}/users/{user_id}/holdings/{source_id}
endpoint.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
companyReference
string
The ID of a specific companyuserId
string
The ID of a specific usersourceId
string
The ID of a specific source
NONE
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Returns a list of all the users of a company with all their holdings by making a GET request to the path /companies/{company_reference}/holdings
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
*Results paginated with 20 elements per page
companyReference
string
The ID of a specific company
page
number
Specific page requested for the paginated results
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
This are all different status that can be set to a source depending of the import process outcome.
The property that contains this values is called status
and it is present for each of the sources listed in the holdings response payload.
There are three different issues that could make an new import or the refresh of an existing one fail:
Key | Value | Description |
---|---|---|
COMPLETE | The user data was successfully updated in the last connection | |
SOURCE_NOT_FOUND | The selected exchange or wallet does no longer exist | |
INVALID_API_KEY | The API credentials provided by the user are no longer valid | |
BAD_ADDRESS | The wallet address provided by the user is not valid | |
INVALID_COIN | The currency provided by the user does not exist | |
INVALID_EXCHANGE | The exchange is wrong | |
UNEXPECTED_ERROR | Due to continuous changes made by each one of the supported exchanges without a notice, we try to be up to date. This error will be shown as we can not identify the real cause. |
The currencies resource in the Compliance API provides information about retrieving the list of supported currencies. By making a GET request to the /compliance/api/v1/currencies
endpoint, you can retrieve the details of available currencies. The request requires authentication using a bearer token.
Please note that the response example for this endpoint will contain the API version and a data object containing an array of currencies. Each currency object includes a reference, code, and name.
Use this information to integrate and work with the supported currencies of the Compliance API.
Returns a paginated list of supported cryptocurrencies by making a GET request to the path /compliance/api/v1/currencies
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
*Results paginated with 100 elements per page
page
number
Specific page requested for the paginated results
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Key | Value | Description |
---|---|---|
page | 42 |
The sources resource in the Compliance API provides information about retrieving the list of supported exchanges and wallet providers. By making a GET request to the /compliance/api/v1/sources
endpoint, you can retrieve the details of available sources. The request requires authentication using a bearer token.
Please note that the response example for this endpoint will contain the API version and a data object containing an array of sources. Each currency object includes a reference, name, type and other useful attributes.
Use this information to integrate and work with the supported sources of the Compliance API.
Returns a paginated list of supported exchanges and wallets by making a GET request to the path /compliance/api/v1/sources
on the base URL.
This endpoint requires authentication via a bearer token, provided in the Authorisation header of the request.
*Results paginated with 100 elements per page
page
number
Specific page requested for the paginated results
200
api_version
string
Version of the targeted APIdata
string
Wrapper for response data (See response example)
Key | Value | Description |
---|---|---|
Authorization | Bearer {{jwt_token}} | |
Content-Type | application/json |
Key | Value | Description |
---|---|---|
page | 1 |
The Compliance API includes specific error codes to indicate and describe various issues and errors that may occur during API interactions. To help you quickly identify and understand these error codes, we have provided a glossary below. This table contains commonly encountered error codes along with their corresponding meanings. Refer to this table for efficient troubleshooting when working with our Compliance API.
Key | Value | Description |
---|---|---|
ZENCS-AUTHGET-AA1 | Forbidden | |
ZENCS-AUTHGET-AA2 | Unauthorised | |
ZENCS-AUTHGET-AA3 | Invalid Api key | |
ZENCS-AUTHGET-AA4 | Invalid OAuth token | |
ZENCS-RSRCGET-AA1 | Resource not found | |
ZENCS-CMPGET-AA1 | Could not retrieve companies | |
ZENCS-CMPGET-AA2 | Could not retrieve company | |
ZENCS-CMPGET-AA3 | Could not find company | |
ZENCS-CMPGET-AA4 | Company has no users | |
ZENCS-CMPPST-AA1 | Could not add company | |
ZENCS-CMPPST-AA2 | Duplicated External ID for company | |
ZENCS-CMPUPD-AA1 | Could not update company details | |
ZENCS-CMPDEL-AA1 | Could not delete company | |
ZENCS-PARAMGET-AA1 | Provided currency not found | |
ZENCS-PARAMGET-AA2 | Wrong date format provided, please provide a valid UTC date in ISO-8601 format | |
ZENCS-PARAMGET-AA3 | Provided source not found | |
ZENCS-USRGET-AA1 | Could not retrieve users | |
ZENCS-USRGET-AA2 | Could not find user | |
ZENCS-USRPST-AA1 | Could not add user | |
ZENCS-USRPST-AA2 | Duplicated email for user | |
ZENCS-USRUPD-AA1 | Could not update user details |
After a user imports a new account, ZenLedger will process it and send a webhook notification to the
defined endpoint one the new import is completed.
This webhook will expect a HTTP 200 response from the Client side, if a different response or none is given, the webhook service will continue to send notification until a valid response is received or the retry cycle is over.
The retry cycle will retry after 1 minute, 3 minutes, 10 minutes, 30 minutes, 1 hour and a final retry after 24 hours.
To set the endpoint in order to receive webhook notifications one of the following should occur:
{
"notification_type": "IMPORT_STATUS_UPDATE",
"company_reference": "company_reference",
"user_id": "7be47a6d-a1b7-43bf-a1b7f5b6-2973cd5e0859",
"source_id": "2973cd5e0859-a1b7-43bf-7be47a6d-97359cd5e082",
"source_reference": "coinbase",
"import_status": "complete",
}