API DOCUMENTATION

Confirm your assigned profile. Draft sections and verification limits are marked.

View open points →

PAYSTAR / DEVELOPER DOCUMENTATION

Deposits

Choose P2P, direct acquiring, hosted checkout or an approved tokenized payment.

[01]

One endpoint, distinct profiles

P2P and ECOM H2H can use the same host but are not the same contract. Select the flow assigned to your pipeline; a hostname alone does not choose the correct request schema.

POSThttps://secure.paystar.uk/api/v1/integration/deposit-order/

Separate hosted-card and tokenized profiles use init.paystar.uk and token.paystar.uk respectively. Follow the host assigned to your integration.

Files in Downloads: OpenAPI JSON · YAML · Postman collection · Postman environment.

Reference files: Additional fields · Currencies · Errors and handling caveats.

The shared Postman collection includes P2P, hosted H2C and tokenized deposit templates, plus a separately named ECOM H2H entry on the same secure deposit endpoint. The ECOM H2H/H2C owner templates show sanitized request bodies and use separate credentials. They are examples, not complete profile contracts or runnable card fixtures.

Shared request fields
FieldPresenceType & meaning
amountRequirednumber
currencyRequiredstring

Currency key as a string, with no lexical length or pattern validation. Values such as USDT_TRC20 can be submitted; this does not guarantee that a value is known or enabled. For payment creation, PayStar first looks up the exact submitted value in its internal currency dictionary, then searches for a route matching the pipeline conditions. Use the currency key provided for your integration. Fiat commonly uses ISO 4217 alpha-3 codes; crypto may use an asset/network key. Requiredness and operation-specific business errors remain unchanged.

CurrencyCode

externalTransactionIdRequiredstring

Unique merchant-generated identifier used for status lookup and safe retry resolution.

minLength: 1

ExternalTransactionId

callbackUrlOptionalstring · uri

Optional callback URL.

processingRedirectUrlOptionalstring · uri
failedRedirectUrlOptionalstring · uri
successRedirectUrlOptionalstring · uri
additionalFieldsTerminal-specificarray of object

Array of objects with key and value. The required field set depends on the individual configuration of each terminal (pipeline). Ask your integration manager for the current required fields before sending a request. A catalog entry is not automatically required or supported for every terminal.

HTTP outcomes for createDeposit
HTTPMeaning
200Deposit order created. Inspect orderStatus: HTTP 200 can include a Failed processing outcome and does not mean payment success.
400Request validation failed, a configured limit was reached, or the merchant order ID already exists. These common examples use owner-confirmed HTTP 400. Deposit H2H/H2C unknown currency remains the separate HTTP 423 response under CUR-002.

BusinessError & handling

401Missing or invalid deposit Bearer token.
403The key is valid but cannot use this deposit capability.
415Unsupported media type. Framework-level error raised before PayStar business processing.
423Business error: Deposit H2H/H2C unknown currency retains statusDescrption 2-00100-2, code 1.2.4.9 and the owner-approved message Currency value "{currencyKey}" is unknown. The distinct common routing error uses HTTP 423, statusDescrption 0000-2 and code 1.2.4.3, confirmed in CREATE-HTTP-001. See x-paystar-create-payload-examples and x-paystar-deposit-currency-errors.

BusinessError & handling

500Internal server error.

BusinessError & handling

[02]

P2P deposit · H2H/H2C

Owner-approved fieldsSandbox recorded · 7 Sep 2026

When the gateway integration uses H2H, the same P2P create request returns both payment instructions and a PayStar payment-form URL. The merchant can display the instructions in its own checkout (H2H) or send the customer to the returned PayStar form (H2C), without creating another order or changing the request.

Keep the same assigned secure.paystar.uk endpoint. This merchant-side choice is distinct from the hosted-card H2C profile below. All three redirect URLs are required; callbackUrl remains optional.

Request fields & cURL

In Downloads, open the shared Postman collection and select Create P2P Deposit. Use the profile-specific environment.

FieldPresenceType & meaning
amountRequirednumber
currencyRequiredstring

Currency key as a string, with no lexical length or pattern validation. Values such as USDT_TRC20 can be submitted; this does not guarantee that a value is known or enabled. For payment creation, PayStar first looks up the exact submitted value in its internal currency dictionary, then searches for a route matching the pipeline conditions. Use the currency key provided for your integration. Fiat commonly uses ISO 4217 alpha-3 codes; crypto may use an asset/network key. Requiredness and operation-specific business errors remain unchanged.

CurrencyCode

externalTransactionIdRequiredstring

Unique merchant-generated identifier used for status lookup and safe retry resolution.

minLength: 1

ExternalTransactionId

callbackUrlOptionalstring · uri

Optional callback URL.

processingRedirectUrlRequiredstring · uri
failedRedirectUrlRequiredstring · uri
successRedirectUrlRequiredstring · uri
additionalFieldsTerminal-specificarray of object

Array of objects with key and value. The required field set depends on the individual configuration of each terminal (pipeline). Ask your integration manager for the current required fields before sending a request. A catalog entry is not automatically required or supported for every terminal.

additionalFields is an array of objects. Each object contains key (the field name) and value (its value). Use the type specified for that field: string, number or boolean; null is not a valid item value.

The example includes payeerIdentifier, your payer/customer ID. It is commonly required, but it is not mandatory for every terminal and may not be the only field you need. New examples use lowerCamelCase.

Array structure: key and value
FieldPresenceType & meaning
keyRequiredstring

Canonical documented casing is lowerCamelCase.

minLength: 1

valueRequiredstring | number | boolean

Flow-specific scalar. Presence and non-null value are normative; formats and ranges belong to the selected flow schema.

AdditionalFieldValue

JSON · illustrative field arraySelect text to copy
{
  "additionalFields": [
    {
      "key": "payeerIdentifier",
      "value": "Merch-Customer-12345"
    }
  ]
}

Browse the additional fields catalog →

cURLSelect text to copy
curl --request POST \
  --url 'https://secure.paystar.uk/api/v1/integration/deposit-order/' \
  --header 'Authorization: Bearer <PAYSTAR_P2P_TOKEN>' \
  --header 'Content-Type: application/json' \
  --data '{
  "amount": 100.00,
  "currency": "RUB",
  "externalTransactionId": "UNIQUE_MERCHANT_ID",
  "callbackUrl": "https://merchant.example/paystar/callback",
  "processingRedirectUrl": "https://merchant.example/payment/processing",
  "failedRedirectUrl": "https://merchant.example/payment/failed",
  "successRedirectUrl": "https://merchant.example/payment/success",
  "additionalFields": [
    {
      "key": "payeerIdentifier",
      "value": "Merch-Customer-12345"
    }
  ]
}'
Accepted response & next step
FieldPresenceType & meaning
externalIdRequiredstring
orderStatusRequiredstring · Processing
paymentDetailsRequiredobject

Payment instructions and the PayStar form URL returned together for P2P with an H2H gateway integration (P2P-FORM-001, owner-confirmed 2026-09-10).

P2PPaymentDetails

JSONSelect text to copy
{
  "externalId": "<PAYSTAR_ORDER_ID>",
  "orderStatus": "Processing",
  "paymentDetails": {
    "card": "<REDACTED_PAYMENT_DETAIL>",
    "fio": "<RECIPIENT_NAME>",
    "bank": "<BANK_NAME>",
    "formUrl": "https://p2p.paystar.uk/?EXAMPLE_ONLY"
  }
}

Display the returned payment instructions in your own checkout, or open the returned paymentDetails.formUrl for the customer. A valid accepted P2P response includes this non-null URL. The example query is illustrative; use the complete URL returned by the API and protect its one-time parameters. Store both IDs and follow the same order status.

Payment details fields

Map payment instructions by their exact response field, not by the input additionalFields key or the shape of the value. Field names are case-sensitive.

Payment instructionResponse pathMapping notes
CardpaymentDetails.cardExisting card mapping; alternative details are not all placed in card.
IBANpaymentDetails.ibanString in the owner example.
Account numberpaymentDetails.accountNumberNot paymentDetails.bankAccount. Preserve the string and its leading zeroes.
QRpaymentDetails.qrUrlOwner describes Base64 content. Do not assume an HTTP URL from the name. Can accompany accountNumber.
Method labelpaymentDetails.methodExample: ArsCbu. Not an exhaustive enum or a unique discriminator.
PhoneNumberpaymentDetails.numberString in the owner example, despite the name number. Preserve the plus sign; do not use phoneNumber or infer a numeric type.
Phone number response example
JSONSelect text to copy
{
  "externalId": "<PAYSTAR_ORDER_ID>",
  "orderStatus": "Processing",
  "paymentDetails": {
    "fio": "<RECIPIENT_NAME>",
    "bank": "<BANK_NAME>",
    "number": "<RECIPIENT_PHONE_NUMBER>",
    "formUrl": "https://checkout.example/EXAMPLE_ONLY"
  }
}
IBAN response example
JSONSelect text to copy
{
  "externalId": "<PAYSTAR_ORDER_ID>",
  "orderStatus": "Processing",
  "paymentDetails": {
    "fio": "<RECIPIENT_NAME>",
    "iban": "<IBAN>",
    "formUrl": "https://checkout.example/EXAMPLE_ONLY"
  }
}
Account number response example
JSONSelect text to copy
{
  "externalId": "<PAYSTAR_ORDER_ID>",
  "orderStatus": "Processing",
  "paymentDetails": {
    "fio": "<RECIPIENT_NAME>",
    "method": "ArsCbu",
    "formUrl": "https://checkout.example/EXAMPLE_ONLY",
    "accountNumber": "<ACCOUNT_NUMBER>"
  }
}
QR and account number response example
JSONSelect text to copy
{
  "externalId": "<PAYSTAR_ORDER_ID>",
  "orderStatus": "Processing",
  "paymentDetails": {
    "qrUrl": "<BASE64_QR_DATA>",
    "fio": "<RECIPIENT_NAME>",
    "method": "ArsCbu",
    "formUrl": "https://checkout.example/EXAMPLE_ONLY",
    "accountNumber": "<ACCOUNT_NUMBER>"
  }
}
Field reference
FieldPresenceType & meaning
cardOptionalstring | null

Sensitive payment detail; redact in stored evidence.

fioOptionalstring | null
bankOptionalstring | null
formUrlRequiredstring · uri

Required non-null PayStar payment-form URI in a valid accepted P2P response. The merchant may use this H2C presentation instead of displaying the returned payment instructions itself. Use the full returned URL, not this illustrative EXAMPLE_ONLY query. Never log one-time query tokens.

numberProfile-specific · rules pendingstring in owner examples · constraints pending

Recipient phone payment instruction at paymentDetails.number, not phoneNumber or card. It is a string in the owner example; preserve the plus sign and value as returned. No numeric conversion, E.164, length, requiredness or nullability rule is inferred.

ibanProfile-specific · rules pendingstring in owner examples · constraints pending

IBAN payment instruction at paymentDetails.iban. Keep it as a string. Confirmed by the owner example, not a universal required field.

accountNumberProfile-specific · rules pendingstring in owner examples · constraints pending

Account-number payment instruction at paymentDetails.accountNumber, not bankAccount. Keep the string exactly as returned, including leading zeroes. It can coexist with qrUrl, as in the owner example.

qrUrlProfile-specific · rules pendingstring in owner examples · constraints pending

QR content at paymentDetails.qrUrl. The owner labels this value Base64; despite the field name, it is not confirmed to be an HTTP URL. Actual QR bytes, MIME type and raw-Base64 versus data-URI envelope remain unconfirmed.

methodProfile-specific · rules pendingstring in owner examples · constraints pending

Method label at paymentDetails.method. ArsCbu is an owner-provided example, not a complete enum or a unique response-variant discriminator.

Check deposit status →

Unsuccessful responseCommon JSON payloads

These are common examples for this flow, not an exhaustive list of API errors; profile-specific requirements still apply. HTTP codes are owner-confirmed for these examples. Responses without a body do not have a JSON example here.

HTTP 200 · Order created, processing failedOrder created

The request produced an order, but processing failed. Keep the PayStar externalId and your original merchant order ID. This is not a rejection without an order.

HTTP: 200

JSON · HTTP 200 response bodySelect text to copy
{
  "externalId": "aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa",
  "orderStatus": "Failed"
}

HTTP 200 means the order was created, not that the payment succeeded. This body uses orderStatus, not status, and does not include payment details or a form URL. Inspect orderStatus and retain both order identifiers.

HTTP 423 · No matching channel or routeNo new order

The currency, amount, or other request parameters do not match available routing conditions for this pipeline. No order is created.

HTTP: 423

JSON · HTTP 423 response bodySelect text to copy
{
  "label": "TEMPORARY_ERROR",
  "message": "TEMPORARY_ERROR",
  "statusDescrption": "0000-2",
  "externalTransactionId": null,
  "code": "1.2.4.3"
}
HTTP 400 · Configured limit reachedNo new order

A configured limit was reached. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "LIMITS_ERROR",
  "message": "Limit id: aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa was reached",
  "statusDescrption": "0001-0",
  "externalTransactionId": null
}

The limit ID is illustrative. This example has no code field; do not map the error by a particular UUID or exact message text.

HTTP 400 · Duplicate merchant order IDNo new order

An order with this merchant ID already exists. No new order is created by this rejected attempt.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "Order with this external_transaction_id already exist",
  "statusDescrption": "1-4007",
  "externalTransactionId": null,
  "code": "1.1.5.1"
}

Query the existing order using the original externalTransactionId from your request, even when externalTransactionId is null in this error. Do not replace the ID for a blind retry.

HTTP 400 · Required parameter missingNo new order

A field required by the configured terminal is missing. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "additionalField BankAccount not found in request data. Description: Beneficiary’s bank account number, e.g. 1234567890",
  "statusDescrption": "0000-0",
  "externalTransactionId": null,
  "code": "1.2.4.8"
}

BankAccount is an example of a configured requirement, not a mandatory field for every flow. Use the required-field list supplied for your terminal.

Unknown currency → · HTTP and transport responses → · Download error catalog and payload examples · JSON ↓

[03]

Card acquiring · ECOM H2H

Owner-provided request / responseFull profile contract still to confirm

Direct card collection requires an approved integration and compliance boundary. The owner example below shows the card fields inside additionalFields; it is not the P2P request schema.

POSThttps://secure.paystar.uk/api/v1/integration/deposit-order

P2P and ECOM H2H share POST https://secure.paystar.uk/api/v1/integration/deposit-order/. They are distinct flow/profile variants: use the credentials, request body and response handling assigned to the selected profile. The P2P example is not an ECOM request template. The owner H2H example omits the final slash; this update does not verify redirect or alias behavior.

In Downloads, open the shared Postman collection and select Create ECOM H2H Deposit — owner-provided template. Use the profile-specific environment.

ECOM H2H — owner request and responseOwner-provided · 10 Sep 2026

Postman request: Create ECOM H2H Deposit — owner-provided template. Exact additionalFields key spelling from the owner example is retained; it does not change the general lowerCamelCase compatibility guidance.

cURL · sanitized owner exampleSelect text to copy
curl --request POST \
  --url 'https://secure.paystar.uk/api/v1/integration/deposit-order' \
  --header 'Authorization: Bearer <PAYSTAR_ECOM_H2H_TOKEN>' \
  --header 'Content-Type: application/json; charset=utf-8' \
  --data '{
  "amount": 20.00,
  "currency": "AZN",
  "externalTransactionId": "UNIQUE_MERCHANT_ID",
  "failedRedirectUrl": "https://merchant.example/failed",
  "processingRedirectUrl": "https://merchant.example/processing",
  "successRedirectUrl": "https://merchant.example/success",
  "callbackUrl": "https://merchant.example/callback",
  "additionalFields": [
    {
      "key": "PayeerIdentifier",
      "value": "MERCHANT_CUSTOMER_ID"
    },
    {
      "key": "CardNumber",
      "value": "<APPROVED_CARD_NUMBER>"
    },
    {
      "key": "CardExpireYear",
      "value": "30"
    },
    {
      "key": "CardExpireMonth",
      "value": "06"
    },
    {
      "key": "CardCvv",
      "value": "<APPROVED_CARD_CVV>"
    },
    {
      "key": "CardHolder",
      "value": "<CARDHOLDER_NAME>"
    }
  ]
}'
JSON · owner response body; HTTP not suppliedSelect text to copy
{
  "externalId": "aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa",
  "orderStatus": "Processing",
  "paymentDetails": {
    "formUrl": "https://redirect.example/EXAMPLE_ONLY",
    "flowData": {
      "action": "https://gateway.example/redirect?token=EXAMPLE_ONLY",
      "method": "GET",
      "params": [
        {
          "name": "token",
          "value": "EXAMPLE_ONLY"
        }
      ],
      "metadata": {
        "description": "Redirect the user to complete payment",
        "type": "redirect"
      },
      "instruction": {
        "type": "query"
      }
    }
  }
}
Response pathMeaning / boundary
paymentDetails.formUrlPayment/redirect link returned by PayStar.
paymentDetails.flowData.actionGateway action URL; may already contain query parameters.
paymentDetails.flowData.methodGET in this example; not a closed method enum.
paymentDetails.flowData.paramsName/value parameters; this example uses token.
paymentDetails.flowData.metadatadescription and type explain the action in this example.
paymentDetails.flowData.instruction.typequery in this example; other instruction variants are not established.

The example repeats the token in action and params. URL assembly, redirect precedence and other flowData variants still require confirmation; do not infer that the token should be appended twice.

The example supplies fields and values, not a complete required-field list, response schema or HTTP mapping. No request or redirect was executed in this documentation update.

The collection uses {{merchantOrderId}} directly as externalTransactionId. For status lookup, retain that ID and supply depositStatusToken authorized for the same order. The old ecomRequestBody environment variable remains empty for import compatibility and is no longer used by this template.

Profile contract still to confirm

The example does not establish universal required fields, card/expiration validation rules, HTTP status, all response variants or precedence between formUrl and flowData. Confirm these for the assigned profile. Card/token/redirect values in this guide are placeholders; do not send them or store real PAN/CVV and one-time tokens in collections or exports.

ECOM contract and sandbox open points →

ECOM open points in Downloads → — owner examples are available, but no complete normative ECOM schema or runnable card fixture is included.

Unsuccessful responseCommon JSON payloads

These are common examples for this flow, not an exhaustive list of API errors; profile-specific requirements still apply. HTTP codes are owner-confirmed for these examples. Responses without a body do not have a JSON example here.

HTTP 200 · Order created, processing failedOrder created

The request produced an order, but processing failed. Keep the PayStar externalId and your original merchant order ID. This is not a rejection without an order.

HTTP: 200

JSON · HTTP 200 response bodySelect text to copy
{
  "externalId": "aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa",
  "orderStatus": "Failed"
}

HTTP 200 means the order was created, not that the payment succeeded. This body uses orderStatus, not status, and does not include payment details or a form URL. Inspect orderStatus and retain both order identifiers.

HTTP 423 · No matching channel or routeNo new order

The currency, amount, or other request parameters do not match available routing conditions for this pipeline. No order is created.

HTTP: 423

JSON · HTTP 423 response bodySelect text to copy
{
  "label": "TEMPORARY_ERROR",
  "message": "TEMPORARY_ERROR",
  "statusDescrption": "0000-2",
  "externalTransactionId": null,
  "code": "1.2.4.3"
}
HTTP 400 · Configured limit reachedNo new order

A configured limit was reached. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "LIMITS_ERROR",
  "message": "Limit id: aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa was reached",
  "statusDescrption": "0001-0",
  "externalTransactionId": null
}

The limit ID is illustrative. This example has no code field; do not map the error by a particular UUID or exact message text.

HTTP 400 · Duplicate merchant order IDNo new order

An order with this merchant ID already exists. No new order is created by this rejected attempt.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "Order with this external_transaction_id already exist",
  "statusDescrption": "1-4007",
  "externalTransactionId": null,
  "code": "1.1.5.1"
}

Query the existing order using the original externalTransactionId from your request, even when externalTransactionId is null in this error. Do not replace the ID for a blind retry.

HTTP 400 · Required parameter missingNo new order

A field required by the configured terminal is missing. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "additionalField BankAccount not found in request data. Description: Beneficiary’s bank account number, e.g. 1234567890",
  "statusDescrption": "0000-0",
  "externalTransactionId": null,
  "code": "1.2.4.8"
}

BankAccount is an example of a configured requirement, not a mandatory field for every flow. Use the required-field list supplied for your terminal.

Unknown currency → · HTTP and transport responses → · Download error catalog and payload examples · JSON ↓

[04]

Hosted checkout · H2C

Documented flowHappy-path verification pending

Card entry takes place on the hosted form, not on the merchant page. This can reduce PCI DSS scope; the actual compliance boundary must be confirmed for the integration.

POSThttps://init.paystar.uk/api/v1/integration/deposit-order/
ECOM H2C — owner request and responseOwner-provided · 10 Sep 2026

Postman request: Create ECOM H2C Deposit — owner-provided template. Exact additionalFields key spelling from the owner example is retained; it does not change the general lowerCamelCase compatibility guidance.

cURL · sanitized owner exampleSelect text to copy
curl --request POST \
  --url 'https://init.paystar.uk/api/v1/integration/deposit-order/' \
  --header 'Authorization: Bearer <PAYSTAR_ECOM_H2C_TOKEN>' \
  --header 'Content-Type: application/json; charset=utf-8' \
  --data '{
  "amount": 50.00,
  "currency": "AZN",
  "externalTransactionId": "UNIQUE_MERCHANT_ID",
  "failedRedirectUrl": "https://merchant.example/failed",
  "processingRedirectUrl": "https://merchant.example/processing",
  "successRedirectUrl": "https://merchant.example/success",
  "callbackUrl": "https://merchant.example/callback",
  "additionalFields": [
    {
      "key": "PayeerIdentifier",
      "value": "MERCHANT_CUSTOMER_ID"
    }
  ]
}'
JSON · owner response body; HTTP not suppliedSelect text to copy
{
  "externalId": "bbbbbbbb-bbbb-4bbb-8bbb-bbbbbbbbbbbb",
  "orderStatus": "Init",
  "formUrl": "https://checkout.example/EXAMPLE_ONLY"
}
Response pathMeaning / boundary
formUrlRoot-level hosted-checkout URL; not paymentDetails.formUrl.
orderStatusInit in this owner example.

This owner sample uses PayeerIdentifier. Another previously tested hosted profile required FirstName; additionalFields requirements remain terminal-specific.

The example supplies fields and values, not a complete required-field list, response schema or HTTP mapping. No request or redirect was executed in this documentation update.

Other hosted profile — illustrative firstName request

In Downloads, open the shared Postman collection and select Create Hosted H2C Deposit — illustrative configured firstName. Use the profile-specific environment.

FieldPresenceType & meaning
amountRequirednumber
currencyRequiredstring

Currency key as a string, with no lexical length or pattern validation. Values such as USDT_TRC20 can be submitted; this does not guarantee that a value is known or enabled. For payment creation, PayStar first looks up the exact submitted value in its internal currency dictionary, then searches for a route matching the pipeline conditions. Use the currency key provided for your integration. Fiat commonly uses ISO 4217 alpha-3 codes; crypto may use an asset/network key. Requiredness and operation-specific business errors remain unchanged.

CurrencyCode

externalTransactionIdRequiredstring

Unique merchant-generated identifier used for status lookup and safe retry resolution.

minLength: 1

ExternalTransactionId

callbackUrlOptionalstring · uri

Optional callback URL.

processingRedirectUrlOptionalstring · uri
failedRedirectUrlOptionalstring · uri
successRedirectUrlOptionalstring · uri
additionalFieldsOptionalarray of object

Array of objects with key and value. The required field set depends on the individual configuration of each terminal (pipeline). Ask your integration manager for the current required fields before sending a request. A catalog entry is not automatically required or supported for every terminal.

cURLSelect text to copy
curl --request POST \
  --url 'https://init.paystar.uk/api/v1/integration/deposit-order/' \
  --header 'Authorization: Bearer <PAYSTAR_H2C_TOKEN>' \
  --header 'Content-Type: application/json' \
  --data '{
  "amount": 100.00,
  "currency": "USD",
  "externalTransactionId": "UNIQUE_MERCHANT_ID",
  "additionalFields": [
    {
      "key": "firstName",
      "value": "Example"
    }
  ]
}'
Documented response & customer handoff
FieldPresenceType & meaning
externalIdRequiredstring
orderStatusRequiredstring · Init
formUrlRequiredstring · uri
JSONSelect text to copy
{
  "externalId": "<PAYSTAR_ORDER_ID>",
  "orderStatus": "Init",
  "formUrl": "https://checkout.example/REPLACE_WITH_RETURNED_URL"
}

Open the returned URL for the customer, protect one-time parameters and monitor status. The example is a schema illustration, not a live H2C response.

Unsuccessful responseCommon JSON payloads

These are common examples for this flow, not an exhaustive list of API errors; profile-specific requirements still apply. HTTP codes are owner-confirmed for these examples. Responses without a body do not have a JSON example here.

HTTP 200 · Order created, processing failedOrder created

The request produced an order, but processing failed. Keep the PayStar externalId and your original merchant order ID. This is not a rejection without an order.

HTTP: 200

JSON · HTTP 200 response bodySelect text to copy
{
  "externalId": "aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa",
  "orderStatus": "Failed"
}

HTTP 200 means the order was created, not that the payment succeeded. This body uses orderStatus, not status, and does not include payment details or a form URL. Inspect orderStatus and retain both order identifiers.

HTTP 423 · No matching channel or routeNo new order

The currency, amount, or other request parameters do not match available routing conditions for this pipeline. No order is created.

HTTP: 423

JSON · HTTP 423 response bodySelect text to copy
{
  "label": "TEMPORARY_ERROR",
  "message": "TEMPORARY_ERROR",
  "statusDescrption": "0000-2",
  "externalTransactionId": null,
  "code": "1.2.4.3"
}
HTTP 400 · Configured limit reachedNo new order

A configured limit was reached. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "LIMITS_ERROR",
  "message": "Limit id: aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa was reached",
  "statusDescrption": "0001-0",
  "externalTransactionId": null
}

The limit ID is illustrative. This example has no code field; do not map the error by a particular UUID or exact message text.

HTTP 400 · Duplicate merchant order IDNo new order

An order with this merchant ID already exists. No new order is created by this rejected attempt.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "Order with this external_transaction_id already exist",
  "statusDescrption": "1-4007",
  "externalTransactionId": null,
  "code": "1.1.5.1"
}

Query the existing order using the original externalTransactionId from your request, even when externalTransactionId is null in this error. Do not replace the ID for a blind retry.

HTTP 400 · Required parameter missingNo new order

A field required by the configured terminal is missing. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "additionalField BankAccount not found in request data. Description: Beneficiary’s bank account number, e.g. 1234567890",
  "statusDescrption": "0000-0",
  "externalTransactionId": null,
  "code": "1.2.4.8"
}

BankAccount is an example of a configured requirement, not a mandatory field for every flow. Use the required-field list supplied for your terminal.

Unknown currency → · HTTP and transport responses → · Download error catalog and payload examples · JSON ↓

[05]

Tokenized deposit

Documented flowLive onboarding pending

Use a PayStar cardStorageToken assigned to an approved tokenized profile. A bank cardToken is not interchangeable with it.

POSThttps://token.paystar.uk/api/v1/integration/deposit-order/
First payment → stored token → next payment
  1. Complete an eligible first payment in the assigned flow.
  2. Obtain the PayStar cardStorageToken through approved status/callback data when the profile supports it.
  3. Store it securely against the correct customer.
  4. Supply the token for the subsequent payment and handle any required customer action.

Token lifetime, reuse conditions and the customer step require profile confirmation. Tokenization does not promise a fully unattended payment or no PCI obligations.

Request fields & cURL

In Downloads, open the shared Postman collection and select Create Tokenized Deposit — onboarding pending. Use the profile-specific environment.

FieldPresenceType & meaning
amountRequirednumber
currencyRequiredstring

Currency key as a string, with no lexical length or pattern validation. Values such as USDT_TRC20 can be submitted; this does not guarantee that a value is known or enabled. For payment creation, PayStar first looks up the exact submitted value in its internal currency dictionary, then searches for a route matching the pipeline conditions. Use the currency key provided for your integration. Fiat commonly uses ISO 4217 alpha-3 codes; crypto may use an asset/network key. Requiredness and operation-specific business errors remain unchanged.

CurrencyCode

externalTransactionIdRequiredstring

Unique merchant-generated identifier used for status lookup and safe retry resolution.

minLength: 1

ExternalTransactionId

callbackUrlOptionalstring · uri

Optional callback URL.

processingRedirectUrlOptionalstring · uri
failedRedirectUrlOptionalstring · uri
successRedirectUrlOptionalstring · uri
additionalFieldsRequiredarray of object
cURLSelect text to copy
curl --request POST \
  --url 'https://token.paystar.uk/api/v1/integration/deposit-order/' \
  --header 'Authorization: Bearer <PAYSTAR_TOKENIZED_TOKEN>' \
  --header 'Content-Type: application/json' \
  --data '{
  "amount": 100.00,
  "currency": "USD",
  "externalTransactionId": "UNIQUE_MERCHANT_ID",
  "additionalFields": [
    {
      "key": "cardStorageToken",
      "value": "<APPROVED_STORED_TOKEN>"
    }
  ]
}'
Documented response
FieldPresenceType & meaning
externalIdRequiredstring
orderStatusRequiredstring · Processing
paymentDetailsOptionalobject
JSONSelect text to copy
{
  "externalId": "<PAYSTAR_ORDER_ID>",
  "orderStatus": "Processing",
  "paymentDetails": {
    "formUrl": "https://checkout.example/REPLACE_WITH_RETURNED_URL"
  }
}

Use the assigned status route to observe the outcome →

Unsuccessful responseCommon JSON payloads

These are common examples for this flow, not an exhaustive list of API errors; profile-specific requirements still apply. HTTP codes are owner-confirmed for these examples. Responses without a body do not have a JSON example here.

HTTP 200 · Order created, processing failedOrder created

The request produced an order, but processing failed. Keep the PayStar externalId and your original merchant order ID. This is not a rejection without an order.

HTTP: 200

JSON · HTTP 200 response bodySelect text to copy
{
  "externalId": "aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa",
  "orderStatus": "Failed"
}

HTTP 200 means the order was created, not that the payment succeeded. This body uses orderStatus, not status, and does not include payment details or a form URL. Inspect orderStatus and retain both order identifiers.

HTTP 423 · No matching channel or routeNo new order

The currency, amount, or other request parameters do not match available routing conditions for this pipeline. No order is created.

HTTP: 423

JSON · HTTP 423 response bodySelect text to copy
{
  "label": "TEMPORARY_ERROR",
  "message": "TEMPORARY_ERROR",
  "statusDescrption": "0000-2",
  "externalTransactionId": null,
  "code": "1.2.4.3"
}
HTTP 400 · Configured limit reachedNo new order

A configured limit was reached. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "LIMITS_ERROR",
  "message": "Limit id: aaaaaaaa-aaaa-4aaa-8aaa-aaaaaaaaaaaa was reached",
  "statusDescrption": "0001-0",
  "externalTransactionId": null
}

The limit ID is illustrative. This example has no code field; do not map the error by a particular UUID or exact message text.

HTTP 400 · Duplicate merchant order IDNo new order

An order with this merchant ID already exists. No new order is created by this rejected attempt.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "Order with this external_transaction_id already exist",
  "statusDescrption": "1-4007",
  "externalTransactionId": null,
  "code": "1.1.5.1"
}

Query the existing order using the original externalTransactionId from your request, even when externalTransactionId is null in this error. Do not replace the ID for a blind retry.

HTTP 400 · Required parameter missingNo new order

A field required by the configured terminal is missing. No order is created.

HTTP: 400

JSON · HTTP 400 response bodySelect text to copy
{
  "label": "VALIDATION_ERROR",
  "message": "additionalField BankAccount not found in request data. Description: Beneficiary’s bank account number, e.g. 1234567890",
  "statusDescrption": "0000-0",
  "externalTransactionId": null,
  "code": "1.2.4.8"
}

BankAccount is an example of a configured requirement, not a mandatory field for every flow. Use the required-field list supplied for your terminal.

Unknown currency → · HTTP and transport responses → · Download error catalog and payload examples · JSON ↓

[06]

Follow the deposit outcome

Keep your original merchant externalTransactionId and the PayStar externalId returned when the order is created. Use the corresponding lookup:

Deposit status by merchant ID →
Deposit status by PayStar ID →

Use the credentials and status host assigned to your deposit profile. Confirm hosted H2C and tokenized profile support during onboarding.

Polling and recovery after an uncertain create →

Files in Downloads: Order statuses · Payment history.

Need the required fields, currencies or limits for your pipeline?

Confirm your profile with Yegor ↗