Wallets

Create and manage single-asset wallets in the Amboss Payments API. One wallet per asset (BTC sats or Taproot Assets like USDT).

A wallet holds balance in exactly one asset (BTC sats, or a Taproot Asset like USDT). One wallet, one asset, one balance. Create separate wallets for each asset you want to support.

Wallets are scoped to a single environment. A wallet's id is the value you pass to create_receive and create_send.

Assets

Query the live asset list at runtime — don't hard-code symbols. BTC appears as a base asset; stablecoins (USDT, USDC, …) appear as Taproot Assets.

query AvailableAssets {
  taproot_assets {
    list {
      id
      symbol
      precision
      type
    }
  }
}

precision tells you the asset's smallest unit:

AssetprecisionSmallest unit
BTC8satoshi (1e-8 BTC)
USDT, USDC61 micro-unit (1e-6 USD)

Create a wallet

Wallets are created with a service API key that has WALLETS: WRITE permission. See API Keys.

mutation CreateWallet {
  payment {
    wallet {
      create(input: {
        name: "Main USDT wallet"
        environment_id: "81b73615-ddf3-46e3-943a-467c3e442e04"
        asset_id: "<asset_id from taproot_assets.list>"
      }) {
        id
        name
        is_ready
        asset { symbol precision }
        balance { balance received sent }
      }
    }
  }
}
curl -X POST https://rails.amboss.tech/graphql \
  -H "Content-Type: application/json" \
  -H "x-api-key: $AMBOSS_API_KEY" \
  -d '{
    "query": "mutation($input: CreatePaymentsWalletInput!) { payment { wallet { create(input: $input) { id name is_ready asset { symbol precision } balance { balance received sent } } } } }",
    "variables": {
      "input": {
        "name": "Main USDT wallet",
        "environment_id": "81b73615-ddf3-46e3-943a-467c3e442e04",
        "asset_id": "<asset_id>"
      }
    }
  }'
import { GraphQLClient, gql } from "graphql-request";

const client = new GraphQLClient("https://rails.amboss.tech/graphql", {
  headers: { "x-api-key": process.env.AMBOSS_API_KEY },
});

const CREATE_WALLET = gql`
  mutation CreateWallet($input: CreatePaymentsWalletInput!) {
    payment {
      wallet {
        create(input: $input) {
          id
          name
          is_ready
          asset { symbol precision }
          balance { balance received sent }
        }
      }
    }
  }
`;

const { payment } = await client.request(CREATE_WALLET, {
  input: {
    name: "Main USDT wallet",
    environment_id: process.env.AMBOSS_ENV_ID,
    asset_id: process.env.AMBOSS_ASSET_ID_USDT,
  },
});
console.log(payment.wallet.create.id);

Example response:

{
  "data": {
    "payment": {
      "wallet": {
        "create": {
          "id": "5e4b1e2a-9f3c-4a5b-8c7d-1234567890ab",
          "name": "Main USDT wallet",
          "is_ready": true,
          "asset": { "symbol": "USDT", "precision": 6 },
          "balance": { "balance": "0", "received": "0", "sent": "0" }
        }
      }
    }
  }
}

Wallet readiness

is_ready indicates whether the wallet can receive payments:

  • Sandbox: is_ready is true immediately. Sandbox wallets don't need any liquidity provisioning.
  • Live: is_ready flips to true once liquidity has been provisioned for the wallet. This takes around 30 minutes — poll the wallet or wait for the corresponding webhook event before issuing invoices.

Querying readiness later:

query GetWallet($id: String!) {
  payment {
    wallet {
      find_one(id: $id) {
        id
        is_ready
        balance { balance received sent }
      }
    }
  }
}

Amount handling

Every amount in the API is a decimal string in the asset's minor units.

  • BTC: sats. "100000" = 0.001 BTC.
  • USDT/USDC (precision 6): micro-units. "1000000" = 1 USDT.

Never pass floats or JS numbers — the API rejects them. Use string-encoded integers. The validator regex is /^[1-9]\d*$/, so "0" and leading zeros are also rejected for input amounts.

Next steps