> For the complete documentation index, see [llms.txt](https://developer.paddle.com/llms.txt).

# Create products and prices

Products and prices make up your catalog in Paddle. They hold information about what's being sold, how much items are being sold for, and how often a charge is made.

---

Your product catalog holds the products that are being sold to customers, including subscription plans, recurring addons, and one-time charges.

Create products and related prices to start billing.

## How it works

A complete product in Paddle is made up of two parts:

1. A [product entity](https://developer.paddle.com/api-reference/products/overview.md) that describes the item, like its name, description, and an image.
2. At least one related [price entity](https://developer.paddle.com/api-reference/prices/overview.md) that describes how much and how often a product is billed.

Products are the items that customers buy — like subscription plans, recurring addons, or one-time charges. Prices describe how they pay for them.

In this example, Enterprise is a product and $3000/mo is a price for it.

{% instruction-steps %}
When switching from monthly to yearly:

- Products remain the same — the name and details remain as Enterprise.
- Prices change — your page should fetch prices for products where the billing cycle is yearly rather than monthly.

{% /dashboard-instructions %}

You can create as many prices for a product as you want to describe all the ways it's billed. However, prices may only relate to one product.

### Billing cycle

The billing cycle against a price determines how often Paddle bills for it. You can set an interval and a frequency. This is typically things like every month, every three months, or every year, but you can be as flexible as you like.

Paddle supports multi-product subscriptions, letting you [add recurring addons alongside subscription plans](https://developer.paddle.com/build/subscriptions/add-remove-products-prices-addons.md). When building multi-product subscriptions, all items on a subscription must have the same billing period. This means that if a customer subscribes to your "Pro plan" with a yearly price, you must also create yearly price for any recurring addons. You can't add a monthly addon to a subscription for a yearly plan.

### One-time charges

Prices don't have to have a billing cycle. These are called "one-time charges."

One-time charges can be billed to subscriptions. They're typically used for things like setup or onboarding fees at the start of a subscription, or data auditing or support incident fees during a subscription.

You might also use them to offer ebooks, access to webinars, or other learning resources to customers.

## Create a product

Create products to describe items being sold. You can add prices to products afterward.

We recommend creating products using the Paddle dashboard.

{% tabs sync="interaction-preference" %}
{% tab-item title="Dashboard" %}

{% instruction-steps %}

1. Go to **Paddle** > **Catalog** > **Products**.
2. Click {% mock-button icon="carbon:add" %}New product
3. Enter details for your new product.
4. Click Save when you're done.

{% /instruction-steps %}

{% /dashboard-instructions %}

{% /tab-item %}

{% tab-item title="API" %}

Send a `POST` request to the `/products` endpoint to create a product.

In your request, include the product `name` and `tax_category`.

Optionally include `description`, `image_url` (HTTPS, square images recommended), and `custom_data`.

{% callout type="info" %}
For `tax_category`, `standard` or `saas` are available by on all Paddle accounts by default. You can request other tax categories for your account in the Paddle dashboard.
{% /callout %}

{% accordion %}
{% accordion-item title="Create a subscription plan product" %}

This example creates a new product for a subscription plan called "AeroEdit Student." It includes an object of custom data.

If successful, Paddle responds with a copy of the new product entity. Paddle creates an `id` starting with `pro_` — keep this for the next step to associate a price.

{% api-example method="POST" path="/products" href="/api-reference/products/create-product" %}

```json
{
  "name": "AeroEdit Student",
  "tax_category": "standard",
  "description": "Essential tools for student pilots to manage flight logs, analyze performance, and plan routes, and ensure compliance. Valid student pilot certificate from the FAA required.",
  "image_url": "https://paddle.s3.amazonaws.com/user/165798/bT1XUOJAQhOUxGs83cbk_pro.png",
  "custom_data": {
    "features": {
      "aircraft_performance": true,
      "compliance_monitoring": false,
      "flight_log_management": true,
      "payment_by_invoice": false,
      "route_planning": true,
      "sso": false
    },
    "suggested_addons": [
      "pro_01h1vjes1y163xfj1rh1tkfb65",
      "pro_01gsz97mq9pa4fkyy0wqenepkz"
    ],
    "upgrade_description": null
  }
}
```

```json
{
  "data": {
    "id": "pro_01htz88xpr0mm7b3ta2pjkr7w2",
    "name": "AeroEdit Student",
    "tax_category": "standard",
    "type": "standard",
    "description": "Essential tools for student pilots to manage flight logs, analyze performance, and plan routes, and ensure compliance. Valid student pilot certificate from the FAA required.",
    "image_url": "https://paddle.s3.amazonaws.com/user/165798/bT1XUOJAQhOUxGs83cbk_pro.png",
    "custom_data": {
      "features": {
        "aircraft_performance": true,
        "compliance_monitoring": false,
        "flight_log_management": true,
        "payment_by_invoice": false,
        "route_planning": true,
        "sso": false
      },
      "suggested_addons": [
        "pro_01h1vjes1y163xfj1rh1tkfb65",
        "pro_01gsz97mq9pa4fkyy0wqenepkz"
      ],
      "upgrade_description": null
    },
    "status": "active",
    "import_meta": null,
    "created_at": "2024-04-08T16:22:16.024Z",
    "updated_at": "2024-04-08T16:22:16.024Z"
  },
  "meta": {
    "request_id": "cf40234b-e140-44d1-a83f-7bbdedd88589"
  }
}
```

{% /api-example %}

{% /accordion-item %}
{% accordion-item title="Create a recurring addon product" %}

This example creates a product for a recurring addon called "Voice rooms addon."

If successful, Paddle responds with a copy of the new product entity. Paddle creates an `id` starting with `pro_` — keep this for the next step to associate a price.

{% api-example method="POST" path="/products" href="/api-reference/products/create-product" %}

```json
{
  "name": "Voice rooms addon",
  "tax_category": "standard",
  "description": "Create voice rooms in your chats to work in real time alongside your colleagues. Includes unlimited voice rooms and recording backup for compliance.",
  "image_url": "https://paddle-sandbox.s3.amazonaws.com/user/10889/GcZzBjXRfiraensppgtQ_icon2.png"
}
```

```json
{
  "data": {
    "id": "pro_01h1vjes1y163xfj1rh1tkfb65",
    "name": "Voice rooms addon",
    "tax_category": "standard",
    "description": "Create voice rooms in your chats to work in real time alongside your colleagues. Includes unlimited voice rooms and recording backup for compliance.",
    "image_url": "https://paddle-sandbox.s3.amazonaws.com/user/10889/GcZzBjXRfiraensppgtQ_icon2.png",
    "custom_data": null,
    "status": "active",
    "created_at": "2023-06-01T13:30:50.302Z"
  },
  "meta": {
    "request_id": "4fd71021-1ba6-4401-97bc-355806af83c3"
  }
}
```

{% /api-example %}

{% /accordion-item %}
{% accordion-item title="Create a one-time charge" %}

This example creates a new product for a one-time charge called "Custom domains setup."

If successful, Paddle responds with a copy of the new product entity. Paddle creates an `id` starting with `pro_` — keep this for the next step to associate a price.

{% api-example method="POST" path="/products" href="/api-reference/products/create-product" %}

```json
{
  "name": "Custom domains setup",
  "tax_category": "standard",
  "description": "Make ChatApp truly your own with custom domains! Custom domains reinforce your brand identity and make it easy for your team to access ChatApp.",
  "image_url": "https://paddle-sandbox.s3.amazonaws.com/user/10889/SW3OevDQ92dUHSkN5a2x_icon3.png"
}
```

```json
{
  "data": {
    "id": "pro_01gsz97mq9pa4fkyy0wqenepkz",
    "name": "Custom domains",
    "tax_category": "standard",
    "description": "Make ChatApp truly your own with custom domains! Custom domains reinforce your brand identity and make it easy for your team to access ChatApp.",
    "image_url": "https://paddle-sandbox.s3.amazonaws.com/user/10889/SW3OevDQ92dUHSkN5a2x_icon3.png",
    "custom_data": null,
    "status": "active",
    "created_at": "2023-02-23T14:01:02.441Z"
  },
  "meta": {
    "request_id": "7b476cdd-c8eb-4f47-90c3-bf24ad5187db"
  }
}
```

{% /api-example %}

{% /accordion-item %}
{% /accordion %}

{% /tab-item %}
{% /tabs %}

## Create a related price

Once you've created products, create related prices that describe how you bill for them. You can't offer a product for sale without creating a price.

{% callout type="note" %}
Add price overrides to a price to set country specific prices. Price overrides let you override the base price with a custom price and currency for any country. See: [Localize prices](https://developer.paddle.com/build/products/offer-localized-pricing.md)
{% /callout %}

{% tabs sync="interaction-preference" %}
{% tab-item title="Dashboard" %}

{% instruction-steps %}

1. Go to **Paddle** > **Catalog** > **Products**, then click the product you want to add a price to in the list.
2. Under the Prices section, click {% mock-button icon="carbon:add" %}New price
3. Enter details for your new price.
4. Click Save when you're done.

{% /instruction-steps %}

{% /dashboard-instructions %}

{% /tab-item %}

{% tab-item title="API" %}

Send a `POST` request to the `/prices` endpoint to create a price.

In you request, include `product_id` (Paddle ID of the product), `unit_price` (base price), and a `description`.

To make a price recurring, include `billing_cycle` with `interval` and `frequency`.

Optionally include `trial_period` (requires `billing_cycle`), `name` (shown at checkout and on invoices), `unit_price_overrides` for [localized pricing](https://developer.paddle.com/build/products/offer-localized-pricing.md), `tax_mode`, `quantity` limits (defaults to 1-100), and `custom_data`.

{% accordion %}
{% accordion-item title="Create a price for a subscription plan" %}

This example creates a monthly price for a subscription plan with a trial period. It's related to the subscription plan product using the `product_id` field.

If successful, Paddle responds with a copy of the new price entity.

{% api-example method="POST" path="/prices" href="/api-reference/prices/create-price" %}

```json
{
  "description": "Monthly (per seat) with 14 day trial",
  "name": "Monthly (per seat)",
  "product_id": "pro_01htz88xpr0mm7b3ta2pjkr7w2",
  "unit_price": {
    "amount": "500",
    "currency_code": "USD"
  },
  "billing_cycle": {
    "interval": "month",
    "frequency": 1
  },
  "trial_period": {
    "interval": "day",
    "frequency": 14
  },
  "tax_mode": "account_setting"
}
```

```json
{
  "data": {
    "id": "pri_01hv0vax6rv18t4tamj848ne4d",
    "product_id": "pro_01htz88xpr0mm7b3ta2pjkr7w2",
    "type": "standard",
    "description": "Monthly (per seat) with 14 day trial",
    "name": "Monthly (per seat)",
    "billing_cycle": {
      "interval": "month",
      "frequency": 1
    },
    "trial_period": {
      "interval": "day",
      "frequency": 14,
      "requires_payment_method": false
    },
    "tax_mode": "account_setting",
    "unit_price": {
      "amount": "500",
      "currency_code": "USD"
    },
    "unit_price_overrides": [],
    "custom_data": null,
    "status": "active",
    "quantity": {
      "minimum": 1,
      "maximum": 100
    },
    "import_meta": null,
    "created_at": "2024-04-09T07:14:38.424504286Z",
    "updated_at": "2024-04-09T07:14:38.424504359Z"
  },
  "meta": {
    "request_id": "9e7f51e8-838b-4b2c-b0fa-d52d0593354c"
  }
}
```

{% /api-example %}

{% /accordion-item %}
{% accordion-item title="Create a price for a recurring addon" %}

This example creates a monthly price for a recurring addon. It's related to the recurring addon product using the `product_id` field.

If successful, Paddle responds with a copy of the new price entity.

{% api-example method="POST" path="/prices" href="/api-reference/prices/create-price" %}

```json
{
  "product_id": "pro_01h1vjes1y163xfj1rh1tkfb65",
  "description": "Monthly (recurring addon)",
  "name": "Monthly (recurring addon)",
  "billing_cycle": {
    "interval": "month",
    "frequency": 1
  },
  "unit_price": {
    "amount": "10000",
    "currency_code": "USD"
  }
}
```

```json
{
  "data": {
    "id": "pri_01h1vjfevh5etwq3rb416a23h2",
    "product_id": "pro_01h1vjes1y163xfj1rh1tkfb65",
    "name": "Monthly (recurring addon)",
    "description": "Monthly (recurring addon)",
    "billing_cycle": {
      "interval": "month",
      "frequency": 1
    },
    "trial_period": null,
    "tax_mode": "account_setting",
    "unit_price": {
      "amount": "10000",
      "currency_code": "USD"
    },
    "unit_price_overrides": [],
    "custom_data": null,
    "status": "active",
    "quantity": {
      "minimum": 1,
      "maximum": 100
    }
  },
  "meta": {
    "request_id": "4e373a48-9dfb-4d97-a914-e7e45ca3a61d"
  }
}
```

{% /api-example %}

{% /accordion-item %}
{% accordion-item title="Create a price for a one-time charge" %}

This example creates a monthly price for a one-time charge. It's related to the one-time charge product using the `product_id` field. Only one charge may be applied at once, so it includes the `quantity` object with `minimum` and `maximum` values of `1`.

If successful, Paddle responds with a copy of the new price entity.

{% api-example method="POST" path="/prices" href="/api-reference/prices/create-price" %}

```json
{
  "product_id": "pro_01gsz97mq9pa4fkyy0wqenepkz",
  "description": "One-time charge",
  "billing_cycle": null,
  "unit_price": {
    "amount": "19900",
    "currency_code": "USD"
  },
  "quantity": {
    "minimum": 1,
    "maximum": 1
  }
}
```

```json
{
  "data": {
    "id": "pri_01gsz98e27ak2tyhexptwc58yk",
    "product_id": "pro_01gsz97mq9pa4fkyy0wqenepkz",
    "name": null,
    "description": "One-time charge",
    "billing_cycle": null,
    "trial_period": null,
    "tax_mode": "account_setting",
    "unit_price": {
      "amount": "19900",
      "currency_code": "USD"
    },
    "unit_price_overrides": [],
    "custom_data": null,
    "status": "active",
    "quantity": {
      "minimum": 1,
      "maximum": 1
    }
  },
  "meta": {
    "request_id": "94f4aa43-45b3-4f01-90ee-4a593eb1b656"
  }
}
```

{% /api-example %}

{% /accordion-item %}
{% /accordion %}

{% /tab-item %}
{% /tabs %}

## Review prices and products

Once you've created products and related prices, you can use the `include` query parameter in the Paddle API to review them. You can:

- [Get a product and include its related prices](#review-get-product)
- [Get a price and include its related product](#review-get-price)
- [List prices for a product](#review-list-prices)

### Get a product and all prices

Use the `include` query parameter with the value `prices` to include related prices in the response.

{% api-endpoint method="GET" path="/products/{product_id}?include=prices" href="/api-reference/products/get-product" %}

{% /api-endpoint %}

### Get a price and related product

Use the `include` query parameter with the value `product` to include the related product in the response.

{% api-endpoint method="GET" path="/prices/{price_id}?include=product" href="/api-reference/prices/get-price" %}

{% /api-endpoint %}

### List prices for a product

Use the `product_id` query parameter to filter prices by product. Pass a comma-separated list to list prices for more than one product.

{% api-endpoint method="GET" path="/prices?product_id={product_id}" href="/api-reference/prices/list-prices" %}

{% /api-endpoint %}