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

# Prices API — List, Create, Retrieve, Update, Archive

> Define one-time or recurring prices for products in your catalog. All amounts are integers in minor currency units (e.g. 5000 = $50.00).

# Prices

A **price** defines how much to charge for a [product](/api-reference/products/overview) and how often. Every product can have multiple prices — for example a monthly plan and an annual plan for the same service, or regional prices in different currencies.

When a line item on an invoice references a price (`price_…`), the unit amount, currency, and tax rate are automatically borrowed from the price. You can still override the description, quantity, and discount at the line-item level.

**All monetary amounts are integers in minor currency units.** For USD, `5000` means \$50.00. For JPY (a zero-decimal currency), `5000` means ¥5000.

**Base URL:** `https://invoice.horizonpay.co/api/v1`

***

## The price object

```json theme={null}
{
  "id": "price_01hxyz1234567890abcdefghij",
  "object": "price",
  "product": "prod_01hxyz1234567890abcdefghij",
  "nickname": "Monthly Pro",
  "unit_amount": 4900,
  "currency": "USD",
  "billing_scheme": "per_unit",
  "type": "recurring",
  "recurring": {
    "interval": "month",
    "interval_count": 1
  },
  "tax_rate": 8.5,
  "active": true,
  "created": "2024-01-10T11:05:00.000Z"
}
```

<ResponseField name="id" type="string">
  Unique identifier for the price. Prefixed with `price_`.
</ResponseField>

<ResponseField name="object" type="string">
  String literal `"price"`.
</ResponseField>

<ResponseField name="product" type="string">
  The `prod_`-prefixed ID of the parent product.
</ResponseField>

<ResponseField name="nickname" type="string | null">
  Optional internal label for the price (e.g. `"Monthly Pro"`, `"Enterprise Annual"`). Not shown to customers.
</ResponseField>

<ResponseField name="unit_amount" type="integer">
  The unit price in minor currency units. `4900` USD = \$49.00. Must be a non-negative integer.
</ResponseField>

<ResponseField name="currency" type="string">
  Three-letter ISO 4217 currency code, uppercase (e.g. `"USD"`, `"EUR"`, `"GBP"`).
</ResponseField>

<ResponseField name="billing_scheme" type="string">
  Always `"per_unit"`. Tiered and volume billing are not supported in the current API version.
</ResponseField>

<ResponseField name="type" type="string">
  `"one_time"` for a single charge, or `"recurring"` for a price that repeats on an interval.
</ResponseField>

<ResponseField name="recurring" type="object | null">
  Present when `type` is `"recurring"`, `null` for `"one_time"` prices.

  <Expandable title="recurring fields">
    <ResponseField name="interval" type="string">
      Billing interval. One of `"day"`, `"week"`, `"month"`, or `"year"`.
    </ResponseField>

    <ResponseField name="interval_count" type="integer">
      Number of intervals between billings. `interval: "month"` and `interval_count: 3` means every 3 months (quarterly). Minimum `1`, maximum `52`.
    </ResponseField>
  </Expandable>
</ResponseField>

<ResponseField name="tax_rate" type="number">
  Tax rate percentage to apply to this price, e.g. `8.5` for 8.5%. Range: `0`–`100`.
</ResponseField>

<ResponseField name="active" type="boolean">
  `true` while the price is available to attach to new invoice lines.
</ResponseField>

<ResponseField name="created" type="string">
  ISO 8601 datetime at which the price was created.
</ResponseField>

***

## Endpoints

<AccordionGroup>
  <Accordion title="GET /api/v1/prices — List prices">
    List prices across your catalog. Results are cursor-paginated.

    **Required scope:** `products:read`

    ### Query parameters

    <ParamField query="product" type="string">
      Filter to prices belonging to a specific product. Accepts a `prod_`-prefixed ID or UUID.
    </ParamField>

    <ParamField query="active" type="boolean">
      Pass `true` for active prices only, `false` for archived ones. Omit to return both.
    </ParamField>

    <ParamField query="currency" type="string">
      Filter by three-letter currency code (e.g. `USD`).
    </ParamField>

    <ParamField query="type" type="string">
      Filter by price type. One of `one_time` or `recurring`.
    </ParamField>

    <ParamField query="cursor" type="string">
      Pagination cursor from a previous `next_cursor`. Omit to start from the first page.
    </ParamField>

    <ParamField query="limit" type="integer">
      Results per page. Defaults to `20`; maximum is `100`.
    </ParamField>

    ### Request

    ```bash theme={null}
    curl "https://invoice.horizonpay.co/api/v1/prices?product=prod_01hxyz1234567890abcdefghij&type=recurring" \
      -H "Authorization: Bearer inv_live_..."
    ```

    ### Response

    ```json theme={null}
    {
      "data": [
        {
          "id": "price_01hxyz1234567890abcdefghij",
          "object": "price",
          "product": "prod_01hxyz1234567890abcdefghij",
          "nickname": "Monthly Pro",
          "unit_amount": 4900,
          "currency": "USD",
          "billing_scheme": "per_unit",
          "type": "recurring",
          "recurring": {
            "interval": "month",
            "interval_count": 1
          },
          "tax_rate": 0,
          "active": true,
          "created": "2024-01-10T11:05:00.000Z"
        },
        {
          "id": "price_01hxyz9876543210zyxwvutsrq",
          "object": "price",
          "product": "prod_01hxyz1234567890abcdefghij",
          "nickname": "Annual Pro",
          "unit_amount": 47880,
          "currency": "USD",
          "billing_scheme": "per_unit",
          "type": "recurring",
          "recurring": {
            "interval": "year",
            "interval_count": 1
          },
          "tax_rate": 0,
          "active": true,
          "created": "2024-01-10T11:10:00.000Z"
        }
      ],
      "next_cursor": null
    }
    ```
  </Accordion>

  <Accordion title="POST /api/v1/prices — Create a price">
    Create a new price and attach it to an existing product. For recurring prices, the `recurring` object is required.

    **Required scope:** `products:write`

    <Note>
      `unit_amount` is always in **minor units** (integer). For a price of \$49.00 USD, send `4900`. For £120.00 GBP, send `12000`.
    </Note>

    ### Body parameters

    <ParamField body="product" type="string" required>
      The `prod_`-prefixed ID or UUID of the parent product.
    </ParamField>

    <ParamField body="unit_amount" type="integer" required>
      Price in minor currency units. Must be a non-negative integer.
    </ParamField>

    <ParamField body="currency" type="string" required>
      Three-letter ISO 4217 currency code, uppercase (e.g. `"USD"`).
    </ParamField>

    <ParamField body="type" type="string">
      `"one_time"` (default) or `"recurring"`. When `"recurring"`, the `recurring` object is required.
    </ParamField>

    <ParamField body="recurring" type="object">
      Required when `type` is `"recurring"`.

      <Expandable title="recurring fields">
        <ParamField body="interval" type="string" required>
          Billing interval: `"day"`, `"week"`, `"month"`, or `"year"`.
        </ParamField>

        <ParamField body="interval_count" type="integer">
          Number of intervals per billing cycle. Defaults to `1`. Maximum `52`.
        </ParamField>
      </Expandable>
    </ParamField>

    <ParamField body="tax_rate" type="number">
      Tax rate percentage, e.g. `8.5` for 8.5%. Range: `0`–`100`. Defaults to `0`.
    </ParamField>

    <ParamField body="nickname" type="string">
      Internal label for this price.
    </ParamField>

    ### Request — one-time price

    ```bash theme={null}
    curl https://invoice.horizonpay.co/api/v1/prices \
      -X POST \
      -H "Authorization: Bearer inv_live_..." \
      -H "Content-Type: application/json" \
      -d '{
        "product": "prod_01hxyz1234567890abcdefghij",
        "unit_amount": 150000,
        "currency": "USD",
        "type": "one_time",
        "tax_rate": 8.5,
        "nickname": "Enterprise Setup Fee"
      }'
    ```

    ### Response `201 Created`

    ```json theme={null}
    {
      "data": {
        "id": "price_01hxyz1111222233334444aaaa",
        "object": "price",
        "product": "prod_01hxyz1234567890abcdefghij",
        "nickname": "Enterprise Setup Fee",
        "unit_amount": 150000,
        "currency": "USD",
        "billing_scheme": "per_unit",
        "type": "one_time",
        "recurring": null,
        "tax_rate": 8.5,
        "active": true,
        "created": "2024-06-01T09:00:00.000Z"
      }
    }
    ```

    ### Request — recurring price

    ```bash theme={null}
    curl https://invoice.horizonpay.co/api/v1/prices \
      -X POST \
      -H "Authorization: Bearer inv_live_..." \
      -H "Content-Type: application/json" \
      -d '{
        "product": "prod_01hxyz1234567890abcdefghij",
        "unit_amount": 4900,
        "currency": "USD",
        "type": "recurring",
        "recurring": {
          "interval": "month",
          "interval_count": 1
        },
        "nickname": "Monthly Pro"
      }'
    ```

    ### Response `201 Created`

    ```json theme={null}
    {
      "data": {
        "id": "price_01hxyz1234567890abcdefghij",
        "object": "price",
        "product": "prod_01hxyz1234567890abcdefghij",
        "nickname": "Monthly Pro",
        "unit_amount": 4900,
        "currency": "USD",
        "billing_scheme": "per_unit",
        "type": "recurring",
        "recurring": {
          "interval": "month",
          "interval_count": 1
        },
        "tax_rate": 0,
        "active": true,
        "created": "2024-06-01T09:05:00.000Z"
      }
    }
    ```
  </Accordion>

  <Accordion title="GET /api/v1/prices/:id — Retrieve a price">
    Retrieve a single price by ID.

    **Required scope:** `products:read`

    The `:id` path parameter accepts either the `price_`-prefixed public ID or the underlying UUID.

    ### Request

    ```bash theme={null}
    curl https://invoice.horizonpay.co/api/v1/prices/price_01hxyz1234567890abcdefghij \
      -H "Authorization: Bearer inv_live_..."
    ```

    ### Response `200 OK`

    ```json theme={null}
    {
      "data": {
        "id": "price_01hxyz1234567890abcdefghij",
        "object": "price",
        "product": "prod_01hxyz1234567890abcdefghij",
        "nickname": "Monthly Pro",
        "unit_amount": 4900,
        "currency": "USD",
        "billing_scheme": "per_unit",
        "type": "recurring",
        "recurring": {
          "interval": "month",
          "interval_count": 1
        },
        "tax_rate": 0,
        "active": true,
        "created": "2024-01-10T11:05:00.000Z"
      }
    }
    ```
  </Accordion>

  <Accordion title="PATCH /api/v1/prices/:id — Update a price">
    Update mutable fields on a price. Omitted fields are left unchanged.

    **Required scope:** `products:write`

    <Warning>
      The parent `product` cannot be changed after creation. To move a price to a different product, create a new price and archive the old one.
    </Warning>

    <Note>
      `unit_amount` remains in minor units on update. To change a $49.00 price to $59.00, send `"unit_amount": 5900`.
    </Note>

    ### Body parameters

    All fields are optional.

    <ParamField body="nickname" type="string | null">
      New internal label. Pass `null` or `""` to clear.
    </ParamField>

    <ParamField body="unit_amount" type="integer">
      New price in minor currency units.
    </ParamField>

    <ParamField body="currency" type="string">
      New three-letter currency code.
    </ParamField>

    <ParamField body="type" type="string">
      `"one_time"` or `"recurring"`. Changing type requires updating the `recurring` object accordingly.
    </ParamField>

    <ParamField body="recurring" type="object">
      Update the recurring interval. Only meaningful when `type` is `"recurring"`.

      <Expandable title="recurring fields">
        <ParamField body="interval" type="string">Billing interval: `"day"`, `"week"`, `"month"`, or `"year"`.</ParamField>
        <ParamField body="interval_count" type="integer">Number of intervals per cycle. Min `1`, max `52`.</ParamField>
      </Expandable>
    </ParamField>

    <ParamField body="tax_rate" type="number">
      New tax rate percentage. Range: `0`–`100`.
    </ParamField>

    <ParamField body="active" type="boolean">
      Set to `false` to deactivate without deleting.
    </ParamField>

    ### Request

    ```bash theme={null}
    curl https://invoice.horizonpay.co/api/v1/prices/price_01hxyz1234567890abcdefghij \
      -X PATCH \
      -H "Authorization: Bearer inv_live_..." \
      -H "Content-Type: application/json" \
      -d '{
        "unit_amount": 5900,
        "nickname": "Monthly Pro (2024)"
      }'
    ```

    ### Response `200 OK`

    ```json theme={null}
    {
      "data": {
        "id": "price_01hxyz1234567890abcdefghij",
        "object": "price",
        "product": "prod_01hxyz1234567890abcdefghij",
        "nickname": "Monthly Pro (2024)",
        "unit_amount": 5900,
        "currency": "USD",
        "billing_scheme": "per_unit",
        "type": "recurring",
        "recurring": {
          "interval": "month",
          "interval_count": 1
        },
        "tax_rate": 0,
        "active": true,
        "created": "2024-01-10T11:05:00.000Z"
      }
    }
    ```
  </Accordion>

  <Accordion title="DELETE /api/v1/prices/:id — Archive a price">
    Archive a price. The price is set to `active: false` and will no longer be returned when filtering by `active=true`. Existing invoice lines that reference this price are not affected.

    **Required scope:** `products:write`

    To reactivate an archived price, use [PATCH /api/v1/prices/:id](#) with `"active": true`.

    ### Request

    ```bash theme={null}
    curl https://invoice.horizonpay.co/api/v1/prices/price_01hxyz1234567890abcdefghij \
      -X DELETE \
      -H "Authorization: Bearer inv_live_..."
    ```

    ### Response `200 OK`

    The archived price object is returned, with `active: false`.

    ```json theme={null}
    {
      "data": {
        "id": "price_01hxyz1234567890abcdefghij",
        "object": "price",
        "product": "prod_01hxyz1234567890abcdefghij",
        "nickname": "Monthly Pro",
        "unit_amount": 4900,
        "currency": "USD",
        "billing_scheme": "per_unit",
        "type": "recurring",
        "recurring": {
          "interval": "month",
          "interval_count": 1
        },
        "tax_rate": 0,
        "active": false,
        "created": "2024-01-10T11:05:00.000Z"
      }
    }
    ```
  </Accordion>
</AccordionGroup>

***

## Error responses

| Status             | Cause                                                                                                                                                          |
| ------------------ | -------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `400 Bad Request`  | Missing `product`, `unit_amount`, or `currency`; non-integer `unit_amount`; missing `recurring` object when `type` is `"recurring"`; or invalid currency code. |
| `401 Unauthorized` | Missing or invalid `Authorization` header.                                                                                                                     |
| `403 Forbidden`    | The API key lacks `products:read` or `products:write`.                                                                                                         |
| `404 Not Found`    | No price or product with the given ID exists in your workspace.                                                                                                |
