Create a customer and an account

For integration engineers. Register a customer under your own reference, register a GBP token account for them, and wait for it to be provisioned.

Who this is for

Engineers who have a token from 1. Authenticate. By the end of this step you have two customers, each with an ACTIVE GBP account and a wallet address.

How customers and accounts work

  • A customer is your customer, registered under your own reference (customerRef). The platform stores the reference and never interprets it. It must be unique within your organisation. Your core banking system stays the book of record for who the customer is.
  • An account holds one asset for one customer, under your own reference (accountRef). Registering an account starts provisioning a wallet for it.
  • A customer is ACTIVE from registration. An account starts PENDING and becomes ACTIVE once provisioning completes, or FAILED if it cannot be provisioned.
Account statusMeaningCan it take token operations?
PENDINGRegistered, provisioning under wayNo
ACTIVEProvisioned, walletAddress is setYes
FAILEDProvisioning was refused, failureReason is setNo. Registering the same accountRef again retries provisioning
INACTIVEDeactivatedNo new operations. Balances can still be read

Three preconditions apply before an account can be registered:

  1. The customer exists and is ACTIVE.
  2. The asset has an ACTIVE token contract.
  3. The accountRef is not already in use by an account in any status other than FAILED.

Wait for account readiness

Customer registration and account readiness are different milestones. The currency contract and customer must be active before account registration; the account must finish provisioning before it can take token operations.

%%{init: {"theme": "neutral"}}%%
flowchart TB
    Customer["Active customer"] --> Register["Register account"]
    Currency["Active contract"] --> Register
    Register --> Pending["Provisioning"]
    Pending --> Ready["Active account"]
    Pending --> Failed["Failed account"]

Read the account to establish its current status. A pending or failed account is not ready for issuance or transfer. Use the documented registration behaviour to retry failed provisioning after its cause is addressed.

View in API Reference

Worked example

Check the asset has an active contract

GET /api/contracts?assetId=GBP&status=ACTIVE HTTP/1.1
Host: api.qfp.quantnetwork.net
Authorization: Bearer eyJraWQiOiJ...
API-Version: 1.0.0

Illustrative example built from the schema. Key and custody reference fields are omitted.

HTTP/1.1 200 OK
Content-Type: application/json

{
  "content": [
    {
      "id": "3f6c1b2a-9d54-4e7c-8b31-0a2f5c7d9e10",
      "assetId": "GBP",
      "contractAddress": "0x7c3aEd41D0f3b6a92cF8e0d1B54a2eD9c15b8A64",
      "decimals": 2,
      "status": "ACTIVE",
      "createdAt": "2026-08-03T09:10:02.118Z",
      "updatedAt": "2026-08-03T09:10:02.118Z"
    }
  ],
  "page": 0,
  "size": 20,
  "totalElements": 1,
  "totalPages": 1
}

An empty content array means no active contract exists for GBP, and account registration will return 404. Contracts are registered with POST /api/contracts. Agree contract deployment responsibilities with the operator. Read the registered contract's decimals value instead of assuming it from the currency code.

Register the customer

POST /api/customers HTTP/1.1
Host: api.qfp.quantnetwork.net
Authorization: Bearer eyJraWQiOiJ...
API-Version: 1.0.0
Content-Type: application/json
Idempotency-Key: 2b8e4f10-6c3a-4d9e-8f21-5a7b0c9d1e32

{
  "customerRef": "CUST-0001"
}
HTTP/1.1 201 Created
Content-Type: application/json

{
  "customerRef": "CUST-0001",
  "status": "ACTIVE",
  "createdAt": "2026-08-03T09:24:11.482Z",
  "updatedAt": "2026-08-03T09:24:11.482Z"
}

Register the account

POST /api/accounts HTTP/1.1
Host: api.qfp.quantnetwork.net
Authorization: Bearer eyJraWQiOiJ...
API-Version: 1.0.0
Content-Type: application/json
Idempotency-Key: 9d4a7c21-3e5b-4f80-a162-8b0e5d3c7f94

{
  "customerRef": "CUST-0001",
  "accountRef": "ACC-0001",
  "assetId": "GBP"
}
HTTP/1.1 202 Accepted
Content-Type: application/json

{
  "accountRef": "ACC-0001",
  "customerRef": "CUST-0001",
  "assetId": "GBP",
  "status": "PENDING",
  "createdAt": "2026-08-03T09:29:10.285Z",
  "updatedAt": "2026-08-03T09:29:10.285Z"
}

202 means the account exists and provisioning is under way. There is no wallet address yet.

Wait for provisioning

Read the account until status is ACTIVE or FAILED. Use bounded polling with backoff and a locally configured deadline. Provisioning duration is deployment-dependent; a local timeout leaves the account state unknown until a read confirms it. You can also subscribe to the account.provisioned and account.provisioning_failed webhook events in 6. Receive your first webhook. Use GET /api/accounts/{accountRef} as the readiness check. The public event catalogue includes account.provisioned, but account-registration documentation does not guarantee a callback; confirm delivery in your environment and retain read-based recovery.

GET /api/accounts/ACC-0001 HTTP/1.1
Host: api.qfp.quantnetwork.net
Authorization: Bearer eyJraWQiOiJ...
API-Version: 1.0.0
HTTP/1.1 200 OK
Content-Type: application/json

{
  "accountRef": "ACC-0001",
  "customerRef": "CUST-0001",
  "assetId": "GBP",
  "status": "ACTIVE",
  "walletAddress": "0x4E55aD154FFfE514D7dEF1658dEbe593907121ae",
  "createdAt": "2026-08-03T09:29:10.285Z",
  "updatedAt": "2026-08-03T09:29:14.911Z"
}

Repeat for the counterparty

Step 5 transfers tokens to a second customer. Register CUST-0002 and its GBP account ACC-0002 the same way, each with a new Idempotency-Key.

Illustrative example built from the schema.

POST /api/customers HTTP/1.1
Host: api.qfp.quantnetwork.net
Authorization: Bearer eyJraWQiOiJ...
API-Version: 1.0.0
Content-Type: application/json
Idempotency-Key: 4c1f9e83-7a2d-4b56-9e08-1d3c6a5b8f27

{
  "customerRef": "CUST-0002"
}
POST /api/accounts HTTP/1.1
Host: api.qfp.quantnetwork.net
Authorization: Bearer eyJraWQiOiJ...
API-Version: 1.0.0
Content-Type: application/json
Idempotency-Key: e7b2d5a0-1f4c-4a39-8d6e-0c9b3f2a7e15

{
  "customerRef": "CUST-0002",
  "accountRef": "ACC-0002",
  "assetId": "GBP"
}

Wait for ACC-0002 to reach ACTIVE before step 5.

View in API Reference

Errors and edge cases

StatusWhenWhat to do
400A required field is missing or invalid, or Idempotency-Key is missing, blank or longer than 255 charactersFix the request
404 on account registrationThe customer does not exist, or the asset has no ACTIVE contractRegister the customer, or confirm the contract as above
409 with customerRef or accountRef and existingStatus in the bodyThe reference is already registered (for an account: in a status other than FAILED)Do not retry. Read the existing record
409 with neither field, and a Retry-After headerAn earlier request under the same Idempotency-Key is still runningWait the number of seconds in Retry-After and retry with the same key
422The customer is INACTIVE, or the same Idempotency-Key was reused with a different payloadReactivate the customer, or use a new key for a new request
Account FAILEDProvisioning was refused. failureReason says whyRegister the same accountRef again to reset it to PENDING and retry provisioning

A replay of the same Idempotency-Key with the same payload returns the first response unchanged.

Example of the already-registered conflict:

HTTP/1.1 409 Conflict
Content-Type: application/json

{
  "timestamp": "2026-08-03T09:29:10.285Z",
  "status": 409,
  "error": "Conflict",
  "message": "An account is already registered for accountRef 'ACC-0001'.",
  "accountRef": "ACC-0001",
  "existingStatus": "ACTIVE"
}

Example of a failed account:

{
  "accountRef": "ACC-0003",
  "customerRef": "CUST-0001",
  "assetId": "JPY",
  "status": "FAILED",
  "failureReason": "Unsupported asset id 'JPY'",
  "createdAt": "2026-08-03T10:05:19.663Z",
  "updatedAt": "2026-08-03T10:05:21.204Z"
}

Follow a Recipe

Step through the code in JavaScript or Python, inspect illustrative responses, and open the connected endpoint schemas.

API Reference

Open an endpoint for request fields, response examples and the interactive API console.

Related pages

Implementation resources

Customers code recipes.

Use Implement a backend client for request handling, durable idempotency and outcome tracking. The developer integration coverage map links every public operation to its API Reference and contract-derived code recipe. Replace example identifiers with values from your assigned environment.


Did this page help you?