Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.lumx.io/llms.txt

Use this file to discover all available pages before exploring further.

Build a treasury product for corporate customers that need to hold working capital across multiple currencies, sweep funds between related entities, and execute FX conversions on demand. Balances are centralized in stablecoin in each entity’s wallet, and converted to local fiat only when needed.

Step 1: Generate your API key

Head over to dashboard.lumx.io. Once logged in, generate a new API key and store it securely. See Authentication for details.

Step 2: Onboard the corporate with multi-currency accounts

Create a business customer for the entity that will hold the treasury. Provision the fiat accounts they need so incoming deposits are converted to stablecoin and consolidated in the customer’s wallet automatically. See Coverage for supported currencies and rails.
Request
curl -X POST https://api-sandbox.lumx.io/customers \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: $(uuidgen)" \
  -d '{
    "type": "BUSINESS",
    "legalName": "Acme Holdings Ltd.",
    "taxId": "123456-7",
    "incorporationDate": "2019-01-15",
    "country": "CYM",
    "email": "treasury@acme.com",
    "accounts": ["USD", "EUR", "BRL", "MXN"]
  }'
Before the corporate can transact, they must accept Lumx’s terms of service (POST /customers/{id}/tos) and complete KYB. See Business verification for the full onboarding flow.

Step 3: Fund the corporate’s wallet

Once each account is ACTIVE, create an on-ramp transaction for every expected deposit, passing the exact amount the corporate plans to fund. The response returns rail-specific payment details in state.payment. Share them with the corporate’s treasury team; when the deposit matches the amount, Lumx converts the fiat to stablecoin and consolidates it in the customer’s wallet.
Request
curl -X POST https://api-sandbox.lumx.io/transactions/on-ramp \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: $(uuidgen)" \
  -d '{
    "customerId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
    "rail": "FEDWIRE",
    "sourceCurrency": "USD",
    "sourceAmount": "1000000.00",
    "targetCurrency": "USDC",
    "purpose": "PERSONAL_ACCOUNT"
  }'
Each deposit must be matched to an on-ramp transaction created in advance with the exact amount.
All deposits land as stablecoin in the same wallet. The corporate doesn’t hold separate per-currency balances. If the corporate already holds stablecoin on-chain, they can also transfer it directly to the wallet returned at customer creation, no on-ramp needed. Subscribe to the onramp.success webhook to know the moment the wallet is credited and balances are ready to be moved or converted. For the full deposit flow by rail, see Global accounts.

Step 4: Onboard subsidiaries and counterparty destinations

How you model the corporate group depends on whether each entity needs its own wallet. Multi-entity (each subsidiary holds its own balance): onboard each subsidiary as its own business customer. Each gets a dedicated wallet, and you can move funds between them with internal transfers. Single-entity (parent holds all balances): register each related external destination under the parent customer with the appropriate holder.relationship so transfers out are correctly categorized.
RelationshipUse when
SELFThe destination belongs to the same legal entity as the customer
HOLDING_COMPANYThe destination belongs to the parent of the customer
SUBSIDIARY_COMPANYThe destination belongs to a subsidiary of the customer
The taxId format varies by jurisdiction; see Tax IDs by country for the expected value per country.
Register a subsidiary's destination under the parent
curl -X POST https://api-sandbox.lumx.io/destinations \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: $(uuidgen)" \
  -d '{
    "customerId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
    "name": "Acme US - Operations",
    "rail": "FEDWIRE",
    "currency": "USD",
    "identifier": {
      "type": "CHECKING",
      "accountNumber": "123456789012",
      "routingNumber": "021000021"
    },
    "bank": {
      "name": "JPMorgan Chase Bank",
      "address": {
        "line1": "383 Madison Avenue",
        "city": "New York",
        "state": "NY",
        "postalCode": "10179",
        "country": "USA"
      }
    },
    "holder": {
      "type": "BUSINESS",
      "relationship": "SUBSIDIARY_COMPANY",
      "legalName": "Acme US Inc.",
      "taxId": "12-3456789",
      "incorporationDate": "2020-03-15",
      "email": "us@acme.com",
      "address": {
        "line1": "100 Wall Street",
        "city": "New York",
        "state": "NY",
        "postalCode": "10005",
        "country": "USA"
      }
    }
  }'
See Destinations for all supported rails and the full holder schema.

Step 5: Move funds between entities

When subsidiaries are onboarded as separate customers, move stablecoin between their wallets without going through fiat. Transfers settle in seconds and don’t incur FX cost.
Request
curl -X POST https://api-sandbox.lumx.io/transactions/transfer \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: $(uuidgen)" \
  -d '{
    "from": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
    "to": "980dc26b-42fd-4044-8a42-2271d20a2eb9",
    "currency": "USDC",
    "amount": "100000.000000",
    "metadata": {
      "memo": "Q2 working capital injection - Acme US"
    }
  }'
Response
{
  "id": "123e4567-e89b-12d3-a456-426614174004",
  "type": "TRANSFER",
  "state": { "status": "PENDING" },
  "request": {
    "currency": "USDC",
    "from": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
    "to": "980dc26b-42fd-4044-8a42-2271d20a2eb9",
    "amount": "100000.000000"
  }
}

Step 6: Convert balances to fiat on demand

When the corporate needs to settle in fiat (paying a supplier, repatriating profits, funding a subsidiary’s local account), create an off-ramp transaction debiting the wallet. Use the purpose code that matches the move:
ScenarioPurpose
Sweep to the entity’s own external accountPERSONAL_ACCOUNT (requires a destination with SELF holder relationship)
Loan or capital injection between related entitiesLOAN
Cross-border supplier or invoice paymentTRADE_TRANSACTIONS
Tax remittanceTAX
Bill paymentBILLS
See Purpose codes for the full list and rules.
Request
curl -X POST https://api-sandbox.lumx.io/transactions/off-ramp \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: $(uuidgen)" \
  -d '{
    "destinationId": "e80d3137-eddd-4791-b9b8-6e36b289f284",
    "sourceCurrency": "USDC",
    "sourceAmount": "50000.00",
    "purpose": "LOAN"
  }'
For predictable FX (budgeting, monthly settlements, locked supplier quotes), fetch a locked exchange rate first and pass its id as exchangeRateId on the off-ramp request. See Exchange Rates.

Step 7: Track and reconcile

Subscribe to offramp.success, offramp.failed, transfer.success, and account.active webhooks to keep balances, transfers, and conversion status in sync inside your product. See Webhooks.

Global accounts

Provision multi-currency virtual accounts.

Exchange Rates

Lock FX rates for predictable conversions.

Destinations

Holder relationships for inter-company moves.

Transactions

Transfer, off-ramp lifecycle and purpose codes.