Create a Recurring Order

Learn how to set up and create a Recurring Order.

Overview

Recurring Orders allow businesses to automate the reordering process for frequently purchased products, ensuring a seamless and efficient purchasing experience for both B2B and B2C customers.

In this tutorial, you will learn how to:

  • Define how often a Recurring Order should be created using different intervals such as daily, weekly, or monthly.
  • Set up pricing options for a Recurring Order and its items.
  • Create your first Recurring Order using the Orders API.
  • Search for a Recurring Order.

Prerequisites

To follow the tutorial steps, you will need the following:

  • A Composable Commerce Project with sample data

    In this tutorial, we use sample data from a preconfigured Project. You can choose to use the sample data when you initially set up your Project in the Merchant Center.
  • A published Product with a Product Variant that has the following configuration:
    • id set to 1
    • SKU set to SKU-TEST

Instructions

Create a Recurrence Policy

A Recurrence Policy specifies how often an item is reordered—for example, daily, weekly, monthly, or on a specific day of each month. They can be reused and assigned to individual Line Items, Custom Line Items, and prices.

Let's consider you want to sell items on a weekly basis. We'll need to create a Recurrence Policy using the Create RecurrencePolicy endpoint, with the RecurrencePolicyDraft intervalUnit as Weeks and value as 1. These fields determine the time between orders.
RecurrencePolicyDraftjson
{
  "key": "policy-weekly",
  "name": {
    "en": "Weekly",
    "de": "Wöchentlich"
  },
  "schedule": {
    "type": "standard",
    "value": 1,
    "intervalUnit": "Weeks"
  }
}
To see other examples of possible schedules, see Recurring Orders overview.

After creating the Recurrence Policy, you can define the pricing for it.

Set up pricing

In this scenario, you want to reward customers for their loyalty by setting up special recurrence pricing. Instead of charging the one time-purchase price for the item, customers receive a discount, depending on their chosen schedule.

You can choose to use Embedded or Standalone Prices for your setup; we've included the setup information for both. To understand the differences between both the types of prices, see Pricing overview.

Embedded Price setup

Standalone Price setup


To set up an Embedded Price, let's update the Product using the Add Price action in the Update Product endpoint, referencing the newly created Recurrence Policy (policy-weekly).

Add Embedded Price requestjson
{
  "version": 2,
  "actions": [
    {
      "action": "addPrice",
      "variantId": 1,
      "price": {
        "value": {
          "currencyCode": "EUR",
          "centAmount": 4000
        },
        "recurrencePolicy": {
          "key": "policy-weekly",
          "typeId": "recurrence-policy"
        }
      },
      "staged": false
    }
  ]
}



To set up a Standalone Price, let's create a new Standalone Price using the Create StandalonePrice endpoint, referencing the newly created Recurrence Policy (policy-weekly).

Create Standalone Price requestjson
{
  "key" : "my-price",
  "sku" : "SKU-TEST",
  "value" : {
    "currencyCode" : "EUR",
    "centAmount" : 4000
  },
  "country" : "DE",
  "recurrencePolicy": {
    "key": "policy-weekly",
    "typeId": "recurrence-policy"
  },
  "active" : true
}

In this case, the price of €40 is selected only if the customer chooses the given variant and the weekly order interval.

If you want to offer the same price (of €40) for a monthly basis too, you must add the price with a monthly Recurrence Policy schedule.

If you do not set specific prices for an item based on a Recurrence Policy interval, the one time-purchase price will be used instead.

Create a Cart

Now that we have defined the Recurrence Policy and the prices for it, let's create a Cart using the Create Cart endpoint. For simplicity, the Cart does not calculate taxes.
Create Cart requestjson
{
  "currency": "EUR",
  "taxMode": "Disabled",
  "customerId": "{{customer-id}}",
  "country": "DE",
  "shippingAddress": {
      "country": "DE"
  }
}

Add a Line Item

Now that we've created a Cart, let's add a Line Item to the Cart using the Update Cart endpoint.
We'll need to include the Recurrence Policy that we created earlier (in the recurrenceInfo field), and how the price should be chosen in subsequent orders (in the priceSelectionMode field). The price chosen in subsequent orders is determined in two ways:
  • If priceSelectionMode is Fixed, future changes to the Product's price will not affect existing Recurring Orders.
  • If priceSelectionMode is Dynamic, future changes to the Product's price will affect existing Recurring Orders.
In this scenario, since we want to keep the item price the same always, the priceSelectionMode field is set to Fixed.
Add Line Item update action requestjson
{
  "version": 1,
  "actions": [
    {
      "action": "addLineItem",
      "productId": "{{product-id}}",
      "variantId": 1,
      "quantity": 1,
      "recurrenceInfo": {
        "recurrencePolicy": {
          "key": "policy-weekly",
          "typeId": "recurrence-policy"
        },
        "priceSelectionMode": "Fixed"
      }
    }
  ]
}
Line Items and Custom Line Items with recurrence information are known as recurring items. For more information about recurring items and the price selection mode, see Recurring Orders overview.

Now that we've created a Cart, let's create an Order.

Create an Order

You can create a Recurring Order using the Recurring Orders API or Orders API. The Recurring Orders API gives you more flexibility to configure your Recurring Order—for example, you can delay the start until a specific date, set the end date, and set Custom Fields. For more information about the different methods, see Recurring Orders overview.
In this tutorial, let's create a Recurring Order using the Create Order endpoint on the Orders API. This is the same endpoint used to create one-time Orders, and the process remains the same.
Create Order requestjson
{
  "cart": {
    "id": "{{cart-id}}",
    "typeId": "cart"
  },
  "version": 1
}
After the Order is created, the platform automatically checks if the Line Item includes recurrence information (specified through the recurrenceInfo field). If present, a new recurring Cart and Recurring Order are created for the Recurrence Policy in the background, linking the new Recurring Order to the original Order.

The Recurring Order manages the schedule and creation of all future Orders based on the recurring Cart and specified recurrence settings.

Search for a Recurring Order

Now, let's locate the Recurring Order that was automatically created.

Each Recurring Order maintains a relationship with the original Order that initiated the subscription or contract. This relationship is represented by the originOrder field, which references the initial Order associated with the Recurring Order.
To retrieve the Recurring Order, let's use the Query Order endpoint with the originOrder parameter:
curl --get 'https://api.{region}.commercetools.com/{projectKey}/recurring-orders?where=originOrder(id="b4124132-cd94-4522-9df8-b2f507a1dbde")' -i \
--header 'Content-Type: application/json' \
--header "Authorization: Bearer ${BEARER_TOKEN}"

The response should be similar to the following:

Query Order response: RecurringOrderjson
{
  "limit": 20,
  "offset": 0,
  "count": 1,
  "total": 1,
  "results": [
    {
      "id": "47556915-f6dc-4802-b799-e1c560f54019",
      "version": 1,
      "versionModifiedAt": "2025-06-17T14:36:53.326Z",
      "lastMessageSequenceNumber": 1,
      "createdAt": "2025-06-17T14:36:53.326Z",
      "lastModifiedAt": "2025-06-17T14:36:53.326Z",
      "lastModifiedBy": {
        "clientId": "OnaHIvnM1lXcMpBJS_ODitiv",
        "isPlatformClient": false
      },
      "createdBy": {
        "clientId": "OnaHIvnM1lXcMpBJS_ODitiv",
        "isPlatformClient": false
      },
      "cart": {                                      //1
        "typeId": "cart",
        "id": "5eddf45d-b462-48a4-8ac8-d74b5df5c9cb"
      },
      "originOrder": {                               //2
        "typeId": "order",
        "id": "b4124132-cd94-4522-9df8-b2f507a1dbde"
      },
      "startsAt": "2025-06-17T14:36:53.255Z",        //3
      "nextOrderAt": "2025-06-24T14:36:53.255Z",     //4
      "recurringOrderState": "Active",
      "schedule": {                                  //5
        "type": "standard",
        "value": 1,
        "intervalUnit": "Weeks"
      },
      "customer": {
        "typeId": "customer",
        "id": "f77e6cb6-4e5f-4bcb-848e-793cafd6ab91"
      }
    }
  ]
}

The highlighted lines contain the following information:

  1. cart: the Cart created specifically for this Recurring Order. It serves as a blueprint for generating future Orders.
  2. originOrder: the original Order from which this Recurring Order was initiated.
  3. startsAt: the date and time when this Recurring Order becomes active and is eligible to generate new Orders.
  4. nextOrderAt: the scheduled date and time when the next Order is automatically created by the platform, using the latest version of the associated cart.
  5. schedule: the defined interval that determines how often new Orders are generated for this Recurring Order.

Summary

In this tutorial, we have shown how you can:

  • Create a Recurrence Policy to sell products at specific prices for different schedules
  • Set up specific prices for your products and define the price selection method to control future price changes
  • Create a Cart and add a Line Item with recurrence information
  • Create a Recurring Order (using the Orders API)
  • Search for a Recurring Order that was created automatically

With this knowledge, you can now use Recurring Orders to reduce manual workload while building customer loyalty through convenience and consistency.