---
title: "Create a Payment"
method: POST
path: "/payments"
tags: ["Payments"]
---

# Create a Payment

`POST /payments`

## Request

- Base URL: `https://api.justifi.ai/v1`
- URL: `https://api.justifi.ai/v1/payments`
- Auth: none declared. Required headers: `Idempotency-Key`, `Authorization`, `Sub-Account`
- TypeScript: <https://skmtc.dev/justifi/apis/justifi-api-documentation/docs/payments/post.ts> (a function with typed inputs; its response is checked against the schema)

Authorize, capture, and charge a payment method. We limit concurrency to 10 concurrent requests per platform.
This is due to the nature of the payments API, to reduce rejections, and false positive fraud detection during bulk
payment processing.

**Payment methods must be tokenized before creating a payment.** Tokenize payment methods use the embedded
**[JustiFi Tokenize Payment Method Web Component](https://docs.justifi.tech/web-components/payment-facilitation/tokenize-payment-method)** 
to securely collect and tokenize card or bank account details.

Once you have a payment method token (e.g. `pm_justifi123`), pass it in the `payment_method.token` field to create a payment.

> **Note:** Passing raw card or bank account details directly to this endpoint requires prior approval. Contact [JustiFi Customer Success](mailto:customer_success@justifi.tech) 
if you have a use case that requires direct PAN submission. At minimum, a completed SAQ (Self-Assessment Questionnaire) is required to allow raw PAN submissions.

*Note: If the sub account status is not `enabled`, `400` will be returned.*

## Headers

- `Idempotency-Key` string, uuid, required
- `Authorization` string, required
- `Sub-Account` string, required

## Request body

- object
  - `amount` number, required: amount to charge in cents
  - `currency` 'usd' | 'cad', required
  - `capture_strategy` 'automatic' | 'manual', required: automatic will authorize and capture the payment in the same request; manual will only authorize the payment. An authorized payment will need to be captured in a subsequent capture payment request. If not captured within 7 days the payment will be canceled. Not supported by bank account (ACH) payment methods.
  - `email` string, email: email address to associate with payment method
  - `payment_method` object, required
    - `token` string, required: A payment method token obtained from the JustiFi Tokenize Payment Method Web Component.
  - `application_fee_amount` integer: Sets a custom application fee amount that applies to this payment, instead of relying on application fee rates configured at the platform account level (*only Platforms may set application_fee_amount*). Must be greater than zero. **New integrations** should use the `fees` array instead for granular control over fee types and selective refunds. See [Enhanced Fee Management](#section/Enhanced-Fee-Management). Cannot be used together with `fees`. > **CAD Payments:** This parameter is not available for CAD payments. Fees for Canadian dollar payments are determined during merchant onboarding and are not configurable via the API. See [Canadian Payments](https://docs.justifi.tech/payments/canadianPayments) for details.
  - `fees` Fee[]: Array of fee objects to charge on this payment. See [Enhanced Fee Management](https://docs.justifi.tech/api-spec#section/Enhanced-Fee-Management) for full documentation. Each fee object specifies: - `type`: `processing_fee` or `platform_fee` (required) - `amount`: Fee amount in cents (required) **Benefits over `application_fee_amount`:** - Separate fee types for clear reporting - Selective refunds: Choose which fees to return - Each fee type appears as a separate balance transaction Cannot be used together with `application_fee_amount`. > **Note:** The `fees` array will be empty in the create response. Fees are processed asynchronously — subscribe to payment webhook events (recommended) to receive the full fee details, or poll with a subsequent [Get Payment](#tag/Payments/operation/GetPayment) request. > **CAD Payments:** This parameter is not available for CAD payments. Fees for Canadian dollar payments are determined during merchant onboarding and are not configurable via the API. See [Canadian Payments](https://docs.justifi.tech/payments/canadianPayments) for details.
    - `type` 'processing_fee' | 'platform_fee', required: The type of fee: - `processing_fee`: Fees related to payment processing costs - `platform_fee`: Fees for your platform's services
    - `amount` integer, required: Fee amount in cents
  - `description` string: your meaningful description of the payment (e.g. an order number or other value from your system)
  - `statement_descriptor` string: description of the payment that will be available on the account's bank statement, must have between 5-22 alphanumeric characters and can include dash or underscore
  - `metadata` object: Any useful information you'd like to store alongside this payment. **Testing Disputes**: Include `dispute_test_spec` to create test disputes: - `expected_result`: `"won"` or `"lost"` - Final dispute outcome - `reason`: Dispute reason (`"fraudulent"`, `"unrecognized"`, `"duplicate"`, `"subscription_canceled"`, `"product_unacceptable"`, `"product_not_received"`, `"processing_error"`, `"credit_not_processed"`, `"general"`) - `due_date`: Response deadline in YYYY-MM-DD format - `event_publish_delay_in_seconds`: Delay before dispute creation (default: 0)
  - `expedited` boolean, nullable: settlement priority of the payment, only applies to ACH payments

## Response `201`

Payment was created successfully

- object
  - `id` string, uuid: the object id, also found in the data object
  - `type` string: the object type, or array of objects
  - `data` union
    - object: the attributes for the object
      - `id` string: unique payment id
      - `account_id` string, uuid
      - `amount` number: payment amount in cents
      - `amount_disputed` number: sum of open or lost disputes for this payment, in cents
      - `amount_refunded` number: sum of refunds for this payment, in cents
      - `amount_refundable` number: amount of this payment currently able to be refunded, in cents
      - `balance` number: sum of debits and credits for this payment, in cents (reflects the amount this account has earned from this payment). Compiled and calculated value, eventually consistent. To see all changes affecting the payment's balance call [Get Balance Transactions](#operation/GetPaymentBalanceTransactions)
      - `fee_amount` number: sum of fees for this payment
      - `financial_transaction_id` string: associated financial transaction id
      - `captured` boolean: whether or not this payment is captured
      - `capture_strategy` 'automatic' | 'manual'
      - `currency` 'usd' | 'cad'
      - `description` string: your meaningful description of the payment (e.g. an order number or other value from your system)
      - `disputed` boolean: whether or not this payment has any open or lost disputes
      - `disputes` unknown[]: list of associated disputes
        - unknown
      - `error_code` string: error code if the payment fails
      - `error_description` string: text description of the error code
      - `is_test` boolean: whether or not this payment was made using the test account
      - `metadata` object: any useful information you'd like to store alongside this payment
      - `payment_intent_id` string: unique id of associated payment intent
      - `checkout_id` string: unique id of associated checkout
      - `payment_method` CardPaymentMethod
        - `card` Card
          - `id` string, uuid: unique card id
          - `acct_last_four` string: last 4 digits of the card number
          - `brand` string: card brand or bank name
          - `digital_wallet` 'apple_pay' | 'google_pay' | 'null', nullable: which digital wallet provider the card is tied to
          - `name` string, nullable: card or account holder name
          - `token` string: same value as unique card id; can be saved and used to process multiple payments with the same card
          - `month` string: expiration date month
          - `year` string: expiration date year
          - `metadata` object, nullable: any useful information you'd like to store alongside this card
          - `created_at` string, date-time
          - `updated_at` string, date-time
          - `address_line1_check` 'fail' | 'pass' | 'unavailable' | 'unchecked': Result of the address line 1 verification check. `pass` — matches the cardholder's address on file; `fail` — does not match; `unavailable` — verification could not be performed; `unchecked` — no address was provided for verification.
          - `address_postal_code_check` 'fail' | 'pass' | 'unavailable' | 'unchecked': Result of the postal code verification check. `pass` — matches the cardholder's postal code on file; `fail` — does not match; `unavailable` — verification could not be performed; `unchecked` — no postal code was provided for verification.
        - `customer_id` string, nullable: customer_id is a deprecated field. Please use our payment method groups instead.
        - `signature` string, nullable: signature that uniquely identifies a credit card or bank account across payment methods
        - `account_id` string, nullable: account id associated with payment method
      - `application_fee` ApplicationFee
        - `id` string, uuid: unique application fee id
        - `amount` number: application fee amount, in cents
        - `currency` 'usd' | 'cad'
        - `created_at` string, date-time
        - `updated_at` string, date-time
      - `application_fee_rate_id` string: unique id of application fee rate applied to this payment, if any
      - `fees` FeeResponse[]: Array of fee objects showing the fees charged on this payment with their remaining refundable amounts. Populated whether the fees were provided via the `fees` array in the payment request or calculated automatically (for example, from a Standard Fee Configuration, or the `processing_fee` on a CAD payment). **Note:** This array is empty in the Create Payment response. Fees are processed asynchronously — subscribe to payment webhook events (recommended) to receive the full fee objects (with `id`, `remaining_amount`, and `currency`), or poll with a subsequent Get Payment request. See [Enhanced Fee Management](https://docs.justifi.tech/api-spec#section/Enhanced-Fee-Management) for full documentation.
        - `id` string: Unique identifier for this fee. Present when fetching a payment.
        - `type` 'processing_fee' | 'platform_fee' | 'refund_processing_fee', required: The type of fee: - `processing_fee`: Fees related to payment processing costs - `platform_fee`: Fees for your platform's services - `refund_processing_fee`: A processing fee charged when a refund is processed. Currently applies to CAD payments only.
        - `amount` integer, required: Fee amount in cents
        - `currency` 'usd' | 'cad': Currency of the fee amount. Present when fetching a payment.
        - `remaining_amount` integer: Amount still available for refund in cents. Updates after each partial refund. Present when fetching a payment.
        - `source_configuration_id` string, nullable: The public ID of the Standard Fee Configuration used to calculate this fee. Null when the fee was explicitly provided in the payment request rather than auto-calculated.
        - `source_fee_type` string, nullable: The fee type from the Standard Fee Configuration that generated this fee (e.g., `processing_ecomm`, `amex_brand_ecomm`, `platform`). Null when the fee was explicitly provided in the payment request.
        - `refund_id` string, nullable: The public ID of the refund this fee is associated with. Populated for `refund_processing_fee` fees (currently CAD payments only); null for all other fees. Present when fetching a payment.
      - `refunded` boolean: whether or not this payment has any refunds
      - `status` 'pending' | 'authorized' | 'canceled' | 'succeeded' | 'failed' | 'partially_refunded' | 'fully_refunded' | 'disputed': status of the payment
      - `payment_mode` 'ecom' | 'ach' | 'card_present'
      - `terminal_id` string: id of terminal used to process the card payment, if any
      - `transaction_hold` object: present when the payment has been flagged for review and held from payouts
        - `id` string: unique transaction hold id
        - `financial_transaction_id` string, uuid: financial transaction id the transaction hold is associated to
      - `expedited` boolean, nullable: settlement priority of the payment, only applies to ACH payments
      - `created_at` string, date-time
      - `updated_at` string, date-time
    - object: the attributes for the object
      - `id` string: unique payment id
      - `account_id` string, uuid
      - `amount` number: payment amount in cents
      - `amount_disputed` number: sum of open or lost disputes for this payment, in cents
      - `amount_refunded` number: sum of refunds for this payment, in cents
      - `amount_refundable` number: amount of this payment currently able to be refunded, in cents
      - `amount_returned` number: amount of this payment reversed by an ACH return, in cents. See [ACH Returns](https://docs.justifi.tech/paymentMethods/achReturns)
      - `balance` number: Sum of debits and credits for this payment, in cents (reflects the amount this account has earned from this payment). Compiled and calculated value, eventually consistent. To see all changes affecting the payment's balance see [Get Payment Balance Transactions](#operation/GetPaymentBalanceTransactions). When an ACH payment is returned, the payment amount and its original fees are both reversed, so any remaining negative `balance` is the ACH return fee.
      - `fee_amount` number: Sum of fees for this payment. Payments using an application fee include the ACH return fee here once the payment is returned; payments using [Enhanced Fee Management](https://docs.justifi.tech/api-spec#section/Enhanced-Fee-Management) do not. Either way the return fee is recorded as a balance transaction. See [ACH Returns](https://docs.justifi.tech/paymentMethods/achReturns).
      - `financial_transaction_id` string: associated financial transaction id
      - `captured` boolean: whether or not this payment is captured
      - `capture_strategy` 'automatic' | 'manual'
      - `currency` 'usd'
      - `description` string: your meaningful description of the payment (e.g. an order number or other value from your system)
      - `disputed` boolean: whether or not this payment has any open or lost disputes
      - `disputes` unknown[]: list of associated disputes
        - unknown
      - `error_code` string: error code if the payment fails
      - `error_description` string: text description of the error code
      - `is_test` boolean: whether or not this payment was made using the test account
      - `metadata` object: any useful information you'd like to store alongside this payment
      - `payment_intent_id` string: unique id of associated payment intent
      - `checkout_id` string: unique id of associated checkout
      - `payment_method` BankAccountPaymentMethod
        - `bank_account` BankAccount
          - `id` string, uuid: unique bank account payment method id
          - `account_owner_name` string: account owner name
          - `account_type` string: type of account (checking, savings, etc.)
          - `bank_name` string, nullable: bank name
          - `acct_last_four` string: last 4 digits of the account number
          - `token` string: same value as unique bank account id; can be saved and used to process multiple payments with the same bank account
          - `metadata` object, nullable: any useful information you'd like to store alongside this bank account
        - `customer_id` string, nullable: customer_id is a deprecated field. Please use our payment method groups instead.
        - `signature` string, nullable: signature that uniquely identifies a credit card or bank account across payment methods
        - `account_id` string, nullable: account id associated with payment method
      - `application_fee` ApplicationFee
        - `id` string, uuid: unique application fee id
        - `amount` number: application fee amount, in cents
        - `currency` 'usd' | 'cad'
        - `created_at` string, date-time
        - `updated_at` string, date-time
      - `application_fee_rate_id` string: unique id of application fee rate applied to this payment, if any
      - `fees` FeeResponse[]: Array of fee objects showing the fees charged on this payment with their remaining refundable amounts. Populated whether the fees were provided via the `fees` array in the payment request or calculated automatically (for example, from a Standard Fee Configuration). **Note:** This array is empty in the Create Payment response. Fees are processed asynchronously — subscribe to payment webhook events (recommended) to receive the full fee objects (with `id`, `remaining_amount`, and `currency`), or poll with a subsequent Get Payment request. See [Enhanced Fee Management](https://docs.justifi.tech/api-spec#section/Enhanced-Fee-Management) for full documentation.
        - `id` string: Unique identifier for this fee. Present when fetching a payment.
        - `type` 'processing_fee' | 'platform_fee' | 'refund_processing_fee', required: The type of fee: - `processing_fee`: Fees related to payment processing costs - `platform_fee`: Fees for your platform's services - `refund_processing_fee`: A processing fee charged when a refund is processed. Currently applies to CAD payments only.
        - `amount` integer, required: Fee amount in cents
        - `currency` 'usd' | 'cad': Currency of the fee amount. Present when fetching a payment.
        - `remaining_amount` integer: Amount still available for refund in cents. Updates after each partial refund. Present when fetching a payment.
        - `source_configuration_id` string, nullable: The public ID of the Standard Fee Configuration used to calculate this fee. Null when the fee was explicitly provided in the payment request rather than auto-calculated.
        - `source_fee_type` string, nullable: The fee type from the Standard Fee Configuration that generated this fee (e.g., `processing_ecomm`, `amex_brand_ecomm`, `platform`). Null when the fee was explicitly provided in the payment request.
        - `refund_id` string, nullable: The public ID of the refund this fee is associated with. Populated for `refund_processing_fee` fees (currently CAD payments only); null for all other fees. Present when fetching a payment.
      - `refunded` boolean: whether or not this payment has any refunds
      - `returned` boolean: whether or not this payment was reversed by an ACH return
      - `status` 'pending' | 'authorized' | 'canceled' | 'succeeded' | 'failed' | 'partially_refunded' | 'fully_refunded' | 'disputed': status of the payment
      - `payment_mode` 'ecom' | 'ach' | 'card_present'
      - `terminal_id` string: id of terminal used to process a card payment, null for bank account payments
      - `transaction_hold` object: present when the payment has been flagged for review and held from payouts
        - `id` string: unique transaction hold id
        - `financial_transaction_id` string, uuid: financial transaction id the transaction hold is associated to
      - `expedited` boolean, nullable: settlement priority of the payment, only applies to ACH payments
      - `created_at` string, date-time
      - `updated_at` string, date-time
  - `page_info` unknown

## Other responses

- `400`: Full card number submitted without PCI approval
- `402`: Error when processing the payment

---

[API](https://skmtc.dev/justifi/apis/justifi-api-documentation.md) - [All operations](https://skmtc.dev/justifi/apis/justifi-api-documentation/llms.txt) - [OpenAPI document](https://skmtc.dev/justifi/apis/justifi-api-documentation/revisions/dd9f3fed7e46?raw)
