> ## Documentation Index
> Fetch the complete documentation index at: https://docs.jenzy.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Create a payout

> Reserve the money and pay a beneficiary in `asset`. `amount` is what they receive; your `source_asset` balance is debited `source_amount` plus `fee`. The destination is validated before any money is reserved, so a refusal (422) leaves nothing behind. The response is the payout as it stands after the payment network has answered — normally `pending`; a payout may be `failed` in its creation response, with the reserved money already released. Requires an `Idempotency-Key`.



## OpenAPI

````yaml /v2/openapi.json post /payouts
openapi: 3.1.0
info:
  title: Jenzy Hermes Multi-asset API
  version: 2.0.0
  description: >-
    Hold, convert and pay out across the assets enabled for your organization.
    Every amount is an exact decimal string beside an `asset` field.
    Authenticate with the same `jz_live_…` API key as `/v1`.
servers:
  - url: https://api.jenzy.com/v2
    description: Production
security: []
paths:
  /payouts:
    post:
      summary: Create a payout
      description: >-
        Reserve the money and pay a beneficiary in `asset`. `amount` is what
        they receive; your `source_asset` balance is debited `source_amount`
        plus `fee`. The destination is validated before any money is reserved,
        so a refusal (422) leaves nothing behind. The response is the payout as
        it stands after the payment network has answered — normally `pending`; a
        payout may be `failed` in its creation response, with the reserved money
        already released. Requires an `Idempotency-Key`.
      parameters:
        - schema:
            type: string
            description: >-
              Required. A key you mint per payout intent (a UUID works). Replays
              of the same key + body return the original response; the same key
              with a different body is a 409.
          required: true
          description: >-
            Required. A key you mint per payout intent (a UUID works). Replays
            of the same key + body return the original response; the same key
            with a different body is a 409.
          name: Idempotency-Key
          in: header
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PayoutCreate'
      responses:
        '201':
          description: >-
            Created. `status` is normally `pending`; it can be `held` (the
            payment network has not yet acknowledged — poll) or already
            `failed`.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Payout'
        '400':
          description: >-
            Malformed body, missing `Idempotency-Key`, or an `amount` with more
            decimals than the asset carries.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorEnvelope'
        '402':
          description: >-
            `insufficient_funds`: your available balance in `source_asset` does
            not cover `source_amount` + fee + reserve, or a shortfall in it must
            clear first.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorEnvelope'
        '403':
          description: >-
            `corridor_not_enabled`: `asset` is not enabled for payouts for your
            organization, or `source_asset` is not enabled. Also the access
            codes above.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorEnvelope'
        '409':
          description: >-
            This `Idempotency-Key` was already used with a different request, or
            its original request is still in progress.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorEnvelope'
        '422':
          description: >-
            The destination is unpayable (`unknown_institution`,
            `invalid_mobile_number`, `invalid_account_number`,
            `invalid_wallet_address`), the pair is `unsupported_pair`, or the
            amount is outside the corridor (`amount_below_minimum`,
            `limit_exceeded`).
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorEnvelope'
        '503':
          description: >-
            `rate_unavailable` (no fresh rate to price the fee),
            `service_unavailable` (no rate for an FX payout), or the `/v2`
            shutter is closed (`service_maintenance` / `service_incident`) —
            your `Idempotency-Key` is NOT spent by a shutter refusal.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorEnvelope'
      security:
        - ApiKeyAuth: []
components:
  schemas:
    PayoutCreate:
      type: object
      properties:
        amount:
          anyOf:
            - type: integer
            - type: string
              pattern: ^\d+(\.\d+)?$
          description: >-
            What the beneficiary receives, in `asset`. Fees and any FX are on
            top, in `source_asset`.
          example: '10000.00'
        asset:
          type: string
          minLength: 1
          description: The asset the beneficiary receives.
          example: KES
        source_asset:
          type: string
          minLength: 1
          description: >-
            The asset you pay from. Defaults to `asset`. A stablecoin balance
            can pay a fiat beneficiary (the FX payout); any other mixed pair is
            `unsupported_pair`.
          example: USDT
        destination:
          oneOf:
            - $ref: '#/components/schemas/BankDestinationCreate'
            - $ref: '#/components/schemas/MomoDestinationCreate'
            - $ref: '#/components/schemas/WalletDestinationCreate'
          discriminator:
            propertyName: type
            mapping:
              bank:
                $ref: '#/components/schemas/BankDestinationCreate'
              momo:
                $ref: '#/components/schemas/MomoDestinationCreate'
              wallet:
                $ref: '#/components/schemas/WalletDestinationCreate'
      required:
        - amount
        - asset
        - destination
    Payout:
      type: object
      properties:
        id:
          type: string
          format: uuid
          description: Payout id — your handle for polling and support.
        status:
          type: string
          enum:
            - received
            - validated
            - held
            - submitted
            - pending
            - succeeded
            - failed
            - reversed
          description: >-
            Lifecycle: `held` (money reserved, the payment network has not yet
            acknowledged) → `pending` → `succeeded` | `failed`. `succeeded`,
            `failed` and `reversed` are terminal. A payout may already be
            `failed` in its creation response: the destination was accepted but
            the payment network refused it at once, and the reserved money is
            released. `reversed` means the payout succeeded and was then clawed
            back — it is not a failure and carries no `failure` object.
          example: pending
        asset:
          type: string
          minLength: 1
          description: >-
            An asset code as `GET /v2/assets` lists it — uppercase, never
            compound (`KES`, `USDT`; never `USDT-TRON`). Network and rail live
            on the payment object.
          example: KES
        amount:
          type: string
          description: >-
            What the beneficiary receives, as an exact decimal string in
            `asset`.
          example: '10000.00'
        source_asset:
          type: string
          minLength: 1
          description: What you paid from.
          example: USDT
        source_amount:
          type: string
          description: >-
            What is debited from your `source_asset` balance for the beneficiary
            amount, FX included; equals `amount` when the assets are the same.
            Your fee is on top.
          example: '77.8875'
        fee:
          type: string
          description: Jenzy’s payout fee, one total, in `source_asset`. Known at creation.
          example: '0.8'
        rate:
          type:
            - string
            - 'null'
          description: >-
            `source_amount ÷ amount` at 8 decimal places — `source_asset` per 1
            `asset` — when the assets differ; null otherwise. Informational: the
            two amounts are the contract.
          example: '0.00778875'
        destination:
          oneOf:
            - type: object
              properties:
                type:
                  type: string
                  enum:
                    - bank
                institution_id:
                  type: string
                account_number:
                  type: string
                beneficiary_name:
                  type: string
              required:
                - type
                - institution_id
                - account_number
                - beneficiary_name
            - type: object
              properties:
                type:
                  type: string
                  enum:
                    - momo
                institution_id:
                  type: string
                mobile_number:
                  type: string
                beneficiary_name:
                  type: string
              required:
                - type
                - institution_id
                - mobile_number
                - beneficiary_name
            - type: object
              properties:
                type:
                  type: string
                  enum:
                    - wallet
                network:
                  type: string
                address:
                  type: string
                beneficiary_name:
                  type: string
                beneficiary_type:
                  type: string
                  enum:
                    - individual
                    - business
                beneficiary_country:
                  type: string
                beneficiary_date_of_birth:
                  type:
                    - string
                    - 'null'
              required:
                - type
                - network
                - address
                - beneficiary_name
                - beneficiary_type
                - beneficiary_country
                - beneficiary_date_of_birth
        failure:
          type:
            - object
            - 'null'
          properties:
            code:
              type: string
              enum:
                - recipient_account_invalid
                - declined
                - provider_unavailable
                - temporarily_unavailable
            message:
              type: string
          required:
            - code
            - message
          description: >-
            Set only when `status` is `failed`: one of the published codes with
            its fixed message. Detail from the payment network is never
            included.
        created_at:
          type: string
          format: date-time
        terminal_at:
          type:
            - string
            - 'null'
          format: date-time
          description: >-
            When the payout reached `succeeded`, `failed` or `reversed`; null
            while in flight.
      required:
        - id
        - status
        - asset
        - amount
        - source_asset
        - source_amount
        - fee
        - rate
        - destination
        - failure
        - created_at
        - terminal_at
    ErrorEnvelope:
      type: object
      properties:
        error:
          type: object
          properties:
            code:
              type: string
              enum:
                - validation_error
                - unauthorized
                - forbidden
                - not_found
                - conflict
                - rate_limited
                - internal_error
                - unknown_institution
                - invalid_mobile_number
                - invalid_account_number
                - mobile_number_institution_mismatch
                - service_unavailable
                - sandbox_only
                - insufficient_funds
                - rail_disabled
                - amount_limit_exceeded
                - org_limit_exceeded
                - service_incident
                - service_maintenance
                - onboarding_incomplete
                - access_suspended
                - corridor_not_enabled
                - unsupported_pair
                - invalid_wallet_address
                - rate_unavailable
                - quote_expired
                - quote_used
                - limit_exceeded
                - amount_below_minimum
                - unsupported_asset
              description: >-
                Stable identifier a client may branch on — never renamed or
                removed.
            message:
              type: string
          required:
            - code
            - message
      required:
        - error
    BankDestinationCreate:
      type: object
      properties:
        type:
          type: string
          enum:
            - bank
        institution_id:
          type: string
          minLength: 1
          description: >-
            An `institution_id` from `GET /v2/institutions?asset=` whose `type`
            matches this destination.
          example: kes-bank-kenya-commercial-bank-limited
        account_number:
          type: string
          minLength: 1
          description: >-
            Digits only, no spaces or separators. The allowed length depends on
            the asset (5–20 for KES). No name check exists: `beneficiary_name`
            is sent and stored, never verified against the account.
          example: '1000012345'
        beneficiary_name:
          type: string
          minLength: 1
          description: >-
            Who the money is for. Sent to the payment network as given — it is
            not verified against the account.
          example: Jane Doe
      required:
        - type
        - institution_id
        - account_number
        - beneficiary_name
    MomoDestinationCreate:
      type: object
      properties:
        type:
          type: string
          enum:
            - momo
        institution_id:
          type: string
          minLength: 1
          description: >-
            An `institution_id` from `GET /v2/institutions?asset=` whose `type`
            matches this destination.
          example: kes-momo-m-pesa
        mobile_number:
          type: string
          minLength: 1
          description: >-
            E.164 with the leading `+` and no spaces (`+254712345678`). The
            country code must match the asset’s country. A number in any other
            form is rejected, never corrected.
          example: '+254712345678'
        beneficiary_name:
          type: string
          minLength: 1
          description: >-
            Who the money is for. Sent to the payment network as given — it is
            not verified against the account.
          example: Jane Doe
      required:
        - type
        - institution_id
        - mobile_number
        - beneficiary_name
    WalletDestinationCreate:
      type: object
      properties:
        type:
          type: string
          enum:
            - wallet
        network:
          type: string
          minLength: 1
          description: >-
            The network by name: `ethereum`, `solana`, `tron`. The asset must be
            supported on it (`invalid_wallet_address` names the supported
            networks otherwise).
          example: tron
        address:
          type: string
          minLength: 1
          maxLength: 64
          description: >-
            The beneficiary wallet address, checked for shape on every network.
            An Ethereum address in mixed case must carry a valid EIP-55
            checksum; all-lowercase is accepted. Addresses that need a memo or
            destination tag are not supported.
          example: TN3W4H6rK2ce4vX9YnFQHwKENnHjoxb3m9
        beneficiary_name:
          type: string
          minLength: 1
          description: >-
            Who the money is for. Sent to the payment network as given — it is
            not verified against the account.
          example: Jane Doe
        beneficiary_type:
          type: string
          enum:
            - individual
            - business
          description: Defaults to `individual`.
        beneficiary_country:
          type: string
          minLength: 2
          maxLength: 2
          description: ISO 3166-1 alpha-2 (`KE`).
          example: KE
        beneficiary_date_of_birth:
          type: string
          description: YYYY-MM-DD. Required when `beneficiary_type` is `individual`.
          example: '1990-02-28'
      required:
        - type
        - network
        - address
        - beneficiary_name
        - beneficiary_country
  securitySchemes:
    ApiKeyAuth:
      type: http
      scheme: bearer
      description: 'Your Jenzy API key: `Authorization: Bearer jz_live_…`'

````