Payouts allow you to manage on/off-ramp payouts.

The payout object is a convenient way to manage on/off-ramping for your customers either directly to their bank, or to another cryptocurrency wallet.

You will need to use the bankAccount object's id when identify where to send it to.

The fee breakdown is:

  • ACH: $0.50
  • ACH (return): $5.00
  • Wire: $20.00

There are no setup or KYC/B fees. All stated network fees are passed at cost.

This feature is available to merchants that have completed KYB and agreed to our terms of service and policy privacy. These compliance flows are also available in our Dashboard >> Settings >> Payouts. It is currently only available for entities with US bank accounts, with additional regional support coming soon.

It is important that you abide by the various jurisdictional regulations regarding sensitive data. Sphere does not store this data on our servers and all data is encrypted. In our interactions with licensed partners, we employ secure transfer protocols subject to GLBA, BSA/AML, FTC, and state laws.

How it works

Regardless of whether the fiat flow is on-ramp or off-ramp, you will generally:

  1. Create a bankAccount for each customer.
  2. Create a wallet for each customer.
  3. Create a payout for each instance of on/off-ramp.

Step #1 is unnecessary for walletToWallet off-ramp, which is currently only available on Solana.

For off-ramp, Step #3 will return a liquidationAddress, where the wallet address used to create the payout must send their tokens to. It is recommended that you build and serve a transaction on your frontend to let your customers transfer their tokens to this address, so that you get granular feedback on the status of pending payouts.

If you would prefer not to collect customer financial data yourself (strongly recommended unless you are familiar with dealing with sensitive financial data), we suggest using Teller to give your customers an inexpensive, pre-built bank account connection user flow where you can compliantly pass the relevant data.

The payout object

Let's take a look at a full example payout object:

{
  "id": "payout_587a3e6b1f6c4cd6a56be535e298fff6",
  "status": "pending", // pending / completed / failed 
  "amount": "1000000",
  "amountDecimal": 1,
  "type": "walletToBankAccount", // walletToWallet / bankAccountToWallet / cardToWallet (coming soon)
  "meta": {},

  "source": {
    "id": "wallet_995015d9e305415ab3900769d7943d24",
    "currency": "usd",
    "network": "eth"
  },
  "destination": {
    "id": "bankAccount_58a554b59b3e443cb3840e77b63413e2",
    "currency": "usdc",
    "network": "eth"
  },
  "customer": {
    "id": "customer_4f473af0a308438593aaea633f2ac2a8",
    "meta": {},
    "address": {
      "line1": "205 S Peoria Street",
      "line2": "Apt 12",
      "city": "Chicago",
      "postalCode": "11203",
      "state": "IL",
      "country": "US"
    },
    "email": "[email protected]",
    "name": "John Smith",
    "phone": "126172014075",
    "kyc": "complete",
    "wallets": [
      "wallet_3e55c628f52349be866d551c992a126c"
    ],
    "bankAccounts": [
      "bankAccount_05edae9ca3b64765b2b450e032922632"
    ],
    "created": "2023-10-20T16:12:13.750Z",
    "updated": "2023-10-20T16:12:13.777Z"
  },
  "depositInstructions": {
    "address": "0xD8FA8849032a4cF2B9563A27243b760B13F3B832",
    "network": "ethereum",
    "currency": "usdc",
    "amountDecimal": 1,
    "amount": "1000000"
  }
}

Attributes

id: string Unique identifier for the object. Auto-generated by Sphere upon creation.

status: enum Denotes the status of the payout, (Either pending, confirmed, failed)

amount string Total raw unit amount deposited to the destination from the payout.

amountDecimal number Total decimal adjusted.

  • Is a string because it is a BigInt.

type: enum defines if the payout is wallet to bank, or wallet to wallet.

  • enum is one of walletToBankAccount, walletToWallet, or bankAccountToWallet.
  • walletToBankAccount: the source must be a wallet, the destination must be a bank account.
  • walletToWallet: the source must be a wallet, the destination must also be a wallet.
  • bankAccountToWallet: the source must be a bank account, the destination must be a wallet.

source: object The source of the payout.

  • id: string The public key for the wallet that is originating the payout.
  • currency string The original currency that is being paid out.
    • For crypto, is the public key of the token mint address (Solana) or token contract (EVM).
    • For convenience, you can also pass in usdc, usdt, or sol.
    • For fiat, is one of usd (gbp and euro coming soon).
  • network string Identifies the source network from which the payout is coming from.

destination: object The destination for the payout. Can either be a public key or bankAccount.

  • id string Unique identifier of the bank account or the public key which will receive the payout.
  • currency string The currency that the payout is converted to, and deposited in.
    • If crypto, then it is either a token mint address (Solana) or token contract address (EVM).
    • For convenience, you can also pass in usdc, usdt, or sol.
    • If fiat, then one of usd, euro, gbp. Defaults to usd.
  • network string Identifies the destination network that the payout is going to be delivered on.
    • Can be either blockchains - sol, eth, tron (coming soon), etc.
    • Or can be fiat - ach or wire. (Push payments to debit coming soon).
  • created: string datetime for when the payout object was created.