CACI Clearing Gateway API (1.0.3)

Download OpenAPI specification:

CACI Support Team: support@caci.id License: MIT

CACI Clearing Gateway API

Merchant-facing APIs exposed by CACI Clearing Gateway for PAKD needs.

Overview

This API allows merchants to manage users, virtual accounts, deposits, and withdrawals through the CACI Clearing Gateway API.

Key Features:

  • User management (CRUD) with KYC and whitelisted accounts
  • Virtual account creation and management
  • Withdrawal processing (asynchronous)
  • Deposit and withdrawal transaction inquiry
  • Payment instrument discovery
  • Webhooks creation and management
  • Payment simulation (non-production only)

Authentication

API Key Authentication:

  • API Key via X-Api-Key header
  • HMAC-SHA512 signature via X-Signature header
  • Unix timestamp (ms) via X-Timestamp header

IP Whitelisting

To access the API, your server's outbound IP address must be whitelisted by the CACI team.

  • Contact support@caci.id and provide your static IP address(es) to be whitelisted
  • All API requests must originate from a whitelisted IP — requests from non-whitelisted IPs will be rejected with 401 Unauthorized
  • If you have multiple environments (staging, production), provide the IPs for each separately
  • Notify the CACI team promptly if your IP address changes

Generating Signature

To generate the HMAC-SHA512 signature:

  1. Create canonical JSON: Sort the request body JSON keys alphabetically
  2. Build payload string: Format as "METHOD|PATH|BODY|TIMESTAMP"
  3. Calculate HMAC-SHA512: Use your client secret as the key
  4. Convert to hex: Lowercase hexadecimal representation

Python Implementation

import hmac
import hashlib
import json

def generate_signature(method, path, raw_body, timestamp, client_secret):
    """
    Generate HMAC-SHA512 signature for CACI API authentication
    
    Args:
        method: HTTP method (e.g., 'POST', 'GET')
        path: API endpoint path (e.g., '/v1/transactions/fiat')
        raw_body: Raw request body JSON string (empty string for GET/DELETE)
        timestamp: Unix timestamp in milliseconds
        client_secret: Your API secret key
    
    Returns:
        Hexadecimal signature string
    """
    # Create canonical JSON with sorted keys
    if raw_body:
        try:
            # Parse and re-sort JSON to ensure canonical ordering
            body_dict = json.loads(raw_body)
            canonical_body = json.dumps(body_dict, sort_keys=True, separators=(',', ':'))
        except json.JSONDecodeError:
            canonical_body = raw_body
    else:
        canonical_body = ""
    
    # Build payload
    payload = f"{method}|{path}|{canonical_body}|{timestamp}"
    
    # Generate HMAC-SHA512 signature
    signature = hmac.new(
        client_secret.encode("utf-8"),
        payload.encode("utf-8"),
        hashlib.sha512
    ).hexdigest()
    
    return signature

# Example usage
if __name__ == "__main__":
    # Sample request data
    method = "POST"
    path = "/d/v1/users"
    timestamp = 1763474667930
    client_secret = "your_api_secret_here"
    
    # Sample request body
    request_data = {
        "requestId": str(uuid.uuid4()),
        "userId": str(uuid.uuid4())[:8],
        "kycName": "Jhon Doe",
        "phone": "+6281234567891",
        "email": "jhon.doe@icex.id",
        "type": "retail",
        "nationality": "ID", 
        "whitelistedKycNames": [
          "Jhon",
          "Pg"
        ]
    }
    
    # Convert to canonical JSON
    raw_body = json.dumps(request_data, sort_keys=True, separators=(',', ':'))
    
    # Generate signature
    signature = generate_signature(method, path, raw_body, timestamp, client_secret)
    
    print(f"Payload: {method}|{path}|{raw_body}|{timestamp}")
    print(f"Signature: {signature}")
    
    # Headers to include in request
    headers = {
        "X-Api-Key": "your_api_key_here",
        "X-Signature": signature,
        "X-Timestamp": str(timestamp)
    }

Important Notes

  • Canonical JSON: Always sort JSON keys alphabetically
  • Timestamp: Unix timestamp in milliseconds (must be within 5 minutes of server time)
  • Empty body: For GET/DELETE requests, use empty string for BODY component
  • Path: Use only the path portion, no host or query parameters

User Management

Merchant user CRUD operations

Create User

Create a new merchant user with KYC information and optional whitelisted accounts.

Authorizations:
ApiKeyAuth
header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key for this request

userId
required
string

Merchant user identifier

kycName
required
string

Legal/KYC name

phone
string

User phone number with country code

email
string

User email

type
required
string
Enum: "institutional" "retail" "other"

User type

nationality
string

ISO country code (2 chars)

idType
string

Identity document type (optional)

idNumber
string

Identity document number (optional)

whitelistedKycNames
Array of strings

Alternate KYC names for verification

Array of objects (WhitelistedWithdrawalAccount)

Whitelisted beneficiary accounts

Responses

Request samples

Content type
application/json
{
  • "requestId": "2dd96e87-4f8f-460e-a04d-040370505552",
  • "userId": "567890",
  • "kycName": "Jhon Doe",
  • "phone": "6281234567890",
  • "email": "john.doe@example.com",
  • "type": "retail",
  • "nationality": "ID",
  • "idType": "ktp",
  • "idNumber": "1234567890",
  • "whitelistedKycNames": [
    ],
  • "whitelistedWithdrawalAccounts": [
    ]
}

Response samples

Content type
application/json
{
  • "timestamp": "1772590502",
  • "code": 201,
  • "message": "success",
  • "data": {
    }
}

Get User

Retrieve detailed information of a specific merchant user.

Authorizations:
ApiKeyAuth
path Parameters
userId
required
string
Example: 1ff159d3

Merchant user identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1774573934924,
  • "data": {
    }
}

Update User

Update an existing merchant user. The userId path parameter must match the user being updated. whitelistedWithdrawalAccounts is updated through this endpoint.

Authorizations:
ApiKeyAuth
path Parameters
userId
required
string
Example: 567890

Merchant user identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key

kycName
string
phone
string
email
string
type
string
Enum: "institutional" "retail" "other"
nationality
string
idType
string
idNumber
string
whitelistedKycNames
Array of strings
Array of objects (WhitelistedWithdrawalAccount)

Responses

Request samples

Content type
application/json
{
  • "requestId": "3eeb5958-a2f5-4934-9d8b-26197d104abb",
  • "kycName": "Jhon Doe Updated",
  • "phone": "6281234567890",
  • "email": "john.updated@example.com",
  • "type": "retail",
  • "nationality": "ID",
  • "idType": "ktp",
  • "idNumber": "1234567890",
  • "whitelistedKycNames": [
    ],
  • "whitelistedWithdrawalAccounts": [
    ]
}

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "reason": "User updated successfully",
  • "requestId": "c4b3fa1a-9720-455d-aa23-6a0822b34193",
  • "timestamp": 1774573970513
}

Delete User

Soft delete a merchant user.

Authorizations:
ApiKeyAuth
path Parameters
userId
required
string
Example: 567890

Merchant user identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key

Responses

Request samples

Content type
application/json
{
  • "requestId": "6b0b4af8-07e4-44fe-b4b3-32a410bbfd67"
}

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "reason": "User deleted successfully",
  • "timestamp": 1774573995972
}

List User Virtual Accounts

Retrieve all virtual accounts associated with a specific merchant user.

Authorizations:
ApiKeyAuth
path Parameters
userId
required
string
Example: USER001

Merchant user identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1774563064105,
  • "data": [
    ]
}

Payment Instruments

Merchant payment instrument discovery

List Merchant Payment Instruments

Returns payment instruments enabled for the authenticated merchant. Data is grouped by upstream provider so merchants can see provider-specific channel/bank availability.

Authorizations:
ApiKeyAuth
header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "timestamp": 1780908709325,
  • "code": 200,
  • "message": "SUCCESS",
  • "data": [
    ]
}

Virtual Accounts

Virtual account creation and management

Create Virtual Account

Create a new virtual account for a merchant user. This operation is synchronous.

Currently supported banks:

  • 002: BRI (Bank Rakyat Indonesia)
  • 014: BCA (Bank Central Asia)
  • 503: NOBU (Bank Nationalnobu)
Authorizations:
ApiKeyAuth
header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key

userId
required
string

User to bind VA to

bankCode
required
string

Destination VA bank/channel code (BI SNAP)

Responses

Request samples

Content type
application/json
{
  • "requestId": "5520ef9c-e671-4c50-821d-9c9d787a5578",
  • "userId": "c28f03f8",
  • "bankCode": "503"
}

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "requestId": "5520ef9c-e671-4c50-821d-9c9d787a5578",
  • "timestamp": 1774723700223,
  • "data": {
    }
}

Get Virtual Account

Retrieve details of a specific virtual account by its payment instrument ID.

Authorizations:
ApiKeyAuth
path Parameters
paymentInstrumentId
required
string <uuid>
Example: 019d35af-3233-7218-9135-170365519896

Payment instrument identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1774726455840,
  • "data": {
    }
}

Update Virtual Account

Update an existing virtual account. This operation is synchronous.

Authorizations:
ApiKeyAuth
path Parameters
paymentInstrumentId
required
string <uuid>
Example: 019d35af-3233-7218-9135-170365519896

Payment instrument identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key

virtualAccountName
string

New display name

expiredDate
string <date-time>

New expiration timestamp

Responses

Request samples

Content type
application/json
{
  • "requestId": "60a59117-5138-4cc0-ae39-babb832021ec",
  • "virtualAccountName": "Jhon Doe Updated",
  • "expiredDate": "2099-12-31T23:59:59Z"
}

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "requestId": "0c2d5982-ea8c-482d-99f9-b8929fec479d",
  • "timestamp": 1774755401625,
  • "data": {
    }
}

Withdrawals

Withdrawal processing and inquiry

Create Withdrawal (Async)

Create a new withdrawal request. This operation is asynchronous. Use GET /v1/withdrawals/{transactionId} or merchant webhook to track final status.

Authorizations:
ApiKeyAuth
header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key

userId
required
string

Merchant user identifier

merchantReference
required
string

Merchant transaction reference

beneficiaryBankCode
required
string

Beneficiary bank code (BI SNAP)

beneficiaryAccountNo
required
string

Beneficiary account number

beneficiaryAccountName
string

Beneficiary account holder name

amount
required
string

Transfer amount (decimal string)

merchantFee
string

Merchant fee override/echo for reporting to clearing

Responses

Request samples

Content type
application/json
{
  • "requestId": "2dd96e87-4f8f-460e-a04d-040370505552",
  • "userId": "567890",
  • "merchantReference": "111111111",
  • "beneficiaryBankCode": "002",
  • "beneficiaryAccountNo": "888801000003301",
  • "beneficiaryAccountName": "Jhon Doe",
  • "amount": "20000.00",
  • "merchantFee": "5000.00"
}

Response samples

Content type
application/json
{
  • "timestamp": "1772590502",
  • "code": 201,
  • "message": "success",
  • "data": {
    }
}

List Withdrawals

List withdrawal transactions with optional filters and pagination.

Authorizations:
ApiKeyAuth
query Parameters
userId
string

Filter by merchant user

status
string

Filter by transaction status

startDate
string <date-time>

Lower bound for requested_at (RFC3339). Max range 90 days. Defaults to 90 days before now.

endDate
string <date-time>

Upper bound for requested_at (RFC3339). Max range 90 days. Defaults to current time.

trxDateTimeStart
string <date-time>

Lower bound for trx_date_time (RFC3339)

trxDateTimeEnd
string <date-time>

Upper bound for trx_date_time (RFC3339)

limit
integer
Default: 100

Page size for pagination

offset
integer
Default: 0

Offset for pagination

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1777024486560,
  • "data": {
    }
}

Get Withdrawal

Retrieve details of a specific withdrawal transaction.

Authorizations:
ApiKeyAuth
path Parameters
transactionId
required
string <uuid>
Example: 019d6638-6b62-7130-b90c-e4d1583f9597

Transaction identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1777025165108,
  • "data": {
    }
}

Deposits

Deposit transaction inquiry

List Deposits

List deposit transactions with optional filters and pagination.

Authorizations:
ApiKeyAuth
query Parameters
status
string

Filter by transaction status

userId
string

Filter by merchant user

startDate
string <date-time>

Lower bound for requested_at (RFC3339). Max range 90 days. Defaults to 90 days before now.

endDate
string <date-time>

Upper bound for requested_at (RFC3339). Max range 90 days. Defaults to current time.

trxDateTimeStart
string <date-time>

Lower bound for trx_date_time (RFC3339)

trxDateTimeEnd
string <date-time>

Upper bound for trx_date_time (RFC3339)

limit
integer
Default: 100

Page size for pagination

offset
integer
Default: 0

Offset for pagination

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1777025342784,
  • "data": {
    }
}

Get Deposit

Retrieve details of a specific deposit transaction by its CACI transaction ID (transactionId / caciTxId).

Authorizations:
ApiKeyAuth
path Parameters
transactionId
required
string <uuid>
Example: 019d6638-6b62-7130-b90c-e4d1583f9597

Transaction identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1777025342784,
  • "data": {
    }
}

Balances

Merchant balance inquiry per provider and vault type

Get Balances

Retrieve the merchant's current balances grouped by provider and vault type.

Each provider entry contains one or more balance records — typically a deposit vault and a withdrawal vault — representing the available funds for each operation type.

Authorizations:
ApiKeyAuth
header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "code": 200,
  • "message": "SUCCESS",
  • "timestamp": 1779722046088,
  • "requestId": "006b6c7b-f11d-4a6e-ab26-cadc9b53c942",
  • "data": [
    ]
}

Webhooks

Merchant webhook configuration, retry operations, and outgoing notification reference.


Outgoing Notifications

After a transaction is processed, the platform asynchronously POSTs a JSON payload to all webhook URLs the merchant has configured for that event type. Delivery runs in a background goroutine and never blocks the transaction response.

Flow

Transaction Processed
        │
        ▼
Payload enriched from DB (VA info, user info)
        │
        ▼
POST to each configured webhook URL
        │
        ▼
WebhookLog stored in Redis
  key: webhook:log:<transactionId>  |  TTL: 24h

Event Types

Event Type Triggered When
va_payment A deposit is successfully processed
transfer A withdrawal status is updated

Verifying Notifications (Required)

Treat every webhook as a signal, not as proof. A webhook payload is delivered to your URL and must not be trusted on its own. After receiving a notification, your server must call the corresponding read API to confirm the transaction's authoritative status before crediting funds, releasing goods, or settling:

Event Confirm with Lookup key
va_payment (deposit) GET /v1/deposits/{transactionId} additionalInfo.caciTxId
transfer (withdrawal) GET /v1/withdrawals/{transactionId} additionalInfo.caciTxId

Act only on the status returned by these endpoints — not on the webhook body. This protects you against forged or replayed notifications, since the read API is authenticated and returns CACI's source-of-truth record. Always dedupe on caciTxId or paymentRequestId so a repeated notification never credits the same transaction twice.

Delivery Details

  • Method: POST
  • Content-Type: application/json
  • User-Agent: CACI-PG-Webhook/1.0
  • Custom headers defined per webhook config are merged into every request.
  • Success is determined by an HTTP 200 or 201 response from the merchant endpoint.
  • One delivery attempt is made per notification. Use the retry endpoint for failed deliveries.

Source IP Addresses

Webhook requests will originate from the following IPs. Whitelist these on your server to ensure delivery:

Environment IP Address
Production 15.233.128.42
Staging 16.78.217.189

Payload Schemas

Deposit — va_payment

{
  "partnerServiceId": "merchant-uuid",
  "customerNo": "merchant-user-id",
  "virtualAccountNo": "1234567890",
  "trxId": "tx-uuid",
  "paymentRequestId": "tx-uuid",
  "paidAmount": {
    "value": "100000",
    "currency": "IDR"
  },
  "trxDateTime": "2025-01-01T10:00:00Z",
  "virtualAccountName": "John Doe",
  "virtualAccountType": "01",
  "virtualAccountPhone": "+62812345678",
  "virtualAccountEmail": "john@example.com",
  "additionalInfo": {
    "minAmount": 0,
    "maxAmount": 10000000,
    "bankCode": "BCA",
    "customerInfo": {
      "customer_id": "internal-user-uuid",
      "customer_ref_id": "merchant-user-ref",
      "given_name": "John Doe",
      "email": "john@example.com",
      "mobile": "+62812345678"
    },
    "expiredDate": "2025-01-02T00:00:00Z",
    "failureReason": null,
    "merchantUserId": "merchant-user-ref",
    "caciTxId": "tx-uuid"
  }
}
Field Description
partnerServiceId Merchant UUID (falls back to merchant ID)
customerNo Merchant-side user reference
virtualAccountNo VA number that received the payment
trxId Internal transaction ID
paymentRequestId Unique identifier for this specific payment from upstream bank or provider.
paidAmount.value Amount as a string
paidAmount.currency e.g. IDR
trxDateTime Timestamp from the provider; falls back to processedAt
additionalInfo.bankCode Bank code of the VA (e.g. BCA, BNI)
additionalInfo.caciTxId Unique identifier for this specific transaction from CACI. Use this for deduplication / idempotency and to verify notifications
additionalInfo.merchantUserId Merchant's user reference
additionalInfo.customerInfo KYC/user details resolved from the user record
additionalInfo.failureReason Populated on failed payments; null on success

Withdrawal — transfer

{
  "originalReferenceNo": "provider-reference-number",
  "originalPartnerReferenceNo": "merchant-reference",
  "responseCode": "00",
  "responseMessage": "Success",
  "amount": {
    "value": "500000",
    "currency": "IDR"
  },
  "paymentInstrumentId": "pi-uuid",
  "beneficiaryAccountNo": "0987654321",
  "beneficiaryBankCode": "BNI",
  "sourceAccountNo": "source-account-number",
  "additionalInfo": {
    "merchantUserId": "merchant-user-ref",
    "caciTxId": "tx-uuid"
  }
}
Field Description
originalReferenceNo Provider's reference number for the transfer
originalPartnerReferenceNo Merchant's own reference number
responseCode Provider response code
responseMessage Provider response message
amount.value Transfer amount as a string
beneficiaryAccountNo Destination account number
beneficiaryBankCode Destination bank code
paymentInstrumentId Payment instrument UUID
additionalInfo.caciTxId Unique identifier for this specific transaction from CACI. Use this for deduplication / idempotency and to verify notifications
additionalInfo.merchantUserId Merchant's user reference

Configuration

Merchants register endpoint URLs via the endpoints below. A merchant may register multiple URLs for the same event type — the platform delivers to all of them.

Create Webhook

Register a new merchant webhook for a specific event type.

Event types:

  • va_payment: Triggered on deposit (virtual account payment) events
  • transfer: Triggered on withdrawal events
Authorizations:
ApiKeyAuth
header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key for this request

eventType
required
string
Enum: "va_payment" "transfer" "qr_payment" "debit_notify"

Event type to subscribe to

url
required
string

Valid HTTPS webhook destination URL

headers
object

Custom headers sent with every delivery

isActive
boolean

Whether the webhook should be active. Defaults to true.

description
string

Free-text label for this webhook

Responses

Request samples

Content type
application/json
{}

Response samples

Content type
application/json
{
  • "timestamp": 1776758146948,
  • "code": 201,
  • "message": "SUCCESS",
  • "data": {
    }
}

List Webhooks

Retrieve all webhooks configured for the authenticated merchant.

Event types:

  • va_payment: Triggered on deposit (virtual account payment) events
  • transfer: Triggered on withdrawal events
Authorizations:
ApiKeyAuth
header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Responses

Response samples

Content type
application/json
{
  • "timestamp": 1776758536186,
  • "code": 200,
  • "message": "SUCCESS",
  • "data": [
    ]
}

Update Webhook

Update an existing merchant webhook configuration.

Note: eventType cannot be changed after creation.

Authorizations:
ApiKeyAuth
path Parameters
webhookId
required
string <uuid>
Example: 717bf9b3-e8f2-4bf7-82fa-00a6bdaa7514

Webhook identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key

url
string

New webhook destination URL

headers
object

Custom headers sent with every delivery

isActive
boolean

Whether the webhook should be active

description
string

Free-text label

Responses

Request samples

Content type
application/json
{}

Response samples

Content type
application/json
{
  • "timestamp": 1776759221472,
  • "code": 200,
  • "message": "SUCCESS",
  • "data": {
    }
}

Delete Webhook

Delete an existing merchant webhook.

Event types:

  • va_payment: Triggered on deposit (virtual account payment) events
  • transfer: Triggered on withdrawal events
Authorizations:
ApiKeyAuth
path Parameters
webhookId
required
string <uuid>
Example: 717bf9b3-e8f2-4bf7-82fa-00a6bdaa7514

Webhook identifier

header Parameters
X-Api-Key
required
string
Example: your-api-key

Merchant API key

X-Signature
required
string
Example: a1b2c3d4e5f6...

HMAC-SHA512 signature of METHOD|PATH|BODY|TIMESTAMP

X-Timestamp
required
string
Example: 1774723700223

Unix timestamp in milliseconds

Request Body schema: application/json
required
requestId
required
string

Idempotency key

Responses

Request samples

Content type
application/json
{
  • "requestId": "6b0b4af8-07e4-44fe-b4b3-32a410bbfd67"
}

Response samples

Content type
application/json
{
  • "timestamp": 1776759320167,
  • "code": 200,
  • "message": "SUCCESS"
}

Webhook Retry

Retry webhook delivery for a specific transaction.

Authorizations:
ApiKeyAuth
Request Body schema: application/json
required
requestId
required
string

Idempotency key

transactionId
required
string

Transaction identifier to retry webhook for

Responses

Request samples

Content type
application/json
{
  • "requestId": "df4d98f2-243f-4fba-8146-7102f0d21312",
  • "transactionId": "019db014-af95-7294-8116-dee5285086e3"
}

Response samples

Content type
application/json
{
  • "timestamp": 1776775674878,
  • "requestId": "df4d98f2-243f-4fba-8146-7102f0d21312",
  • "code": 200,
  • "message": "SUCCESS",
  • "data": {
    }
}

Payment Simulator

Payment simulation endpoints for non-production environments only.

Prerequisites: Before simulating a deposit, you must complete the following steps:

  1. Create a user via POST /v1/users
  2. Create a virtual account for that user via POST /v1/virtual-accounts
  3. Use the simulator to send a test payment to the created VA

You can also test deposits via the UI at: https://sandbox-simulator.caci.id

Simulate Deposit Inquiry

Looks up a virtual account by account number and bank code, returning the VA details. Used to verify a VA exists before simulating a payment.

Non-production environments only. This endpoint is disabled in production.

Request Body schema: application/json
required
virtualAccountNo
required
string

Virtual account number to look up

bankCode
required
string

VA bank code — accepts BI SNAP numeric codes or provider codes

Responses

Request samples

Content type
application/json
{
  • "virtualAccountNo": "662312136281234",
  • "bankCode": "503"
}

Response samples

Content type
application/json
{
  • "timestamp": 1774723700223,
  • "code": 200,
  • "message": "SUCCESS",
  • "data": {
    }
}

Simulate Deposit Payment

Simulates an inbound deposit payment to a virtual account. Creates a completed deposit transaction and triggers the configured merchant webhook.

Non-production environments only. This endpoint is disabled in production.

Request Body schema: application/json
required
virtualAccountNo
required
string

Virtual account number to receive the payment

bankCode
required
string

VA bank code — accepts BI SNAP numeric codes (e.g. "014" for BCA, "503" for NOBU) or provider codes (e.g. "BCA", "NOBU")

required
object

Responses

Request samples

Content type
application/json
{
  • "virtualAccountNo": "662312136281234",
  • "bankCode": "503",
  • "payment": {
    }
}

Response samples

Content type
application/json
{
  • "timestamp": 1774723700223,
  • "code": 201,
  • "message": "SUCCESS",
  • "transactionId": "2f1cf3d6-65db-447e-b68c-434efbf72479"
}

Changelog

v1.0.3 — 2026-06-02

  • Added GET /v1/deposits/{transactionId} endpoint to retrieve a single deposit by its CACI transaction ID
  • Added Verifying Notifications (Required) guidance in Webhooks — confirm each notification via the read API and deduplicate so a repeated notification is never processed twice (idempotency)
  • Clarified paymentRequestId and additionalInfo.caciTxId field descriptions; caciTxId is the recommended key for deduplication / idempotency and notification verification

v1.0.2 — 2026-05-25

  • Added GET /v1/balances endpoint to retrieve merchant balances per provider and vault type
  • Added IP Whitelisting section in the overview with instructions to contact support
  • Added Source IP Addresses table in Webhooks — Production 15.233.128.42, Staging 16.78.217.189

v1.0.1 — 2026-05-20

  • Updated Virtual Account creation and update operations from asynchronous to synchronous
  • Removed "(Async)" suffix from Create Virtual Account and Update Virtual Account endpoint summaries
  • Clarified Key Features description: virtual account management no longer labeled as asynchronous

v1.0.0 — Initial Release

  • User management (CRUD) with KYC and whitelisted accounts
  • Virtual account creation and management
  • Withdrawal processing (asynchronous)
  • Deposit and withdrawal transaction inquiry
  • Payment instrument discovery
  • Webhooks creation and management
  • Payment simulation (non-production only)