chevrons-vertical
go ruby

Overview

Deliveroo has developed a suite of APIs to make it easier than ever to increase your conversion, streamline your operations and get updated data on your business. Let machines do the work and focus on delighting your customers.

Partner Platform Suite

Use our Order API to manage orders arriving from Deliveroo. These include two separate webhooks; one for accepting or rejecting incoming orders and receiving updates such as cancellations and the rider status and the other for receiving orders after they’ve been accepted by the site, as well as cancellations.

The Menu API allows sites to push a menu from their own system and manage inventory in real-time. Update your menus seamlessly, including pictures, prices, pos IDs and allergen information.

Our Site API can be used to open and close the site, control opening hours, input days off and set a workload mode when the site is running overcapacity.

Retail Platform Suite

This suite has access to everything our partner platform suite offers as well as the Picking API. Sites can receive incoming orders from Deliveroo and remove or substitute items from the basket before accepting or rejecting the order.

Signature Suite

Our Signature suite lets you build your apps on top of Deliveroo's delivery service.

The Deliveroo fulfillment API allows partners to request delivery via Deliveroo couriers for an order processed and managed by their own internal systems.

Our Site API can be used to open and close the site, control opening hours, input days off and set a workload mode when the site is running overcapacity.

Overview of Deliveroo APIs

Authorization

Authentication is performed via HTTP Basic Auth. Use your api-key as the Basic Auth username and the api-secret as the password.

All API requests must be made over HTTPS. Calls made over plain HTTP will fail, as will API requests made without any authentication headers.

The content-type header for all requests must be set to application/json.

Our APIs are served over HTTPS with JSON payloads.

Verify API credentials

Once you've been issued an api-key and api-secret, you can verify your credentials using this endpoint.

Example request with cURL:

curl --user <api-key>:<api-secret> https://partners.deliveroo.com/api/v1/auth/verify
HTTP Request

GET /api/v1/auth/verify

Successful response:

{
  "api_access": {
    "fulfillment": true,
    "menu": true,
    "pos": false
  },
  "api_key": "<api-key>",
  "test_mode": false
}

An HTTP 401 unauthorized error:

{
  "error": {
    "code": "unauthorized",
    "message": "api key or secret is invalid"
  }
}

Fulfillment API

Introduction

The Deliveroo fulfillment API allows partners to request delivery via Deliveroo couriers for an order processed and managed by their own internal systems.

We offer 5 key features:

How it works

  1. A customer places an order on your restaurant's website or app.
  2. You create the order with Deliveroo's fulfillment API.
  3. A Deliveroo rider picks up and delivers the order, you can optionally receive webhook callbacks notifying you of the order's lifecycle.

Test mode

A test mode is provided to simulate the lifecycle of an order. Test credentials are distinct from live credentials.

Quotes and orders created in test mode are isolated and distinct from those in live mode. Similarly, webhook callback configuration is independent from live mode so you can test functionality without interfering with live configuration.

Use the test-api-key as the Basic Auth username and the test-api-secret as the password.

Note: Test mode does not yet cover every feature found in the live APIs. The specifics for each endpoint can be found in the respective documentation.

Verify API test credentials

Example request with cURL:

curl --user <test-api-key>:<test-api-secret> https://partners.deliveroo.com/api/v1/auth/verify

HTTP Request

GET /api/v1/auth/verify

Successful response:

{
  "api_key": "<test-api-key>",
  "test_mode": true
}

An HTTP 401 unauthorized error:

{
  "error": {
    "code": "unauthorized",
    "message": "api key or secret is invalid"
  }
}

Errors

The fulfillment API uses the following HTTP status codes for errors.

Code Description
400 Bad request
A required parameter is missing or invalid, or the destination cannot be delivered.
401 Unauthorized
The provided API key and API token is invalid or disabled.
404 Not found
The specified resource could not be found.
>=500 Internal server error
Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Errors return a JSON structured like this, where message may contain more specific information:

{
  "error": {
    "code": "unauthorized",
    "message": "invalid credential"
  }
}

Additionally, the returned JSON error will contain additional details for developers in the message field, as well as a specific error code.

Code Description
bad_gateway An error occurred on one of our internal systems. You may try again.
bad_request Generally as a result of a validation issue.
duplicate_order_id The specified order identifier already exists.
menu_item_unavailable Order contains item that has run out of stock.
missing_configuration Your account is missing required configuration.
modifiers_malformed Order items contain unexpected modifiers for parent, or quantity.
not_found The specified resource could not be found.
restaurant_closed The restaurant is currently closed.
unauthorized Missing or invalid API key or secret.
undeliverable The destination address is undeliverable, can occur at order creation.
unprocessable_entity Idempotency key was reused with a different request body.
idempotency_check The initial request submitted with the provided idempotency key is still being processed.
busy_rider_fleet All riders in the area are busy or when it is off-peak time there are not enough riders.

Idempotent requests

Some endpoints (such as create order v2) support idempotency for safely retrying requests without unintentionally repeating an operation. This is useful for when you do not receive a response, due to a network error for example.

To perform an idempotent request, provide an Idempotency-Key: <key> header in the request.

An idempotency key is any unique client-generated value with sufficient entropy to avoid collisions. We recommend using V4 UUIDs as your keys.

For idempotent requests, the API saves the status code and body of the response of the initial request and, when the same idempotency key is used in another request, it replays the saved response. This includes error responses such as 400 and 500 errors. The following validation is also performed for idempotent requests:

When a response is replayed, an Idempotent-Replayed: true header will be attached to the response.

Idempotency keys will be removed once they are at least 24 hours old, after which a key may be reused and will be processed as an initial request and response.

Restaurants

Get restaurants for location

Get relevant restaurants which deliver to a location. Some restaurants may be returned which are closed or otherwise unavailable.

A location may be specified either by a lat/lon or by postcode/country_code.

In test mode, resolution of locations is constrained and coarse, searching for specific restaurants is not supported. First, based on the location specified, the closest city from the table below is selected. Then, a list of randomly generated restaurants, located at random positions within the city selected, is returned. The following table lists cities that are currently supported in test mode, the sample location parameters may be used to obtain a list of restaurants within a city.

City lat, lon postcode, country_code
Amsterdam 52.37470870786686, 4.893654361769081 1012 ZJ, NL
Brussels 50.848384005904016, 4.3524495407350186 1000, BE
Cardiff 51.481583, -3.179090 n/a
Dubai 25.237937224403826, 55.26566394128973 n/a
Dublin 53.34987581794567, -6.270388962883456 n/a
Edinburgh 55.953251, -3.188267 n/a
Hong Kong 22.294276514141128, 114.17232206816648 n/a
Kuwait City 29.37954940317905, 47.975323968949 n/a
London 51.5101095, -0.0932817 EC4R 3TE, GB
Madrid 40.42166681761659, -3.688642740370964 28001, ES
Rome 41.90819745538432, 12.46835546911818 00193, IT
Singapore 1.3548271449398184, 103.86693061094368 550307, SG
Sydney -33.82510611963573, 151.2152967 2000, AU
Taipei 25.02836031697522, 121.45349656673051 n/a

HTTP Request

GET /api/v1/fulfillment/restaurants?lat={lat}&lon={lon}&brand_id={brand_id}

GET /api/v1/fulfillment/restaurants?postcode={postcode}&country_code={country_code}&brand_id={brand_id}

Request Parameters by lat/lon

Parameter Description
lat float
51.5101095 Delivery location latitude.
lon float
-0.0932817 Delivery location longitude.
brand_id string (optional)
brandid-gb Unique identifier for the brand.

Request Parameters by postcode/country code

Parameter Description
postcode string
EC4R3TE Delivery location postcode.
country_code string
GB Delivery location country code.
brand_id string (optional)
brandid-gb Unique identifier for the brand.

Response parameters

Get restaurants for location response body example:

[
  {
    "id": "EgG27rbviS26itnuhLaHin",
    "distance": 1218.213236,
    "estimated_duration": {
      "begin": "20m0s",
      "end": "25m0s"
    },
    "location": {
      "lat": 51.510109,
      "lon": -0.093282
    },
    "name": "restaurant name",
    "display_name": "restaurant display name",
    "status": "available",
    "delivery_fee": {
      "currency_code": "GBP",
      "fractional": 350
    },
    "visible": true
  },
  {
    "id": "gcjv053teh3j-xYM7X3DCtlw",
    "distance": 2377.1997179077333,
    "estimated_duration": {
      "begin": "45m0s",
      "end": "45m0s"
    },
    "name": "Featured Arcu",
    "display_name": "A Friendly Name",
    "location": {
      "lat": 51.51522735141347,
      "lon": -3.141261871084153
    },
    "status": "closed",
    "delivery_fee": {
      "currency_code": "",
      "fractional": 0
    },
    "visible": true
  }
]

The value of delivery_fee consists of currency_code and fractional. If delivery fee cannot currently be retrieved for a site, the value of currency_code becomes "" (empty string) and the value of fractional becomes 0. This occurs, for example, for sites currently closed.

If the value of the visible flag is set to false, Deliveroo cannot currently deliver from this site.

Please note, that when the estimated duration exceeds one hour, fields in estimated_duration section (begin or end) will be prefixed with hour mark, as in the following example: 1h10m0s.

Quotes

A quote validates that a location is deliverable from a particular restaurant and provides the delivery fee and the estimated travel time. Postcode or lat/lon is required at a minimum, but using the customer address is preferable once it is available.

Create quote

Creating a quote is not required to place an order, but is recommended.

For example, if your server must push new orders to the restaurant point-of-sale system, creating a valid quote is sufficient to accept an order from a customer while waiting for acknowledgement of the order from the restaurant.

Once acknowledgement of the order is received from the restaurant point-of-sale, use the create order endpoint to request fulfillment.

Delivery destination can be specified in two alternative, mutually exclusive ways:

In test mode, create a test quote using a restaurant fixture with an available status returned from the /api/v1/fulfillment/restaurants endpoint.

HTTP request

POST /api/v1/fulfillment/quotes

Request parameters (by lat/lon)

Create quote by lat/lon request body example:

{
  "lat": 51.510109,
  "lon": -0.093282,
  "fulfillment_type": "delivery",
  "restaurant_id": "EgG27rbviS26itnuhLaHin"
}

Note that the lat/lon and address parameters are mutually exclusive.

Parameter Description
lat number
51.5101095 Delivery location latitude.
lon number
-0.0932817 Delivery location longitude.
restaurant_id string
EgG27rbviS26itnuhLaHin Restaurant ID.
fulfillment_type string (optional)
delivery / pickup Fulfillment type.

If a quote is created by supplying lat/lon, the same values should also be provided as address.lat/address.lon when creating the corresponding order. This can avoid potential order rejections due to a different lat/lon being derived from the full address information.

Request parameters (by address)

Create quote by address request body example:

{
  "address": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "postcode": "EC4R 3TE"
  },
  "fulfillment_type": "delivery",
  "restaurant_id": "EgG27rbviS26itnuhLaHin"
}

Note that the lat/lon and address parameters are mutually exclusive.

Parameter Description
address.country_code string
GB ISO Alpha-2 country code.
address.city string
London City.
address.postcode string (optional)
EC4R 3TE Postcode.
address.delivery_note string (optional)
Flat 5, Alexa Building. Buzzer is broken, please knock. Customer provided delivery note. (maximum is 160 characters)
address.line1 string
1 Cousin Lane Street address and number, company name, c/o.
address.line2 string (optional)
Peckham neighborhood.
restaurant_id string
EgG27rbviS26itnuhLaHin Restaurant ID.
fulfillment_type string (optional)
delivery / pickup Fulfillment type.

Response parameters

Create quote response body example:

{
  "id": "2dJicwfqtax8rYrPphAPEy",
  "created": "2019-06-04T18:18:19.454393Z",
  "delivery_fee": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "destination": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "lat": 51.510109,
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "lon": -0.093282,
    "postcode": "EC4R 3TE"
  },
  "estimated_duration": {
    "begin": "20m0s",
    "end": "25m0s"
  },
  "estimated_rider_arrival_time": "15m0s",
  "fulfillment_type": "delivery",
  "restaurant": {
    "id": "EgG27rbviS26itnuhLaHin",
    "name": "Restaurant name",
    "location": {
      "lat": 51.510109,
      "lon": -0.093282
    }
  },
  "valid_until": "2019-06-04T18:23:19.454393Z"
}

If a destination is out of range for our riders, you will receive an error with code undeliverable:

{
  "error": {
    "code": "undeliverable",
    "message": "the destination address is undeliverable"
  }
}

Please note, that when the estimated duration exceeds one hour, fields in estimated_duration section (begin or end) will be prefixed with hour mark, as in the following example: 1h10m0s.

Orders

Create order

Note: This endpoint will be deprecated in future. We recommend using create order v2 instead.

Create a new order for fulfillment by Deliveroo. A new order is returned with the status accepted.

For test mode usage, see create test order.

Example of a typical payload for placing an order, where a delivery quote is created first:

HTTP request

POST /api/v1/fulfillment/orders

Create order request body example:

{
  "id": "4K6CexdNbessmia4HDVewu9",
  "address": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "postcode": "EC4R 3TE"
  },
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will",
    "drinking_age_confirmed": true
  },
  "fulfillment_type": "delivery",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1,
      "contains_alcohol": true
    }
  ],
  "quote_id": "2dJicwfqtax8rYrPphAPEy",
  "restaurant_id": "EgG27rbviS26itnuhLaHin",
  "partner_fee_fractional": 400,
  "total_price_fractional": 1099
}

Request parameters

Parameter Description
id string (optional)
If provided, sets a case-sensitive order id (otherwise one will be generated for you). The identifier must consist of letters, numbers, dashes, and underscores only.
address.city string
London City.
address.country_code string
GB ISO Alpha-2 country code.
address.delivery_note string (optional)
Buzzer is broken, please knock. Customer provided delivery note. (maximum is 160 characters)
address.line1 string
1 Cousin Lane Street address, company name, c/o.
address.line2 string (optional)
1st Floor Apartment, suite, unit, building, floor, etc.
address.full string (optional)
Can be used in lieu of supplying line1/line2/postcode
address.postcode string (optional)
EC4R 3TE Postcode.
address.lat number (optional)
51.510109 Can be used to exactly specify the latitude of the delivery location. If supplied, address.lon must also be supplied.
address.lon number (optional)
-0.093282 Can be used to exactly specify the longitude of the delivery location. If supplied, address.lat must also be supplied.
customer.id string
1000 External unique customer identifier, used to correlate orders from the same person.
customer.email string (optional)
will@example.com Customer email address.
customer.first_name string
William Customer first name.
customer.last_name string
Shu Customer last name. Optional if first name passed.
customer.phone_number string
+442036999977 Customer phone number.
customer.preferred_name string (optional)
Will Customer preferred name used to greet the customer. First name will be used if omitted.
customer.drinking_age_confirmed boolean (required if the order item has contains_alcohol: true)
true Customer has confirmed they are able to show proof of age by valid ID to receive these items; otherwise they will not be delivered.
fulfillment_type string (optional)
delivery / pickup Fulfillment type, defaults to delivery if omitted. Note: pickup orders are not yet supported.
items.id string
y97n2Iwmciih9cHMhoTPzQ The external id for the menu item. This should match the identifier used by your POS system, so we can associate it to an item on your live menu.
items.description string
Burger The menu item name. Only used if we couldn't find a corresponding menu item on your live menu by the aforementioned ID.
items.modifiers string
[...] An array of modifiers to the current menu item.
items.modifiers.id string
-qqrSSp504GHyMoB3TM7ow The external id for the modifier. This should match the identifier used by your POS system, so we can associate it to an item on your live menu.
items.modifiers.description string
Well done The modifier name. Only used if we couldn't find a corresponding menu item on your live menu by the aforementioned ID.
items.modifiers.parent_id string (optional)
y97n2Iwmciih9cHMhoTPzQ The id of the item or modifier to which this modifier corresponds.
items.price_fractional number
599 The unit price of the item in the currency's smallest subunit (e.g. pence for GBP)
items.quantity string
1 The item's quantity.
items.contains_alcohol boolean (optional)
true Describes if the item contains alcohol.
quote_id string (optional)
2dJicwfqtax8rYrPphAPEy The id of a previously acquired quote.
restaurant_id string
EgG27rbviS26itnuhLaHin Restaurant ID.
partner_fee_fractional number (optional)
400 The price of all fees charged to the customer in the currency's smallest subunit (e.g. pence for GBP).
This information is required if Customer Support is managed by Deliveroo so customers can be accurately compensated.
total_price_fractional number
1099 The total order price in the currency's smallest subunit (e.g. pence for GBP)

Response parameters

Please note, that when the estimated duration exceeds one hour, fields in estimated_duration section (begin or end) will be prefixed with hour mark, as in the following example: 1h10m0s.

Create order response body example:

{
  "id": "4K6CexdNbessmia4HDVewu9",
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will"
  },
  "destination": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "lat": 51.510109,
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "lon": -0.093282,
    "postcode": "EC4R 3TE"
  },
  "estimated_duration": {
    "begin": "20m0s",
    "end": "25m0s"
  },
  "estimated_rider_arrival_time": "15m0s",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    }
  ],
  "prepare_for": "2019-06-04T18:18:19.454393Z",
  "restaurant": {
    "id": "EgG27rbviS26itnuhLaHin",
    "name": "Restaurant name",
    "location": {
      "lat": 51.510109,
      "lon": -0.093282
    }
  },
  "short_id": "1234",
  "status": "accepted",
  "status_logs": [
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "accepted"
    }
  ],
  "partner_fee": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "total_price": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "webview_url": "https://partner-support.deliveroo.com/webview/b4b76357-90b0-4775-918e-1d5d6a6e84ba",
  "webview_map_url": "https://partner-support.deliveroo.com/webview/b4b76357-90b0-4775-918e-1d5d6a6e84ba?mapOnly=true"
}

How does Deliveroo ensure the deliverability of an order?

In the same vein as in our core product, we utilise a geopoint and a restaurant's denoted delivery area to determine whether or not an order is deliverable. A small example:

Foo's burger joint is located in Bermondsey. Bermondsey is configured to have a 500 meter delivery radius.

Foo's burger joint has received an order located 520 meters away from the delivery radius's centre.

Foo's burger joint can deliver this order because its own configurable range delta in meters is of 100 meters.

NOTE If an API user believes an order that was rejected and is located at a bound should've been accepted, then a request to update the configurable range delta must be placed against Deliveroo's team to make the change.

Create order v2

Supports idempotency.

Create a new order for fulfillment by Deliveroo. A new order is returned with the status accepted.

For test mode usage, see create test order.

Example of a typical payload for placing an order, where a delivery quote is created first:

HTTP request

POST /api/v2/fulfillment/orders

Create order v2 request body example:

{
  "address": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "postcode": "EC4R 3TE"
  },
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will",
    "drinking_age_confirmed": true
  },
  "fulfillment_type": "delivery",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1,
      "contains_alcohol": true
    }
  ],
  "quote_id": "2dJicwfqtax8rYrPphAPEy",
  "restaurant_id": "EgG27rbviS26itnuhLaHin",
  "partner_fee_fractional": 400,
  "total_price_fractional": 1099
}

Request parameters

Parameter Description
address.city string
London City.
address.country_code string
GB ISO Alpha-2 country code.
address.delivery_note string (optional)
Buzzer is broken, please knock. Customer provided delivery note. (maximum is 160 characters)
address.line1 string
1 Cousin Lane Street address, company name, c/o.
address.line2 string (optional)
1st Floor Apartment, suite, unit, building, floor, etc.
address.full string (optional)
Can be used in lieu of supplying line1/line2/postcode
address.postcode string (optional)
EC4R 3TE Postcode.
address.lat number (optional)
51.510109 Can be used to exactly specify the latitude of the delivery location. If supplied, address.lon must also be supplied.
address.lon number (optional)
-0.093282 Can be used to exactly specify the longitude of the delivery location. If supplied, address.lat must also be supplied.
customer.id string
1000 External unique customer identifier, used to correlate orders from the same person.
customer.email string (optional)
will@example.com Customer email address.
customer.first_name string
William Customer first name.
customer.last_name string
Shu Customer last name. Optional if first name passed.
customer.phone_number string
+442036999977 Customer phone number.
customer.preferred_name string (optional)
Will Customer preferred name used to greet the customer. First name will be used if omitted.
customer.drinking_age_confirmed boolean (required if the order item has contains_alcohol: true)
true Customer has confirmed they are able to show proof of age by valid ID to receive these items; otherwise they will not be delivered.
fulfillment_type string (optional)
delivery / pickup Fulfillment type, defaults to delivery if omitted. Note: pickup orders are not yet supported.
items.id string
y97n2Iwmciih9cHMhoTPzQ The external id for the menu item. This should match the identifier used by your POS system, so we can associate it to an item on your live menu.
items.description string
Burger The menu item name. Only used if we couldn't find a corresponding menu item on your live menu by the aforementioned ID.
items.modifiers string
[...] An array of modifiers to the current menu item.
items.modifiers.id string
-qqrSSp504GHyMoB3TM7ow The external id for the modifier. This should match the identifier used by your POS system, so we can associate it to an item on your live menu.
items.modifiers.description string
Well done The modifier name. Only used if we couldn't find a corresponding menu item on your live menu by the aforementioned ID.
items.modifiers.parent_id string (optional)
y97n2Iwmciih9cHMhoTPzQ The id of the item or modifier to which this modifier corresponds.
items.price_fractional number
599 The unit price of the item in the currency's smallest subunit (e.g. pence for GBP)
items.quantity string
1 The item's quantity.
items.contains_alcohol boolean (optional)
true Describes if the item contains alcohol.
quote_id string (optional)
2dJicwfqtax8rYrPphAPEy The id of a previously acquired quote.
restaurant_id string
EgG27rbviS26itnuhLaHin Restaurant ID.
partner_fee_fractional number (optional)
400 The price of all fees charged to the customer in the currency's smallest subunit (e.g. pence for GBP).
This information is required if Customer Support is managed by Deliveroo so customers can be accurately compensated.
total_price_fractional number
1099 The total order price in the currency's smallest subunit (e.g. pence for GBP)

Response parameters

Please note, that when the estimated duration exceeds one hour, fields in estimated_duration section (begin or end) will be prefixed with hour mark, as in the following example: 1h10m0s.

Create order v2 response body example:

{
  "id": "gb:4ed842b5-051b-4bb9-9d32-041bc61f9205",
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will"
  },
  "destination": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "lat": 51.510109,
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "lon": -0.093282,
    "postcode": "EC4R 3TE"
  },
  "estimated_duration": {
    "begin": "20m0s",
    "end": "25m0s"
  },
  "estimated_rider_arrival_time": "15m0s",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    }
  ],
  "prepare_for": "2019-06-04T18:18:19.454393Z",
  "restaurant": {
    "id": "EgG27rbviS26itnuhLaHin",
    "name": "Restaurant name",
    "location": {
      "lat": 51.510109,
      "lon": -0.093282
    }
  },
  "short_id": "1234",
  "status": "accepted",
  "status_logs": [
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "accepted"
    }
  ],
  "partner_fee": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "total_price": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "webview_url": "https://partner-support.deliveroo.com/webview/b4b76357-90b0-4775-918e-1d5d6a6e84ba",
  "webview_map_url": "https://partner-support.deliveroo.com/webview/b4b76357-90b0-4775-918e-1d5d6a6e84ba?mapOnly=true"
}

Create pickup order

Note that pickup orders and the fulfillment_type attribute aren't supported yet, but will be available in the near future.

Create a new order for customer pickup.

Generally, a healthy pickup order lifecycle has the following status changes: placed => accepted => picked-up.

The following status changes are sent to the status_url for pickup orders:

Status Description
placed The order was created.
accepted The restaurant confirmed the order.
picked-up The customer picked-up the order.

The following status changes are sent to the refund_url only:

Refund Status Description
canceled A terminal status for when an order is canceled.

If you are a configured to receive orders from Deliveroo to your point-of-sale, a new pickup order is returned with status placed. If your server is handling sending orders to the restaurant point-of-sale, a new pickup order is returned with the status accepted.

Example of a typical payload for placing a pickup order, note the fulfillment_type attribute is pickup:

HTTP request

POST /api/v1/fulfillment/orders

Create pickup order request body example:

{
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will"
  },
  "fulfillment_type": "pickup",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    }
  ],
  "quote_id": "2dJicwfqtax8rYrPphAPEy",
  "restaurant_id": "EgG27rbviS26itnuhLaHin",
  "total_price_fractional": 1099
}

Response parameters

Please note, that when the estimated duration exceeds one hour, fields in estimated_duration section (begin or end) will be prefixed with hour mark, as in the following example: 1h10m0s.

Create pickup order response body example:

{
  "id": "4K6CexdNbessmia4HDVewu9",
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will"
  },
  "delivery_fee": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "estimated_duration": {
    "begin": "20m0s",
    "end": "25m0s"
  },
  "fulfillment_type": "pickup",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    }
  ],
  "prepare_for": "2019-06-04T18:18:19.454393Z",
  "restaurant": {
    "id": "EgG27rbviS26itnuhLaHin",
    "name": "Restaurant name",
    "location": {
      "lat": 51.510109,
      "lon": -0.093282
    }
  },
  "short_id": "1234",
  "status": "accepted",
  "status_log": [
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "accepted"
    }
  ],
  "total_price": {
    "currency_code": "GBP",
    "fractional": 400
  }
}

Create test order

Create a new test order by using your test credentials. In test mode, the server will perform webhook callbacks based on the durations provided in the scheduled_webhook_events object.

The following limitations compared to create order:

Note that not providing scheduled_webhook_events will create an order reaching terminal status immediately. It won't be possible to track the location of such an order.

When supplying scheduled_webhook_events, make sure to set the value of delivered far enough into the future to allow to track the location of the order by subsequent requests. Also, some events, such as canceled or rejected will terminate the order and prevent location tracking.

HTTP request

POST /api/v1/fulfillment/orders

Create order request body example:

{
  "address": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "postcode": "EC4R 3TE"
  },
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will"
  },
  "fulfillment_type": "delivery",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    }
  ],
  "quote_id": "2dJicwfqtax8rYrPphAPEy",
  "restaurant_id": "EgG27rbviS26itnuhLaHin",
  "scheduled_webhook_events": [
    {"status": "accepted", "delay": "1s"},
    {"status": "rider_arrived", "delay": "2s"},
    {"status": "rider_assigned", "delay": "3s"},
    {"status": "rider_unassigned", "delay": "4s"},
    {"status": "rider_assigned", "delay": "5s"},
    {"status": "rider_in_transit", "delay": "6s"},
    {"status": "rider_nearby", "delay": "7s"},
    {"status": "rejected", "delay": "8s"},
    {"status": "undeliverable", "delay": "8s"},
    {"status": "delivered", "delay": "8s"},
    {"status": "canceled", "delay": "8s"}
  ]
}

When creating an order in test mode, set the value of delivered far enough into the future, to be able to track the location of the order later. Also note that specifying values for rejected, undeliverable and canceled will terminate the order eventually. An order that has reached terminal status can no longer be tracked. Note that the rider_status webhook will only be triggered, if any rider_* event has been scheduled and the rider_status_url parameter is set. It is possible to schedule webhook events not containing any rider_* events. In this case, the rider_status webhook will never fire, while other webhooks will get triggered as usual. When first assigning a rider with rider_assigned and then unassigning the rider with rider_unassigned, a new rider will be assigned to the order automatically. All rider assignments and rider unassignment will surface in subsequent rider_status webhook callbacks.

{
  "scheduled_webhook_events": [
    {"status": "accepted", "delay": "1s"},
    {"status": "rider_arrived", "delay": "2s"},
    {"status": "rider_assigned", "delay": "3s"},
    {"status": "rider_unassigned", "delay": "4s"},
    {"status": "rider_assigned", "delay": "5s"},
    {"status": "rider_in_transit", "delay": "6s"},
    {"status": "rider_nearby", "delay": "7s"}
  ]
}

Get order location

Get the current order location. This endpoint returns the current location of the order's delivery rider along with their name and contact numbers, if available.

You can use this endpoint to render tracking maps for customers or an approximate progress bar based on travel distance remaining. If the location isn't available, the order may not have a delivery rider yet. The best time to begin using this endpoint is after you've received a rider_assigned order status webhook callback. Riders can be subject to change after assignment, for this reason contact information should only be passed to the customer after the order has been collected. If another rider is assigned a new rider_assigned status will be sent via webhook callback, use this endpoint to call for new rider contact information.

The location data does not update more than every minute, so it's unnecessary to poll more frequently. It will stop providing location data once any terminal order status is reached (delivered, undeliverable, canceled).

In test mode, for a location to be returned, sensible values must be specified for test_webhooks, to assure that the order does not reach terminal status before querying its location. In particular, specify a duration long enough for delivered.

This endpoint can also be used to retrieve rider's information. Their full name and contact number will always be filled in the response. However, as riders can have their personal phone numbers protected (masked), a temporary phone number and code will be assigned to rider_bridge_number and rider_bridge_code fields. In this case, rider_contact_number field will be formatted as rider_bridge_number (rider_bridge_code). When rider's phone is unmasked, rider_bridge_number and rider_bridge_code will be null.

Test orders return a random location with 2km of the test restaurant.

Note that if the location isn't available, the endpoint will return HTTP 200 with an empty JSON object. If this happens in test mode, the order may have reached a terminal status. Make sure to specify sensible values for test_webhooks, in particular for delivered.

HTTP request

GET /api/v1/fulfillment/orders/{id}/location

URI Parameters

Parameter Description
id string
4K6CexdNbessmia4HDVewu9 Order unique identifier.

Get order location response body example. In test mode, phone will always be masked, see next example.

{
  "accuracy_in_meters": 16,
  "at": "2019-06-04T18:18:19.454393Z",
  "delivery_eta": {
    "lower": "2021-10-26T13:15:00Z",
    "upper": "2021-10-26T13:10:00Z"
  },
  "lat": 51.510109,
  "lon": -0.093282,
  "rider_full_name": "Rider Name",
  "rider_contact_number": "441234567",
  "rider_bridge_code": null,
  "rider_bridge_number": null,
  "stacked_with": [
    "tAke4r1VSjil2BMTLi3MeQ"
  ],
  "delivery_priority": [
    "tAke4r1VSjil2BMTLi3MeQ",
    "y97n2Iwmciih9cHMhoTPzQ"
  ]
}

Get order location returning masked phone in the response body example. In test mode, phone will always be masked.

{
  "accuracy_in_meters": 16,
  "at": "2019-06-04T18:18:19.454393Z",
  "delivery_eta": {
    "lower": "2021-10-26T13:15:00Z",
    "upper": "2021-10-26T13:10:00Z"
  },
  "lat": 51.510109,
  "lon": -0.093282,
  "rider_full_name": "Rider Name",
  "rider_contact_number": "98765432 (123)",
  "rider_bridge_code": "98765432",
  "rider_bridge_number": "123",
  "stacked_with": [
    "tAke4r1VSjil2BMTLi3MeQ"
  ],
  "delivery_priority": [
    "tAke4r1VSjil2BMTLi3MeQ",
    "y97n2Iwmciih9cHMhoTPzQ"
  ]
}

Get order location when unavailable response body example. In test mode, this may happen if the order has reached terminal status. Increase timeouts in the test_webhooks supplied when posting the order.

{}

Get order location v2

This API supports an alternative endpoint that provides more detailed information about the riders that are assigned to a given order. The main differences when compared to the previous version is the fact that this endpoint supports multiple riders as well as a status_log array containing the events that occurred for each rider. It is important to note that when rider anonymisation setting is enabled for the partner, rider's name will have Deliveroo Rider as a fixed value.

HTTP request

GET /api/v2/fulfillment/orders/{id}/location

URI Parameters

Parameter Description
id string
Order unique identifier.

Response parameters

Get order location v2 response body example:

{
  "stacked_with":[
    "tAke4r1VSjil2BMTLi3MeQ"
  ],
  "delivery_eta":{
    "lower":"2021-10-26T13:15:00Z",
    "upper":"2021-10-26T13:10:00Z"
  },
  "riders":[
    {
      "full_name":"Mary A.",
      "contact_number":"4400123456 (7890123)",
      "bridge_code":"7890123",
      "bridge_number":"4400123456",
      "accuracy_in_meters":200,
      "lat":51.4606780787024,
      "lon":0.0274540382576987,
      "at":"2021-07-05T12:55:26Z",
      "estimated_arrival_time":"2021-07-05T13:18:10Z",
      "status_log":[
        {
          "status":"rider_assigned",
          "at":"2021-07-05T12:45:39.649Z"
        },
        {
          "status":"rider_unassigned",
          "at":"2021-07-05T12:55:08.573Z"
        }
      ]
    },
    {
      "full_name":"John T.",
      "contact_number":"442039605334 (875285953)",
      "bridge_code":"875285953",
      "bridge_number":"442039605334",
      "accuracy_in_meters":200,
      "lat":51.4606780787024,
      "lon":0.0274540382576987,
      "at":"2021-07-05T12:55:26Z",
      "estimated_arrival_time":"2021-07-05T13:17:10Z",
      "status_log":[
        {
          "status":"rider_assigned",
          "at":"2021-07-05T12:55:05.649Z"
        },
        {
          "status":"rider_arrived",
          "at":"2021-07-05T12:55:08.573Z"
        },
        {
          "status":"rider_in_transit",
          "at":"2021-07-05T12:57:15.221Z"
        },
        {
          "status":"rider_nearby",
          "at":"2021-07-05T12:58:20.591Z"
        }
      ]
    }
  ]
}
Parameter Description
order_id string
Order's unique identification.
stacked_with array
Array containing unique ids of orders stacked with this order.
delivery_priority array
Array containing unique ids of orders sorted by their delivery priority.
delivery_eta object
Delivery ETA object.
delivery_eta.lower string
Lower time bound when order will be delivered.
delivery_eta.upper string
Upper time bound when order will be delivered.
riders array
Array containing one or more rider objects.
rider object
Rider object.
rider.estimated_arrival_time string
Estimated time when the rider will arrive at the restaurant.
rider.at string
When rider's information was updated.
rider.lat float
Rider's location latitude.
rider.lon float
Rider's location longitude.
rider.accuracy_in_meters int
Rider's location accuracy in meters.
rider.full_name int
Rider's full name or Deliveroo Rider when rider anonymisation is enabled.
rider.contact_number int
Rider's phone number.
rider.bridge_number string
As riders can have their personal phone numbers protected (masked), a temporary phone number and code will be assigned to bridge number.
rider.bridge_code string
When rider's have their phone number masked, this value should be used when calling their temporary phone number.
rider.status_log array
Array containing one or more status_log object.
status_log.at string
Timestamp when the given event occurred in RFC3339 format.
status_log.status string
Can be either rider_assigned, rider_arrived, rider_in_transit, rider_nearby or rider_unassigned.
Rider Status Description
rider_assigned Rider was assigned to the order.
rider_unassigned Rider was unassigned to the order.
rider_arrived Rider nearby to the restaurant.
rider_confirmed_at_restaurant Rider arrival at the restaurant confirmed on rider's app.
rider_in_transit Rider en route to the customer.
rider_nearby Rider is arriving at customer.

Get order

Get information about an order.

HTTP request

GET /api/v1/fulfillment/orders/{id}

URI Parameters

Parameter Description
id string
Order unique identifier.

Response parameters

Please note, that when the estimated duration exceeds one hour, fields in estimated_duration section (begin or end) will be prefixed with hour mark, as in the following example: 1h10m0s.

delivered_place is an optional parameter, and it will be passed only when rider had problems delivering the order. The description field of delivered_place will take one of these values: CONCIERGE, RECEPTION, NEIGHBOUR, DOORSTEP, FRONT_GARDEN, OTHER, UNDELIVERED.

Get order response body example:

{
  "id": "4K6CexdNbessmia4HDVewu9",
  "created": "2021-11-04T16:30:52.487207Z",
  "customer": {
    "id": "1000",
    "first_name": "William",
    "last_name": "Shu",
    "phone_number": "+442036999977",
    "preferred_name": "Will"
  },
  "delivered_place": {
    "description": "UNDELIVERED",
    "note": "I tried to contact the client.  I'm not finding the place and she's not answering."
  },
  "delivery_fee": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "destination": {
    "city": "London",
    "country_code": "GB",
    "delivery_note": "Buzzer is broken, please knock.",
    "door_code": "#0000",
    "lat": 51.510109,
    "line1": "1 Cousin Lane",
    "line2": "1st Floor",
    "lon": -0.093282,
    "postcode": "EC4R 3TE"
  },
  "estimated_duration": {
    "begin": "20m0s",
    "end": "25m0s"
  },
  "estimated_rider_arrival_time": "15m0s",
  "fulfillment_type": "delivery",
  "items": [
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    },
    {
      "id": "y97n2Iwmciih9cHMhoTPzQ",
      "description": "Burger",
      "modifiers": [
        {
          "id": "-qqrSSp504GHyMoB3TM7ow",
          "description": "Well done",
          "parent_id": "y97n2Iwmciih9cHMhoTPzQ"
        }
      ],
      "price_fractional": 599,
      "quantity": 1
    }
  ],
  "prepare_for": "Hello, world!",
  "restaurant": {
    "id": "EgG27rbviS26itnuhLaHin",
    "name": "Restaurant name",
    "location": {
      "lat": 51.510109,
      "lon": -0.093282
    }
  },
  "short_id": "1234",
  "status": "accepted",
  "status_log": [
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "accepted"
    }
  ],
  "stacked_with": [
    "tAke4r1VSjil2BMTLi3MeQ"
  ],
  "delivery_priority": [
    "tAke4r1VSjil2BMTLi3MeQ",
    "y97n2Iwmciih9cHMhoTPzQ"
  ],
  "total_price": {
    "currency_code": "GBP",
    "fractional": 400
  },
  "webview_url": "https://partner-support.deliveroo.com/webview/b4b76357-90b0-4775-918e-1d5d6a6e84ba",
  "webview_map_url": "https://partner-support.deliveroo.com/webview/b4b76357-90b0-4775-918e-1d5d6a6e84ba?mapOnly=true"
}

Webhook callbacks

We provide webhook callbacks for the order's lifecycle as well as rider's status so that partners can provide customers with realtime information about the arrival of their order.

Generally, a healthy order lifecycle has the following status changes: placed => accepted => rider_assigned => rider_arrived => rider_in_transit => rider_nearby => delivered.

Keep in mind that while every attempt is made to make callbacks in the order they occurred and in a timely manner, neither can be absolutely guaranteed. It is also possible to receive the same callback more than once.

The following status changes are sent to the status_url:

Status Description
placed The order was created.
accepted The restaurant confirmed the order.
rider_assigned A rider is assigned to the order.
rider_arrived The rider arrived at the restaurant.
rider_in_transit The rider picked up the order and is en route to the delivery address.
rider_nearby Rider is arriving at customer.
delivered A terminal status for a successfully delivered order.

The following status changes are sent to the refund_url only:

Order Status Description
canceled A terminal status for when an order is canceled.
rejected A terminal status for when an order is rejected.
undeliverable A terminal status for when the rider is unable to deliver an order.

If an order reaches a terminal status, the customer should be refunded the full amount.

Customers can request compensation by calling Deliveroo if the order did not meet their expectations and they will be provided with compensation if the claims are valid.

A customer may be entitled to a partial or full refund, if Deliveroo support approves a compensation claim, you will be notified through the refund_url for this action and we will provide you with the approved refund_amount and reason so that you can process the customer's compensation.

Customers may be provided with an option to accept credit instead of a refund. If that is the case, we will notify you for this action via the credit_url and we will provide you with the approved credit_amount and reason so that you can process a customer's compensation of your choice, for example a voucher.

An alternative option to credit or refund that customers may choose, is the option to receive a redelivery which may include all or specific items from the original order. If that is the case, we will generate a new order internally and notify you via the redelivery_url where we would expect your response on whether you wish to accept or reject this order. Following your response, the order status will update accordingly and you will receive further updates like you would receive them on a normal order via the status_url.

Authentication

Upon registration, your account manager will provide you with a webhook-secret. This distinct from your api-secret that is used in API calls.

For every webhook request, this webhook secret and a sequential globally unique identifier (GUID) are used to generate a Hash-based message authentication code (HMAC) of the request payload. This GUID and generated HMAC are set as X-Deliveroo-Sequence-Guid and X-Deliveroo-Hmac-Sha256 headers respectively on the webhook request. When you receive a webhook request, you should use these headers to compute a digest and verify that it’s a genuine, authorized request sent from Deliveroo.

Example webhook request headers:

X-Deliveroo-Sequence-Guid: 16c3ec58343
X-Deliveroo-Hmac-Sha256: 2bf0ade9f5c33b266a8be1287d5af41864bc3a77ee9c53c75af979abc9a79b9e

Example to generate HMAC:

package main

import (
  "crypto/hmac"
  "crypto/sha256"
  "fmt"
)

func main() {
  webhook_secret := []byte("webhook-secret")
  sequence_guid := "deliveroo-sequence-guid" // from request header
  payload := "our-payload" // from request body

  mac := hmac.New(sha256.New, webhook_secret)
  message := fmt.Sprintf("%s %s", sequence_guid, payload)
  mac.Write([]byte(message))
  expected := mac.Sum(nil)

  fmt.Printf("%x", expected)
}
require "openssl"

webhook_secret = "webhook-secret"
sequence_guid = "deliveroo-sequence-guid" # from request header
payload = "our-payload" # from request body

digest = OpenSSL::Digest.new('sha256')
message = "#{sequence_guid} #{payload}"
expected = OpenSSL::HMAC.hexdigest(digest, webhook_secret, message)

puts expected

Delivery failure and retries

A successful webhook callback occurs when the server responds with an HTTP 2xx success range; any other HTTP status or a timeout will result in a retry.

Our server will continually retry failed webhook callbacks with exponential back-off per event and circuit breaking when failures are successive in a short amount of time.

When the circuit breaker is tripped, the total number of requests per minute is significantly reduced until the endpoint appears healthy again.

For order statuses, we "give up" and discard the event callback after 30 minutes.

For refund and credit requests, we "give up" and discard the event after 10 hours.

Order status callback

This webhook is called when an order changes status.

HTTP request

POST https://partner-server.com/partner-order-status-webhook

Response parameters

delivered_place is an optional parameter, and it will be passed only when rider had problems delivering the order. The description field of delivered_place will take one of these values: CONCIERGE, RECEPTION, NEIGHBOUR, DOORSTEP, FRONT_GARDEN, OTHER, UNDELIVERED.

The webhook callback JSON is structured like this:

{
  "order_id": "4K6CexdNbessmia4HDVewu9",
  "restaurant_brand_id": "38763b54-dfe0-4cb7-906c-54f2fbb2f273",
  "status": "delivered",
  "delivered_place": {
    "description": "UNDELIVERED",
    "note": "I tried to contact the client.  I'm not finding the place and she's not answering."
  },
  "status_log": [
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "accepted"
    },
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "rider_in_transit"
    },
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "delivered"
    }
  ]
}

Order refund callback

This webhook is called when an order has reached a terminal state or the customer has requested a refund as a form of compensation.

HTTP request

POST https://partner-server.com/partner-order-refund-webhook

Response parameters

delivered_place is an optional parameter, and it will be passed only when rider had problems delivering the order. The description field of delivered_place will take one of these values: CONCIERGE, RECEPTION, NEIGHBOUR, DOORSTEP, FRONT_GARDEN, OTHER, UNDELIVERED.

The webhook callback JSON is structured like this for a terminal order status:

{
  "order_id": "4K6CexdNbessmia4HDVewu9",
  "customer_id": "7c779a04-6fa2-11eb-9439-0242ac130002",
  "restaurant_id": "12345",
  "restaurant_brand_id": "38763b54-dfe0-4cb7-906c-54f2fbb2f273",
  "reason": "Customer requested cancellation",
  "status": "canceled",
  "refund_amount": {
    "fractional": 1234,
    "currency_code": "GBP"
  },
  "status_log": [
    {
      "at": "2019-06-04T18:18:19.454393Z",
      "status": "accepted"
    }
  ]
}

The webhook callback JSON is structured like this for a refund request:

{
  "order_id": "DN1cOmXoRrCSBZa84P5V-A",
  "restaurant_id": "12345",
  "restaurant_brand_id": "38763b54-dfe0-4cb7-906c-54f2fbb2f273",
  "customer_id": "65361",
  "reason": "Auto-generated ( Agent Name )\n\nIssue:\nMissing items\n\nAffected items:\n  Meal Deal for Two - £22.90\n    Affected modifiers for this item:\n      Chili Sauce - £0.00\n      NEW! General Tso's Chicken - £0.00\n      Crispy Chicken Bao - £0.00\n      NEW! General Tso's Chicken - £0.00\n      Claypot Aubergine Bao (Vg) - £0.00\n\nSelected resolution:\nRefund - £22.90\n\nNote:\n full refund",
  "status": "delivered",
  "delivered_place": {
    "description": "RECEPTION",
    "note": "I tried to contact the client, she's not answering."
  },
  "refund_amount": {
    "currency_code": "GBP",
    "fractional": 2290
  },
  "status_log": [
    {
      "at": "2021-02-05T16:17:38.845429997Z",
      "status": "placed"
    },
    {
      "at": "2021-02-05T16:17:57.831Z",
      "status": "delivered"
    }
  ]
}

Order credit callback

This webhook is called when a customer has requested credit as a form of compensation.

HTTP request

POST https://partner-server.com/partner-order-credit-webhook

Response parameters

delivered_place is an optional parameter, and it will be passed only when rider had problems delivering the order. The description field of delivered_place will take one of these values: CONCIERGE, RECEPTION, NEIGHBOUR, DOORSTEP, FRONT_GARDEN, OTHER, UNDELIVERED.

The webhook callback JSON is structured like this:

{
  "order_id": "XkKEJWOsQbSspsPp6srKzK",
  "restaurant_id": "12345",
  "restaurant_brand_id": "38763b54-dfe0-4cb7-906c-54f2fbb2f273",
  "customer_id": "654321",
  "reason": "incorrect_food",
  "status": "delivered",
  "delivered_place": {
    "description": "RECEPTION",
    "note": "I tried to contact the client, she's not answering."
  },
  "credit_amount": {
    "currency_code": "GBP",
    "fractional": 2364
  },
  "status_log": [
    {
      "at": "2021-02-05T16:06:29.43054125Z",
      "status": "placed"
    },
    {
      "at": "2021-02-05T16:06:48.515Z",
      "status": "delivered"
    }
  ]
}

Order redelivery callback

This webhook is called when a customer has requested redelivery as a form of compensation.

HTTP request

POST https://partner-server.com/partner-order-redelivery-webhook

The webhook callback JSON is structured like this:

{
  "parent_order_id": "pEfGNBE4Sb6FGpd7Fv8L8A",
  "new_order_id": "fhFidBvGQJefs49lGKfR4A",
  "short_id": "1234",
  "restaurant_id": "596",
  "restaurant_brand_id": "38763b54-dfe0-4cb7-906c-54f2fbb2f273",
  "customer_id": "33080005",
  "reason": "awol",
  "amount": {
    "currency_code": "GBP",
    "fractional": 1080
  },
  "prepare_for": "2021-03-26T16:03:22Z",
  "items": [
    {
      "description": "Single Mushroom Swiss Meal",
      "id": "HBV",
      "modifiers": [
        {
          "description": "Single Mushroom Swiss",
          "id": "LAO",
          "parent_id": "HBV",
          "price_fractional": 0
        },
        {
          "description": "Cheesy Fries (L) ",
          "id": "HHR",
          "parent_id": "HBV",
          "price_fractional": 80
        },
        {
          "description": "Tea",
          "id": "JAC",
          "parent_id": "HBV",
          "price_fractional": 0
        }
      ],
      "price_fractional": 800,
      "quantity": 1
    },
    {
      "description": "Onion Rings Large",
      "id": "HHI",
      "price_fractional": 380,
      "quantity": 1
    },
    {
      "description": "Cheesy Fries Large",
      "id": "HHP",
      "modifiers": [
        {
          "description": "Single Mushroom Swiss",
          "id": "LAO",
          "parent_id": "HHP",
          "price_fractional": 0
        }
      ],
      "price_fractional": 420,
      "quantity": 1
    }
  ]
}

HTTP expected webhook response body for accepting an order

{
  "decision": "accepted"
}

HTTP expected webhook response body for rejecting an order

{
  "decision": "rejected",
  "reason": "ingredient_unavailable"
}

Rider status webhook

We also provide webhook callbacks when a rider status is updated. It is important to notice that these webhooks will only be triggered when rider_status_url configuration entry is set.

Usually a regular rider status lifecycle is rider_assigned => rider_arrived (at the restaurant) => rider_in_transit (en route to customer) => rider_nearby.

The following are all the valid values for a rider status.

Rider Status Description
rider_assigned Rider was assigned to the order.
rider_unassigned Rider was unassigned to the order.
rider_arrived Rider nearby to the restaurant.
rider_confirmed_at_restaurant Rider arrival at the restaurant confirmed on rider's app.
rider_in_transit Rider en route to the customer.
rider_nearby Rider is arriving at customer.

Keep in mind that while every attempt is made to make callbacks in the order they occurred and in a timely manner, neither can be absolutely guaranteed. It is also possible to receive the same callback more than once.

The following status changes are sent to the rider_status_url:

Request parameters

Rider update status webhook request body example:

{
  "order_id": "w7ICBuVZRmOctXOwyUVdsQ",
  "restaurant_brand_id": "38763b54-dfe0-4cb7-906c-54f2fbb2f273",
  "stacked_with": [
    "tAke4r1VSjil2BMTLi3MeQ"
  ],
  "delivery_priority": [
    "tAke4r1VSjil2BMTLi3MeQ",
    "y97n2Iwmciih9cHMhoTPzQ"
  ],
  "delivery_eta": {
    "lower": "2021-10-26T13:15:00Z",
    "upper": "2021-10-26T13:10:00Z"
  },
  "riders": [
    {
      "estimated_arrival_time": "2021-06-30T22:35:10.197448096Z",
      "at": "2021-06-30T22:11:20.540915696Z",
      "accuracy_in_meters": 14,
      "lat": 51.4850045052611,
      "lon": -0.1742838066332262,
      "full_name": "Fast Food Euismod",
      "contact_number": "448496931925 ( 129355339 )",
      "bridge_code": "129355339",
      "bridge_number": "448496931925",
      "status_log": [
        {
          "at": "2021-06-30T22:11:10.197448493Z",
          "status": "rider_assigned"
        },
        {
          "at": "2021-06-30T22:11:20.525742664Z",
          "status": "rider_nearby"
        }
      ]
    }
  ]
}
Parameter Description
order_id string
Order unique identifier.
restaurant_brand_id string
Restaurant brand unique identifier.
stacked_with array
Array containing unique ids of orders stacked with this order.
delivery_priority array
Array containing unique ids of orders sorted by their delivery priority.
delivery_eta object
Delivery ETA object.
delivery_eta.lower string
Lower time bound when order will be delivered.
delivery_eta.upper string
Upper time bound when order will be delivered.
riders array
Array containing one or more rider objects.
rider object
Rider object.
rider.estimated_arrival_time string
Estimated time when the rider will arrive at the restaurant.
rider.at string
When rider's information was updated.
rider.lat float
Rider's location latitude.
rider.lon float
Rider's location longitude.
rider.accuracy_in_meters int
Rider's location accuracy in meters.
rider.full_name int
Rider's full name or Deliveroo Rider when rider anonymisation is enabled.
rider.contact_number int
Rider's phone number.
rider.bridge_number string
As riders can have their personal phone numbers protected (masked), a temporary phone number and code will be assigned to bridge number.
rider.bridge_code string
When rider's have their phone number masked, this value should be used when calling their temporary phone number.
rider.status_log array
Array containing one or more status_log object.
status_log.at string
Timestamp when the given event occurred in RFC3339 format.
status_log.status string
Can be either rider_assigned, rider_arrived, rider_in_transit, rider_nearby or rider_unassigned.

HTTP expected response

The webhook call expects a response on whether the order can be accepted or rejected. Please see below the valid reject reasons:

Reason Description
ingredient_unavailable The order contains items out of stock.
closing_early The branch is closing earlier than expected.
busy Impossible to prepare the order due to heavy workload.

Webhook configuration

It is possible to programmatically modify the webhook URLs configured for your account.

Get webhooks

Return a list of all currently registered webhooks.

HTTP request

GET /api/v1/fulfillment/webhooks

Get webhook configuration response body example:

{
  "refund_url": "https://example.com/order/refund",
  "credit_url": "https://example.com/order/credit",
  "redelivery_url": "https://example.com/order/redelivery",
  "status_url": "https://example.com/order/status",
  "rider_status_url": "https://example.com/order/rider_status"
}

Register webhook

If you do not wish to receive order status updates (and perhaps poll the order endpoint instead), you can omit the status_url.

HTTP request

POST /api/v1/fulfillment/webhooks

Register webhook configuration request body example:

{
  "refund_url": "https://example.com/order/refund",
  "credit_url": "https://example.com/order/credit",
  "redelivery_url": "https://example.com/order/redelivery",
  "status_url": "https://example.com/order/status",
  "rider_status_url": "https://example.com/order/rider_status"
}

Register webhook configuration response body example:

{
  "refund_url": "https://example.com/order/refund",
  "credit_url": "https://example.com/order/credit",
  "redelivery_url": "https://example.com/order/redelivery",
  "status_url": "https://example.com/order/status",
  "rider_status_url": "https://example.com/order/rider_status"
}

Release Notes

27 Jul 2022 - Updated error description for when there are no free riders.

25 July 2022 - Added display_name to get restaurants for location endpoint.

13 July 2022

11 May 2022 - Added rider anonymisation support.

9 May 2022 - Added service_unavailable error code. - Revised 503 HTTP error description to include high rider network load.

25 March 2022 - Added delivery_priority which contains the information about which order will be delivery first in a stacked order situation. - Get order location v1 - Get order location v2 - Riders status update webhook

23 February 2022

16 February 2022

28 January 2022

6 December 2021

4 November 2021

27 October 2021

13 October 2021

5 October 2021

27 September 2021

5 July 2021

4 June 2021

21 May 2021

25 Mar 2021

29 Jul 2020

28 Jul 2020

23 Jul 2020

20 Jul 2020

Data API

Introduction

Gain round-the-clock access to your Deliveroo order data and actionable insights to iterate and consistently improve your Deliveroo operations.

Our Data API allows you to:

Endpoints

Following are the list of endpoints currently available on API

Authentication to below endpoints is done by Basic Auth using the service key shared to the user. This needs to be submitted via Authentication header with value as base64 encoded username:password

username: user access key provided
password: empty

Orders report

Provided the user access key, as basic auth in authentication header, has access to configured branches, below endpoint generates orders report for either previous day or a given specific date.

Request

GET /report Returns orders report for previous day

GET /report?date={iso-8601-date-format} Returns orders report for given date. Date validation is done to make sure given date is in expected iso-8601 format (yyyy-MM-dd)

curl -X GET -u username:password -H "Content-Type: application/json" https://restaurant-data-api.deliveroo-data.net/report```

Reports can be fetched for specific branches by providing a branch_ids query parameter. branch_ids parameter is a comma separated list of branch ids

GET /report?branch_ids=111,222

Response Format

Below is the response format returned by the API.

{
    "data": {
        "report": [
            {
                "id": 1,
                "restaurant_id": "1",
                "restaurant_name": "restaurant name",
                ...
            },
            {
                "id": 2,
                "restaurant_id": "1",
                "restaurant_name": "restaurant name",
                ...
            }
        ]
    }
}

Full list of fields returned by the API:

    id
    restaurant_id
    restaurant_name
    restaurant_city
    restaurant_fulfillment_type
    status
    customer_reference
    rejection_reason
    contains_alcohol
    order_type
    scheduled_orders
    rating_stars
    rating_comment
    total_price {
        fractional
        currencyCode
    }
    subtotal_price {
        fractional
        currencyCode
    }
    tip {
        fractional
        currencyCode
    }
    surcharge {
        fractional
        currencyCode
    }
    fee {
        fractional
        currencyCode
    }
    commission {
        fractional
        currencyCode
    }
    vat_on_commission {
        fractional
        currencyCode
    }
    created_at
    placed_at
    accepted_by_restaurant_at
    confirmed_by_restaurant_at
    completion_target
    in_transit_at
    delivered_at
    rejected_at
    ready_for_pickup_at
    payment_status
    order_items
    restaurant_address
    cutlery_requested
    rider_wait_time
    branch_code
    uuid

Order items report

GET /report/items Returns order items report for previous day

GET /report/items?date={iso-8601-date-format} Returns order items report for given date. Date validation is done to make sure given date is in expected iso-8601 format (yyyy-MM-dd)

Reports can be fetched for specific branches by providing a branch_ids query parameter. branch_ids parameter is a comma separated list of branch ids GET /report/items?branch_ids=111,222

** Response Format **

Below is the response format returned by the API.

{
  "data": {
    "orderItems": [
      {
        "restaurant_name": "Benugo - Suren/Rider test",
        "top_items": "Prawn & Vegetable Tempura on Rice, Avocado Maki, Salmon Maki",
        "item": "Chilli Squid",
        "category": "Sides",
        ...
      }
    ]
  }
}

Full list of order item fields returned by the API:

    item
    category
    unit_price {
        fractional
        currencyCode
    }
    total_price {
        fractional
        currencyCode
    }
    quantity

Branch summary report

GET /report/summary Returns branch summary report for previous day

GET /report/summary?date={iso-8601-date-format} Returns branch summary report for given date. Date validation is done to make sure given date is in expected iso-8601 format (yyyy-MM-dd)

Reports can be fetched for specific branches by providing a branch_ids query parameter. branch_ids parameter is a comma separated list of branch ids GET /report/summary?branch_ids=111,222

Response Format

Below is the response format returned by the API.

{
    "data": {
        "branchSummary": {
            "top_items": "Hash Brown, Twister Meal",
            "restaurant_name": "Test Breakfast - Test Mall",
            "net_revenue_local": 935,
            "scheduled_active_hours": 5.69,
            "total_active_hours": 7.84,
            ...
        }
    }
}

Full list of branch summary fields returned by the API

    top_items
    restaurant_name
    total_accepted_orders
    total_cancelled_orders
    commission_without_vat
    commission_tax
    rejected_order_gmv
    net_revenue_local
    total_value_of_orders
    total_number_of_orders
    average_order_value
    average_user_experience_time
    average_time_to_accept
    scheduled_hours
    open_hours
    scheduled_active_hours
    open_active_hours
    total_active_hours

Response codes

200 - Successful report generation\ 400 - Validation failures, date parameter validation\ 420 - Rate limiting, tokens expiry / frequent report fetches 5xx - Service issues around unavailability or timeouts

Rate limiting

Access to API is throttled and rate limiting is done using token bucket approach. Where each user access key is allocated predefined set of tokens. A token is spent for every successfully downloaded report. If there are any errors in generating the report, token is unspent.

A scheduler is configured to top-up tokens into each user's bucket

Once the available tokens are spent, user's access to API is throttled. Access is also throttled by not allowing users to run frequent or parallel requests to pull reports when date parameter is specified. Users are forced to wait certain interval between subsequent requests.

Menu API

The Deliveroo Menu API enables you to upload and manage the menus on all your sites seamlessly without manual intervention. This ensures consumers always see the latest menu for your restaurant, as well as lets you innovate more quickly by trying new dishes, new pictures, and much more!

The Deliveroo Menu API consists of the following components

Item: An item is a single element that a user selects when browsing through one of your sites menus on Deliveroo. For example, an item could be a sandwich, a cheesecake, or a pizza

Modifiers: Modifiers are a variant option for a particular item on the menu. Modifiers present the option to let users customize their orders based on their preferences. For example, a modifier for a sandwich can be 'Extra Cheese', 'Gluten free bread', 'Mustard'.

Category: A category represents a logical grouping of items that make is easier for users to navigate your menu. For example, categories in your menus could be 'Appetizers', 'Mains', 'Desserts'. If you are running a promotion, you could also include a category called 'Specials', or 'Deal of the Day' as a category.

Menu: A menu groups together one or more categories to present a single complete view of your offerings to your users.

Please read our menu guidelines below to ensure your menu stands out in the best way.

An article with full guidelines on how to make your menu standout is available, below is an extract adapted and updated for API users.

Example menu on Deliveroo app

This should showcase your brand and encourage customers to visit your restaurant page.
Accepted formats: JPEG, PNG. At least 1920x1080 pixels, 16:9 aspect ratio.

This sits at the top of the menu page and explains what makes your restaurant different. We recommend telling the story of your brand and explaining why it was created.
Accepted formats: Up to 500 characters - ideally between 200-245 characters.

The titles of the sections of your menu. This should help customers easily navigate your menu and clearly understand each section.
Accepted formats: Between 3-120 characters.

It should explain why these set of items are grouped together as well as highlight the key ingredients and tastes associated with the category.
Accepted formats: Between 3-255 characters - ideally between 200-245 characters.

The titles of your dishes.
Accepted formats: 2-120 characters, ideally below 60 characters.

It should give the customer all the information they need to understand the dish, from ingredients to allergens.
Accepted formats: Up to 500 characters, but only the first 60 characters will be visible on screen on the menu page (the rest is visible when click on the item)

These will be photos of specific menu items. Customers will see these photos when they visit your restaurant page. Specific photos of each item on your menu makes it as easy as possible for customers to decide what to order.
Accepted formats: JPEG, PNG. 1920x1080 pixels 16:9 aspect ratio.

Help consumers with allergies by providing an up-to-date structure description of any allergens that may be present in your dishes.

The special code no_allergens means that the item has none of the known allergens on the list. In order to send "information unavailable" just provide an empty array.

Valid allergen values by country:

Country Valid allergens value
UK "no_allergens","celery", "crustaceans", "eggs", "fish", "gluten", "lupin", "milk", "molluscs", "mustard", "nuts", "peanuts", "sesame_seeds", "soybeans", "sulphur_dioxide_sulphites"

Help consumers with dietary information by providing an up-to-date description of any dietary category (or categories) a specific item complies with.

This information helps customers to easily identify the items that more closely match with their requirements

Currently supported dietary codes are:

"dairy_free" "gluten_free" "halal" "keto" "paleo" "plant_based" "vegan" "vegetarian"

For Deliveroo menus, both top-level menu items, and items that are only available as modifier choices can have calorie information attributed to them via a specific energy_kcal field (present on menu.items[].nutritional_info). This information will be displayed clearly and prominently at the ‘point of choice’ for the customer on Deliveroo menu pages.

From the energy_kcal field on the nutritional information object, we will only display the nutritional_info.energy_kcal.high field to customers, however this may change in the future.

In the case of mapping a single value, rather than a range, both nutritional_info.energy_kcal.high and nutritional_info.energy_kcal.low should be set to the same value.

To remove calorie information from an item, or signify that an Item does not have calorie information set nutritional_info.energy_kcal to null, when an Item is configured like this, no calorie value will be shown at all.

Additionally, setting the whole nutritional_info field to null will also have the same effect.

Scheduled menus allow you to set which categories of items should appear to customers on a schedule. In order to drive this experience, you’ll need to utilise the menu.mealtimes.schedule object within your menu payload (see sidebar).

 "schedule": [
          {
            "day_of_week": 0,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 1,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 2,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 3,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 4,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 5,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 6,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          }
        ]

A “hero” image is the image that customers see for your shop and menu page when browsing the consumer app. You can configure an image for each mealtime (i.e. an image url for each mealtime in your menu).

When multiple hero images are provided, customers will see a different image for your shop and menu page when browsing the consumer app depending on which mealtime is active.

Two options are available for configuring schedules. The options are detailed below.

The provided schedules must cover a 7D/24H period. This is to ensure that if customers are browsing a menu outside of opening hours, they still see a menu. Consider the following hours:

Customers browsing in the early hours in the morning (4-6AM) would see the breakfast menu. Users browsing outside of the opening hours of the store would still see the configured mealtime. If it is not possible to configure schedules for all days+hours of the week, partners should explore the option below.

A default mealtime is a mealtime without any schedules associated.Menu API - Scheduled Menus should be either null or an empty collection. This will be recognised as the “default” mealtime.

A default mealtime is one that shows when there are no other active mealtimes by schedule. Consider a single “breakfast” mealtime in addition to a default:

During the breakfast hours, the breakfast mealtime will be shown. Outside these hours, given no other mealtime is active, the default will be shown.

This gives partners the ability to only configure a single specific mealtime and use a fallback at all other times of the day without increased scheduling complexity.

Scheduled start and end times must not have the same start and end time, e.g. a mealtime ends at 10:29 and another starts at 10:30. The next mealtime must start at 10:30. Schedules must not overlap, a single mealtime may only be active at a given time. If using default mealtimes, only a single mealtime must be present. Schedules that do not meet the above requirements will cause the menu request to be rejected (400 - Bad Request).

Partners should avoid duplicating categories, items and modifiers across mealtimes. The correct usage is to use the same category in multiple mealtimes (if required), and items within multiple categories.

Do not create duplicate items and categories unless the items in the category differ, or some part of the item differs.

If the items are not unique by their name+price (excluding overrides), the menu request will be rejected (400 - Bad Request).

Examples:

The Get Menu API allows you to retrieve a menu created via the Upload Menu API. You can call this API to view the latest status of the menu uploaded in Deliveroo.

Note that menus created using the menu manager cannot be retrieved using this API currently. Only menus created via the Upload Menu API can be retrieved through this endpoint. If a menu for the menu id passed in the request does not exist this API will return an error response.

GET https://partners.deliveroo.com/api/v1/brands/:brand_id/menus/:id

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
id string
The unique identifier for the menu for the given "brand" context.

Get menu response body example:

{
  "name": "site-234 menu",
  "menu": {
    "mealtimes": [
      {
        "id": "breakfast-menu",
        "name": {
          "en": "Breakfast menu"
        },
        "description": {
          "en": "Best breakfast menu in town! Everything on the menu is freshly made at the start of the day."
        },
        "seo_description": {
          "en": "Best breakfast menu in town!"
        },
        "image": {
          "url": ""
        },
        "category_ids": [
          "breakfast-bundle", "porridge", "drinks"
        ]
      }
    ],
    "categories": [
      {
        "id": "porridge",
        "name": {
          "en": "Porridge 🥣"
        },
        "description": {
          "en": "Freshly made porridge"
        },
        "item_ids": ["porridge_blueberries", "porridge_banana"]
      },
      {
        "id": "drinks",
        "name": {
          "en": "Drinks ☕️"
        },
        "description": {},
        "item_ids": ["tea", "coffee", "orange_juice"]
      },
      {
        "id": "breakfast-bundle",
        "name": {
          "en": "Breakfast bundle 📦"
        },
        "description": {},
        "item_ids": ["breakfast-bundle"]
      }
    ],
    "items": [
      {
        "id": "porridge_blueberries",
        "name": {
          "en": "Porridge with blueberries"
        },
        "description": {
          "en": "Porridge with blueberries and cinnamon"
        },
        "price_info": {
          "price": 350,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "porridge_blueberries123",
        "ian": "4006381333931",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [
          "extra_toppings"
        ],
        "allergies": ["milk"],
        "nutritional_info": {
          "energy_kcal": {
            "low": 123,
            "high": 456
          },
          "hfss": false
        },
        "contains_alcohol": false
      },
      {
        "id": "porridge_banana",
        "name": {
          "en": "Porridge with bananas"
        },
        "operational_name": "porridge-ban",
        "description": {
          "en": "Porridge with bananas and cinnamon"
        },
        "price_info": {
          "price": 350,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "porridge_banana123",
        "ian": "4006381333932",
        "image": {},
        "is_eligible_as_replacement": false,
        "is_eligible_for_substitution": false,
        "tax_rate": 20.0,
        "modifier_ids": [
          "extra_toppings"
        ],
        "allergies": ["milk"],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "peanut_butter",
        "name": {
          "en": "Peanut butter"
        },
        "operational_name": "peanut-butter",
        "description": {
          "en": "Crunchy peanut butter"
        },
        "price_info": {
          "price": 100,
          "overrides": []
        },
        "plu": "peanut_butter_123",
        "ian": "4006381333933",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": false,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": ["peanuts"],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "granola",
        "name": {
          "en": "Granola"
        },
        "operational_name": "granola",
        "description": {
          "en": "Granola"
        },
        "price_info": {
          "price": 100,
          "overrides": []
        },
        "plu": "granola_123",
        "ian": "4006381333934",
        "image": {},
        "is_eligible_as_replacement": false,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "honey",
        "name": {
          "en": "Honey"
        },
        "operational_name": "honey",
        "description": {
          "en": "Honey"
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "honey_123",
        "ian": "4006381333935",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "tea",
        "name": {
          "en": "Tea"
        },
        "operational_name": "tea",
        "description": {},
        "price_info": {
          "price": 150,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "tea_$23",
        "ian": "4006381333936",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": ["choose_milk"],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "coffee",
        "name": {
          "en": "Coffee"
        },
        "operational_name": "coffee",
        "description": {},
        "price_info": {
          "price": 250,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "coffee_$78",
        "ian": "4006381333937",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": ["choose_milk"],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "no_milk",
        "name": {
          "en": "No milk"
        },
        "operational_name": "no-milk",
        "description": {
          "en": ""
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "no_milk_$49",
        "ian": "4006381333938",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "whole_milk",
        "name": {
          "en": "Whole milk"
        },
        "operational_name": "whole-milk",
        "description": {
          "en": ""
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "whole_milk_$39",
        "ian": "4006381333939",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "orange_juice",
        "name": {
          "en": "Orange juice"
        },
        "operational_name": "orange-juice",
        "description": {},
        "price_info": {
          "price": 250,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "orange_juice_$69",
        "ian": "4006381333940",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "breakfast-bundle",
        "name": {
          "en": "Breakfast bundle"
        },
        "description": {
          "en": "Porridge with a drink of your choice."
        },
        "price_info": {
          "price": 450,
          "overrides": []
        },
        "plu": "breakfast_bundle123",
        "ian": "4006381333941",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [
          "choose_your_porridge", "choose_your_drink"
        ],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      }
    ],
    "modifiers": [
      {
        "id": "extra_toppings",
        "name": {
          "en": "Choice of extra toppings 🍯"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 3,
        "repeatable": false,
        "item_ids": [
          "honey",
          "peanut_butter",
          "granola"
        ]
      },
      {
        "id": "choose_milk",
        "name": {
          "en": "Choose milk"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "no_milk",
          "whole_milk"
        ]
      },
      {
        "id": "choose_your_porridge",
        "name": {
          "en": "Choose your porridge"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "porridge_blueberries",
          "porridge_banana"
        ]
      },
      {
        "id": "choose_your_drink",
        "name": {
          "en": "Choose your drink"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "tea",
          "coffee",
          "orange_juice"
        ]
      }
    ]
  },
  "site_ids": ["site-234"]
}

Failed Get menu response body example:

{
  "error": {
    "message": "can't find requested live menu",
    "code": "not_found"
  }
}
Response Code Error Code
400 bad_request
404 not_found
500 500

With the Upload Menu API you can:

  1. Create a new menu in Deliveroo.
  2. Update an existing menu using the same menu id that was sent when the menu was created.
  3. Assign multiple sites to the same menu.

Use the Upload menu API if you wish to create menus or update existing menus to let users see the most updated status of your menus and offerings. Reduce the chances of poor customer experience due to orders being placed against an outdated menu by updating outdated menus in real time without any manual intervention.

PUT https://partners.deliveroo.com/api/v1/brands/:brand_id/menus/:id

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
id string
The unique identifier for the menu for the given "brand" context..

Put menu request body example:

{
  "name": "site-234 menu",
  "menu": {
    "mealtimes": [
      {
        "id": "breakfast-menu",
        "name": {
          "en": "Breakfast menu"
        },
        "description": {
          "en": "Best breakfast menu in town! Everything on the menu is freshly made at the start of the day."
        },
        "seo_description": {
          "en": "Best breakfast menu in town!"
        },
        "image": {
          "url": ""
        },
        "category_ids": [
          "breakfast-bundle", "porridge", "drinks"
        ],
        "schedule": [
          {
            "day_of_week": 0,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 1,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 2,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 3,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 4,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 5,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          },
          {
            "day_of_week": 6,
            "time_periods": [
              {
                "start": "00:00:00",
                "end": "10:29:00"
              }
            ]
          }
        ]
      }
    ],
    "categories": [
      {
        "id": "porridge",
        "name": {
          "en": "Porridge 🥣"
        },
        "description": {
          "en": "Freshly made porridge"
        },
        "item_ids": ["porridge_blueberries", "porridge_banana"]
      },
      {
        "id": "drinks",
        "name": {
          "en": "Drinks ☕️"
        },
        "description": {},
        "item_ids": ["tea", "coffee", "orange_juice"]
      },
      {
        "id": "breakfast-bundle",
        "name": {
          "en": "Breakfast bundle 📦"
        },
        "description": {},
        "item_ids": ["breakfast-bundle"]
      }
    ],
    "items": [
      {
        "id": "porridge_blueberries",
        "name": {
          "en": "Porridge with blueberries"
        },
        "description": {
          "en": "Porridge with blueberries and cinnamon"
        },
        "price_info": {
          "price": 350,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "porridge_blueberries123",
        "ian": "4006381333931",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [
          "extra_toppings"
        ],
        "allergies": ["milk"],
        "nutritional_info": {
          "energy_kcal": {
            "low": 123,
            "high": 456
          },
          "hfss": false
        },
        "contains_alcohol": false,
        "max_quantity": 2
      },
      {
        "id": "porridge_banana",
        "name": {
          "en": "Porridge with bananas"
        },
        "operational_name": "porridge-ban",
        "description": {
          "en": "Porridge with bananas and cinnamon"
        },
        "price_info": {
          "price": 350,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "porridge_banana123",
        "ian": "4006381333932",
        "image": {},
        "is_eligible_as_replacement": false,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [
          "extra_toppings"
        ],
        "allergies": ["milk"],
        "nutritional_info": {},
        "contains_alcohol": false,
        "max_quantity": 2
      },
      {
        "id": "peanut_butter",
        "name": {
          "en": "Peanut butter"
        },
        "operational_name": "peanut-butter",
        "description": {
          "en": "Crunchy peanut butter"
        },
        "price_info": {
          "price": 100,
          "overrides": []
        },
        "plu": "peanut_butter_123",
        "ian": "4006381333933",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": false,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": ["peanuts"],
        "nutritional_info": {},
        "contains_alcohol": false,
        "max_quantity": 2
      },
      {
        "id": "granola",
        "name": {
          "en": "Granola"
        },
        "operational_name": "granola",
        "description": {
          "en": "Granola"
        },
        "price_info": {
          "price": 100,
          "overrides": []
        },
        "plu": "granola_123",
        "ian": "4006381333934",
        "image": {},
        "is_eligible_as_replacement": false,
        "is_eligible_for_substitution": false,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false,
        "max_quantity": 2
      },
      {
        "id": "honey",
        "name": {
          "en": "Honey"
        },
        "operational_name": "honey",
        "description": {
          "en": "Honey"
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "honey_123",
        "ian": "4006381333935",
        "image": {},
        "is_eligible_as_replacement": false,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "tea",
        "name": {
          "en": "Tea"
        },
        "operational_name": "tea",
        "description": {},
        "price_info": {
          "price": 150,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "tea_$23",
        "ian": "4006381333936",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": ["choose_milk"],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false,
        "max_quantity": 4
      },
      {
        "id": "coffee",
        "name": {
          "en": "Coffee"
        },
        "operational_name": "coffee",
        "description": {},
        "price_info": {
          "price": 250,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "coffee_$78",
        "ian": "4006381333937",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": ["choose_milk"],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false,
        "max_quantity": 2
      },
      {
        "id": "no_milk",
        "name": {
          "en": "No milk"
        },
        "operational_name": "no-milk",
        "description": {
          "en": ""
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "no_milk_$49",
        "ian": "4006381333938",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false,
        "max_quantity": 2

      },
      {
        "id": "whole_milk",
        "name": {
          "en": "Whole milk"
        },
        "operational_name": "whole-milk",
        "description": {
          "en": ""
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "whole_milk_$39",
        "ian": "4006381333939",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "orange_juice",
        "name": {
          "en": "Orange juice"
        },
        "operational_name": "orange-juice",
        "description": {},
        "price_info": {
          "price": 250,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "orange_juice_$69",
        "ian": "4006381333940",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "breakfast-bundle",
        "name": {
          "en": "Breakfast bundle"
        },
        "description": {
          "en": "Porridge with a drink of your choice."
        },
        "price_info": {
          "price": 450,
          "overrides": []
        },
        "plu": "breakfast_bundle123",
        "ian": "4006381333941",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [
          "choose_your_porridge", "choose_your_drink"
        ],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      }
    ],
    "modifiers": [
      {
        "id": "extra_toppings",
        "name": {
          "en": "Choice of extra toppings 🍯"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 3,
        "repeatable": false,
        "item_ids": [
          "honey",
          "peanut_butter",
          "granola"
        ]
      },
      {
        "id": "choose_milk",
        "name": {
          "en": "Choose milk"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "no_milk",
          "whole_milk"
        ]
      },
      {
        "id": "choose_your_porridge",
        "name": {
          "en": "Choose your porridge"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "porridge_blueberries",
          "porridge_banana"
        ]
      },
      {
        "id": "choose_your_drink",
        "name": {
          "en": "Choose your drink"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "tea",
          "coffee",
          "orange_juice"
        ]
      }
    ]
  },
  "site_ids": ["site-234", "site-456"]
}
Parameter Description Required Type Length
menu Menu object Required object
menu.name Name of the menu Required object
menu.mealtimes List of mealtimes. A mealtime act as a wrapper around a group of categories enabling them to be displayed during specified time periods. Required Array of objects
menu.mealtimes.schedule Schedule describes the operational hours of the menu. See mealtime schedule Optional Array of objects 1-5
menu.mealtimes.schedule.day_of_week DayOfWeek is the day of the week on which these hours will be applied. Accepted values are 0 through 6, where 0 is Monday and 6 is Sunday. Required int 0-6
menu.mealtimes.schedule.time_periods TimePeriods are the time spans during which the menu is available. Required Array of objects
menu.mealtimes.schedule.time_periods.start Start time at which the menu becomes available, in 24-hour HH:MM format, e.g. “08:30”, “23:00”. The start time reflects an abstract date and time that is not tied to a specific time and place (for example, breakfast starts on weekdays at 9:00 A.M.). See schedule rules Required TimeOfDay
menu.mealtimes.schedule.time_periods.end End the time at which the menu ceases to be available, in 24-hour HH:MM format, e.g. “08:30”, “23:00”. Required TimeOfDay
menu.mealtimes.id Unique identifier for the mealtime. Required String 255
menu.mealtimes.name Translated name of the mealtime. Required Object 255
menu.mealtimes.description Translated description of the mealtime. You need to send the language code as supported in Deliveroo. For a list of supported languages and corresponding language codes, refer to the 'Language Codes section below'. Optional object
menu.mealtimes.image Object for mealtime images Required Object
menu.mealtimes.image.url URL for the image. See mealtime images
Accepted formats: JPEG, PNG, at least 1920x1080 pixels, 16:9 aspect ratio.
Required string
menu.mealtimes.category_ids IDs of the categories inside the mealtime. Required array of strings
menu.categories List of categories. There's a limit of 100 categories per menu. If you get over the limit, you'll get "the length must be between 1 and 100" request error. Required array of objects 1-100 categories
menu.categories.id Unique identifier for the category. Required String 255
menu.categories.name
Translated name of the category.
Required Object 3-120
menu.categories.description Translated description of the category. You need to send the language code as supported in Deliveroo. For a list of supported languages and corresponding language codes, refer to the 'Language Codes section below'. Optional object 255
menu.categories.item_ids IDs of the items inside the category. Required array of strings
menu.items List of items. There's a limit of 5000 items per menu. If you get over the limit, you'll get "the length must be between 1 and 5000" request error. Required array of objects 1-5000 items
menu.items.id Unique identifier for the item. Required String 255
menu.items.name Translated name of the item. Required Object 2-120
menu.items.description Translated description of the item. You need to send the language code as supported in Deliveroo. For a list of supported languages and corresponding language codes, refer to the 'Language Codes section below'. Optional Object 500
menu.items.operational_name Operational name the restaurant uses in-house for the item. Optional String 255
menu.items.price_info Price information for the item. Allows context specific overrides. Required Object
menu.items.price
Positive integer or zero Price in minor units of the currency, eg. pennies for GBP, or cents for EUR.
Required Number
menu.items.overrides Price overrides for the item in different contexts. Optional Array of objects
menu.items.overrides.type Type of the context where the price is overridden. Permitted values: ITEM, MODIFIER, PICKUP\_ITEM, PICKUP\_MODIFIER, Optional String
menu.items.overrides.id Unique identifier for the context. Optional String
menu.items.overrides.price Price in minor units of the currency, eg. pennies for GBP, or cents for EUR.
positive integer or zero
Optional Number
menu.items.plu PLU (price lookup code) for the item. This field is Mandatory if the menu linked to pos integrated site. Conditional Mandatory String 255
menu.items.ian IAN is the International Article Number provided by the partner. Optional String
menu.items.image Object containing the item images Optional Object
menu.items.image.url URL for the image. Accepted formats: JPEG, PNG, at least 1920x1080 pixels, 16:9 aspect ratio. Optional String
menu.items.is_eligible_as_replacement Describes whether this item can be used as replacement during a substitution (relevant to grocery partners only, default true) Optional Boolean
menu.items.is_eligible_for_substitution Describes whether this item can be substituted if it's out of stock (relevant to grocery partners only, default true) Optional Boolean
menu.items.tax_rate Tax rate percentage (from 0-100) for the item.
Accepted tax_rates by country:
AE: 0.0, 5.0
AU: 0.0, 10.0
BE: 0.0, 6.0, 12.0, 21.0
ES: 0.0, 4.0, 10.0, 21.0
FR: 0.0, 2.1, 5.5, 10.0, 20.0
HK: 0.0
IE: 0.0, 9.0, 13.5, 23.0
IT: 0.0, 4.0, 5.0, 10.0, 22.0
KW: 0.0
NL: 0.0, 9.0, 21.0
SG: 0.0, 7.0
TW: 0.0, 5.0
GB: 0.0, 5.0, 12.5, 20.0
QA: 0.0
Required Float
menu.items.modifier_ids Modifiers associated with the item. Optional Array of string
menu.items.allergies Item's allergy information. Permitted strings listed in the 'Item allergens' section above. Empty array means "allergy information unavailable. Optional Array of string
menu.items.diets Item's dietary information. Permitted strings listed in the 'Item dietary information' section above. Optional Array of string
menu.items.nutritional_info Item's nutritional information. Optional Object
menu.items.nutritional_info.
energy_kcal
Item's Calorie information. If present and empty, 0 calories will be assumed. Optional Object
menu.items.nutritional_info.
energy_kcal.low
Lower bound of energy in "Kcal" in the item. >= 0. Optional Integer
menu.items.nutritional_info.
energy_kcal.high
Upper bound of energy in "Kcal" in the item. >= 0, >= item.nutritional_info.energy_kcal.low. Optional Integer
menu.items.nutritional_info.hfss Describes whether the item is considered high in saturated fat, salt and sugar (HFSS), according to the Department of Health’s Nutrient Profiling Model (relevant to some grocery partners in England and Wales only). Set this to true to mark this item as HFSS. Optional boolean
menu.items.contains_alcohol Describes if the item contains alcohol. Required boolean
menu.items.max_quantity Maximum quantity of the item the consumer can order. Optional Integer
menu.modifiers List of modifiers. Array of objects
menu.modifiers.id Unique identifier for the modifier. Required String 255
menu.modifiers.name Translated name of the modifier. You need to send the language code as supported in Deliveroo. For a list of supported languages and corresponding language codes, refer to the 'Language Codes section below'. Required Object 250
menu.modifiers.description Translated description of the modifier. Optional Object 500
menu.modifiers.min_selection Minimum number of items the consumer can choose from the modifier. Integer
menu.modifiers.max_selection Maximum number of items the consumer can choose from the modifier. Integer
menu.modifiers.repeatable Describes whether a consumer can choose the same item inside a modifier group multiple times. Boolean
menu.modifiers.item_ids IDs of the items inside the modifier. Array of strings
site_ids IDs of the sites the menu should be published to. Required Array of strings

Successful Put menu response body example:

{
  "status": "OK"
}

Failed Put menu response body example:

{
  "error": {
    "code": "bad_request",
    "message": "{\"items\":{\"0\":{\"description\":{\"en\":\"the length must be no more than 500\"}}}}"
  }
}
Response Code Error Code
503 service_unavailable
400 bad_request
422 unprocessable_entity
429 too_many_requests
409 conflict

POST https://partners.deliveroo.com/api/v1/brands/:brand_id/menus/:id/plus

Menu items are stored in our platform and can be identified by their id, which is provided by the restaurant partner. When a restaurant is integrated with our POS APIs, an additional ID is used to identify the same item the customer is ordering on the restaurant partner POS systems. These IDs are sometimes referred as "sku", "external_id", or "plu": this - plu is what we call those identifiers that must find a match on the restaurant's POS system. Our menus APIs can be used to upload an entire menu, including their PLU codes. This API, however, is meant to be the way partners can provide and update that mapping between an item and its PLU code.

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
id string
The unique identifier for the menu for the given "brand" context.

Post plus request body example:

[
  {
    "item_id": "1234",
    "plu": "1234-plu"
  },
  {
    "item_id": "5678",
    "plu": "5678-plu"
  }
]

Successful Post plus menu response body example:

{
  "status": "OK"
}

Failed Post plus response body example:

{
  "error": {
    "code": "bad_request",
    "message": "{\"items\":{\"0\":{\"description\":{\"en\":\"the length must be no more than 500\"}}}}"
  }
}
Response Code Error Code
400 bad_request
409 conflict

The request body must contain an array of JSON objects representing the mapping between an item and its plu.

Parameter Description
item_id string
The unique identifier an existing item within the menu identified by the resource.
plu string
The PLU (Price Look-Up) that identifies the item and its price in the external system.

PUT https://partners.deliveroo.com/api/v1/brands/:brand_id/menus/:id/item_unavailabilities/:site_id

Once a menu is sent to our platform, all the items in the menu are theoretically "available", therefore a customer can order them. This endpoint allows the caller to set items as "unavailable" or "hidden":

The call acts as a complete override of all the item unavailabilities for the given menu/site; as a corollary, sending an empty array will make everything available again.

This endpoint is rate limited at 1 request per minute per site.

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
id string
The unique identifier for the menu for the given "brand" context.
site_id string
ID of the site the menu unavailabilities should be applied to.

Put item_unavailabilities request body example:

{
   "unavailable_ids": ["orange_juice", "granola"],
   "hidden_ids": ["whole_milk"]
}

The above sets orange_juice and granola as unavailable/sold out for the current day, and whole_milk as hidden. The following subsequent update would bring back granola as available, keep orange_juice as sold out, and set "whole_milk" to hidden.

{
   "unavailable_ids": ["orange_juice"],
   "hidden_ids": ["whole_milk"]
}

The request body must contain a json object with two arrays defining the unavailable and hidden IDs.

Parameter Description
unavailable_ids array
Item ids from the site menu that will be marked as unavailable/sold out for the day.
hidden_ids array
Item ids from the site menu that will be hidden indefinitely.

POST https://partners.deliveroo.com/api/v1/brands/:brand_id/menus/:id/item_unavailabilities/:site_id

This endpoint allows the caller to set individual items with an "unavailable" or "hidden" status, as well as marking them available again:

This endpoint is rate limited at 10 requests per second per site.

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
id string
The unique identifier for the menu for the given "brand" context.
site_id string
ID of the site the menu unavailabilities should be applied to.

Post item_unavailabilities request body example:

{
  "item_unavailabilities": [
    {
      "item_id": "orange_juice",
      "status": "unavailable"
    },
    {
      "item_id": "granola",
      "status": "available"
    },
    {
      "item_id": "whole_milk",
      "status": "hidden"
    }
  ]
}

The request body must contain an item_id and the target status.

Parameter Description
item_unavailabilities array[ItemUnavailability]
Contains list of individual item unavailability updates.
ItemUnavailability
item_id string
Item id from the site menu that will be marked as unavailable/sold out for the day.
status string
Status to mark unavailable, or sold out for the day.
Status code Description
200 (OK) Completed successfully. All item status change requests were updated.
400 (Bad request) Typically a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
404 (Not Found) The specified resource could not be found. Ex. an item_id requested does not exist on the menu.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Empty Response

GET https://partners.deliveroo.com/api/v1/brands/:brand_id/menus/:id/item_unavailabilities/:site_id

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
id string
The unique identifier for the menu for the given "brand" context.
site_id string
ID of the site the menu unavailabilities should be applied to.

Get item_unavailabilities response body example:

{
   "unavailable_ids": ["orange_juice", "granola"],
   "hidden_ids": ["whole_milk"]
}

Failed Get item_unavailabilities response body example:

{
  "error": {
    "message": "branch_drn_id is required",
    "code": "bad_request"
  }
}
Response Code Error Code
403 forbidden
404 not_found
400 bad_request
Parameter Description
unavailable_ids array
Item ids from the site menu that have been marked as unavailable/sold out for the day.
hidden_ids array
Item ids from the site menu that have been hidden indefinitely.

Menus that are created and managed using Menu Manager cannot be retrieved or managed using our original Menu API endpoints (detailed in the 'Menu API' section and described as v1).
We have therefore built specific endpoints to allow you to manage menus created by Menu Manager, which are detailed below and described as v2. (please note, only a subset of the Menu API endpoints are currently available as v2).

The Get Menu API allows you to retrieve a menu created via the Upload Menu API or Menu Manager for a particular site. You can call this API to view the latest status of the menu uploaded in Deliveroo.

GET /api/v2/brands/:brand_id/sites/:external_id/menu

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
external_id string
Identifier of the site.

Get menu response body example:

{
  "name": "site-234 menu",
  "menu": {
    "mealtimes": [
      {
        "id": "breakfast-menu",
        "name": {
          "en": "Breakfast menu"
        },
        "description": {
          "en": "Best breakfast menu in town! Everything on the menu is freshly made at the start of the day."
        },
        "seo_description": {
          "en": "Best breakfast menu in town!"
        },
        "image": {
          "url": ""
        },
        "category_ids": [
          "breakfast-bundle", "porridge", "drinks"
        ]
      }
    ],
    "categories": [
      {
        "id": "porridge",
        "name": {
          "en": "Porridge 🥣"
        },
        "description": {
          "en": "Freshly made porridge"
        },
        "item_ids": ["porridge_blueberries", "porridge_banana"]
      },
      {
        "id": "drinks",
        "name": {
          "en": "Drinks ☕️"
        },
        "description": {},
        "item_ids": ["tea", "coffee", "orange_juice"]
      },
      {
        "id": "breakfast-bundle",
        "name": {
          "en": "Breakfast bundle 📦"
        },
        "description": {},
        "item_ids": ["breakfast-bundle"]
      }
    ],
    "items": [
      {
        "id": "porridge_blueberries",
        "name": {
          "en": "Porridge with blueberries"
        },
        "description": {
          "en": "Porridge with blueberries and cinnamon"
        },
        "price_info": {
          "price": 350,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "porridge_blueberries123",
        "ian": "4006381333931",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [
          "extra_toppings"
        ],
        "allergies": ["milk"],
        "nutritional_info": {
          "energy_kcal": {
            "low": 123,
            "high": 456
          },
          "hfss": false
        },
        "contains_alcohol": false
      },
      {
        "id": "porridge_banana",
        "name": {
          "en": "Porridge with bananas"
        },
        "operational_name": "porridge-ban",
        "description": {
          "en": "Porridge with bananas and cinnamon"
        },
        "price_info": {
          "price": 350,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "porridge_banana123",
        "ian": "4006381333932",
        "image": {},
        "is_eligible_as_replacement": false,
        "is_eligible_for_substitution": false,
        "tax_rate": 20.0,
        "modifier_ids": [
          "extra_toppings"
        ],
        "allergies": ["milk"],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "peanut_butter",
        "name": {
          "en": "Peanut butter"
        },
        "operational_name": "peanut-butter",
        "description": {
          "en": "Crunchy peanut butter"
        },
        "price_info": {
          "price": 100,
          "overrides": []
        },
        "plu": "peanut_butter_123",
        "ian": "4006381333933",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": false,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": ["peanuts"],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "granola",
        "name": {
          "en": "Granola"
        },
        "operational_name": "granola",
        "description": {
          "en": "Granola"
        },
        "price_info": {
          "price": 100,
          "overrides": []
        },
        "plu": "granola_123",
        "ian": "4006381333934",
        "image": {},
        "is_eligible_as_replacement": false,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "honey",
        "name": {
          "en": "Honey"
        },
        "operational_name": "honey",
        "description": {
          "en": "Honey"
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "honey_123",
        "ian": "4006381333935",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "tea",
        "name": {
          "en": "Tea"
        },
        "operational_name": "tea",
        "description": {},
        "price_info": {
          "price": 150,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "tea_$23",
        "ian": "4006381333936",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": ["choose_milk"],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "coffee",
        "name": {
          "en": "Coffee"
        },
        "operational_name": "coffee",
        "description": {},
        "price_info": {
          "price": 250,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "coffee_$78",
        "ian": "4006381333937",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": ["choose_milk"],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "no_milk",
        "name": {
          "en": "No milk"
        },
        "operational_name": "no-milk",
        "description": {
          "en": ""
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "no_milk_$49",
        "ian": "4006381333938",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "whole_milk",
        "name": {
          "en": "Whole milk"
        },
        "operational_name": "whole-milk",
        "description": {
          "en": ""
        },
        "price_info": {
          "price": 0,
          "overrides": []
        },
        "plu": "whole_milk_$39",
        "ian": "4006381333939",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "orange_juice",
        "name": {
          "en": "Orange juice"
        },
        "operational_name": "orange-juice",
        "description": {},
        "price_info": {
          "price": 250,
          "overrides": [
            {
              "type": "ITEM",
              "id": "breakfast-bundle",
              "price": 0
            }
          ]
        },
        "plu": "orange_juice_$69",
        "ian": "4006381333940",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      },
      {
        "id": "breakfast-bundle",
        "name": {
          "en": "Breakfast bundle"
        },
        "description": {
          "en": "Porridge with a drink of your choice."
        },
        "price_info": {
          "price": 450,
          "overrides": []
        },
        "plu": "breakfast_bundle123",
        "ian": "4006381333941",
        "image": {},
        "is_eligible_as_replacement": true,
        "is_eligible_for_substitution": true,
        "tax_rate": 20.0,
        "modifier_ids": [
          "choose_your_porridge", "choose_your_drink"
        ],
        "allergies": [],
        "nutritional_info": {},
        "contains_alcohol": false
      }
    ],
    "modifiers": [
      {
        "id": "extra_toppings",
        "name": {
          "en": "Choice of extra toppings 🍯"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 3,
        "repeatable": false,
        "item_ids": [
          "honey",
          "peanut_butter",
          "granola"
        ]
      },
      {
        "id": "choose_milk",
        "name": {
          "en": "Choose milk"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "no_milk",
          "whole_milk"
        ]
      },
      {
        "id": "choose_your_porridge",
        "name": {
          "en": "Choose your porridge"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "porridge_blueberries",
          "porridge_banana"
        ]
      },
      {
        "id": "choose_your_drink",
        "name": {
          "en": "Choose your drink"
        },
        "description": {
          "en": ""
        },
        "min_selection": 0,
        "max_selection": 1,
        "repeatable": true,
        "item_ids": [
          "tea",
          "coffee",
          "orange_juice"
        ]
      }
    ]
  },
  "site_ids": ["site-234"]
}

Failed Get menu response body example:

{
  "error": {
    "message": "can't find requested live menu",
    "code": "not_found"
  }
}
Response Code Error Code
400 bad_request
404 not_found
500 500

PUT https://partners.deliveroo.com/api/v2/brands/:brand_id/sites/:external_id/menu/item_unavailabilities

Once a menu is sent to our platform, all the items in the menu are theoretically "available", therefore a customer can order them. This endpoint allows the caller to set items as "unavailable" or "hidden":

The call acts as a complete override of all the item unavailabilities for the given menu/site; as a corollary, sending an empty array will make everything available again.

Note: this endpoint works for menus created by Upload Menu API as well as menus created using the menu manager.

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
external_id string
ID of the site the menu unavailabilities should be applied to.

Put item_unavailabilities request body example:

{
   "unavailable_ids": ["orange_juice", "granola"],
   "hidden_ids": ["whole_milk"]
}

The above sets orange_juice and granola as unavailable/sold out for the current day, and whole_milk as hidden. The following subsequent update would bring back granola as available, keep orange_juice as sold out, and set "whole_milk" to hidden.

{
   "unavailable_ids": ["orange_juice"],
   "hidden_ids": ["whole_milk"]
}

The request body must contain a json object with two arrays defining the unavailable and hidden IDs.

Parameter Description
unavailable_ids array
Item ids from the site menu that will be marked as unavailable/sold out for the day.
hidden_ids array
Item ids from the site menu that will be hidden indefinitely.

POST https://partners.deliveroo.com/api/v2/brands/:brand_id/sites/:external_id/menu/item_unavailabilities

This endpoint allows the caller to set individual items with an "unavailable" or "hidden" status, as well as marking them available again:

Note: this endpoint works for menus created by Upload Menu API as well as menus created using the menu manager.

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
external_id string
ID of the site the menu unavailabilities should be applied to.

Post item_unavailabilities request body example:

{
  "item_unavailabilities": [
    {
      "item_id": "orange_juice",
      "status": "unavailable"
    },
    {
      "item_id": "granola",
      "status": "available"
    },
    {
      "item_id": "whole_milk",
      "status": "hidden"
    }
  ]
}

The request body must contain an item_id and the target status.

Parameter Description
item_unavailabilities array[ItemUnavailability]
Contains list of individual item unavailability updates.
ItemUnavailability
item_id string
Item id from the site menu that will be marked as unavailable/sold out for the day.
status string
Status to mark unavailable, or sold out for the day.
Status code Description
200 (OK) Completed successfully. All item status change requests were updated.
400 (Bad request) Typically a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
404 (Not Found) The specified resource could not be found. Ex. an item_id requested does not exist on the menu.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Empty Response

GET https://partners.deliveroo.com/api/v2/brands/:brand_id/sites/:external_id/menu/item_unavailabilities

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).
external_id string
Identifier of the site.

Get item_unavailabilities response body example:

{
   "unavailable_ids": ["orange_juice", "granola"],
   "hidden_ids": ["whole_milk"]
}

Failed Get item_unavailabilities response body example:

{
  "error": {
    "message": "branch_drn_id is required",
    "code": "bad_request"
  }
}
Response Code Error Code
403 forbidden
404 not_found
400 bad_request
Parameter Description
unavailable_ids array
Item ids from the site menu that have been marked as unavailable/sold out for the day.
hidden_ids array
Item ids from the site menu that have been hidden indefinitely.

The menus API uses the following HTTP status codes for errors.

Code Description
400 Bad request
Typically, a required parameter is missing or invalid.
401 Unauthorized
The provided API key and API token is invalid or disabled.
404 Not found
The specified resource could not be found.
429 Too Many Requests
The user has sent too many requests in a given amount of time. A menu with a given "external_id" can only be updated once per minute.
>=500 Internal server error
Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Language codes are useful to pass menu contents like category names, item names, item descriptions, seo descriptions for multiple languages to seamlessly translate based on users' language preferences.

You can pass information for the fields that accept language specific inputs for multiple languages.

Below is the list of language codes supported by Deliveroo. You will have to pass the language codes listed below along with the details in the corresponding language for the field.

Additional language options are limited by market and aren’t yet supported in the UK and Ireland. Please check the table below to see what languages are supported in each market.

Language Language Code Supported Markets
English en All Markets
French fr France, Belgium
Italian it Italy
Arabic ar Kuwait, Qatar, UAE
Chinese (Traditional) zh Hong Kong, Singapore
Dutch nl Netherlands, Belgium

Orders API

Site API

Introduction

The Deliveroo Site API provides developers the ability to manage sites' information.

This API consists in the following components:

Opening hours: A developer can use this feature to view or define a site opening hours. Multiple opening hours can be applied for each weekday.

Status: A developer can set the online status of a site to be open or closed.

Days off: A developer can add, retrieve, update or cancel days off periods for a given site. Days off are exceptions to the normal opening hours of a site that are applied each day.

Workload A developer can change workload mode as well as set the preparation time for each mode.

API path

All site API endpoints that controls site details are located under the following path /api/v1/brands/{brandId}/sites/{siteId}

Path parameters

Parameter Description
brandId string
The unique identifier for the brand.
siteId int
Identifier defined by the user.

A list of all brands can be retrieved at GET /api/v1/brands

Get site opening hours response body example:

{
    "brands": [
        {
            "id": "brandunique-id",
            "name": "name",
            "market": "GB"
        }
    ]
}

Errors

The site API uses the following HTTP status codes for errors.

Code Description
400 Bad request
Typically, a required parameter is missing or invalid.
401 Unauthorized
The provided API key and API token is invalid or disabled.
404 Not found
The specified resource could not be found.
>=500 Internal server error
Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Errors return JSON structured like this, where message may contain more specific information:

{
  "error": {
    "code": "bad_request",
    "message": "invalid date format"
  }
}

Additionally, the returned JSON error will contain additional details for developers in the message, as well as a specific error code.

Code Description
bad_gateway An error occurred on one of our internal systems. You may try again.
bad_request Generally as a result of a validation issue.
disabled The specified site is disabled.
scope The site configuration does not allow changes via API
unauthorized Missing or invalid API key or secret.

Opening hours

The following endpoints can be used to set and update the opening hours for each weekday, which can have multiple opening hours as long as they do not overlap.

Get site opening hours

HTTP Request

GET /api/v1/brands/{brandId}/sites/{siteId}/opening_hours

Get site opening hours response body example:

{
    "opening_hours": {
       "monday": [
            {
                "local_start_time": "12:00",
                "local_end_time": "15:00"
            }
        ],
        "friday": [
            {
                "local_start_time": "11:30",
                "local_end_time": "16:00"
            },
            {
                "local_start_time": "18:00",
                "local_end_time": "23:00"
            }
        ]
    }
}

Update site opening hours

Opening hours endpoint does not support partial updates so you must specify all opening hours when updating data, so each call to this endpoint overwrites any existing opening hours.

Request parameters

Parameter Description
opening_hours map
Map of weekday. Accepted values are monday,tuesday,wednesday,thursday,friday,saturday and sunday.
weekday array
Array containing one or more opening_hour objects.
opening_hour object
Opening hour object.
local_start_time string
Start time of opening hour in local time in the format HH:MM in the timezone where the site operates in.
local_end_time string
End time of opening hour in local time in the format HH:MM in the timezone where the site operates in.

Response

Status code Description
200 (OK) Completed successfully. Data is returned in the response body.
400 (Bad request) Typically, a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

HTTP Request

POST /api/v1/brands/{brandId}/sites/{siteId}/opening_hours

Update site opening hours request body example:

{
    "opening_hours": {
       "monday": [
            {
                "local_start_time": "12:00",
                "local_end_time": "15:00"
            }
        ],
        "wednesday": [
            {
                "local_start_time": "13:00",
                "local_end_time": "15:00"
            }
        ],
        "friday": [
            {
                "local_start_time": "11:30",
                "local_end_time": "16:00"
            },
            {
                "local_start_time": "18:00",
                "local_end_time": "23:00"
            }
        ]
    }
}

Brand Sites

Get sites for a brand

Returns a list of the sites a brand has

HTTP Request

GET https://partners.deliveroo.com/api/v1/brands/:brand_id/sites

Response parameters

Parameter Description
brand_id string
The brand's id.

Get sites for a brand response body example:

{
  "sites": [
    {
      "location_id": "location-test-1",
      "name": "Name of site1",
      "status": "OPEN",
      "api_access": {
        "fulfillment": false,
        "kiosk": true,
        "menu": true,
        "picking": false,
        "pos": false,
        "rider_status_updates": true,
        "site": false,
        "update_order_status": false
      },
      "phone_number": "",
      "branch_type": "RESTAURANT",
      "on_vacation": false,
      "timezone": "Europe/London"
    },
    {
      "location_id": "location-test-2",
      "name": "Name of site2",
      "status": "OPEN",
      "api_access": {
        "fulfillment": false,
        "kiosk": true,
        "menu": true,
        "picking": true,
        "pos": false,
        "rider_status_updates": false,
        "site": false,
        "update_order_status": false
      },
      "phone_number": "07987342740",
      "branch_type": "UNKNOWN",
      "on_vacation": false,
      "timezone": "Europe/London"
    }
  ]
}

Status

The status defines if a site is open or closed. It can be retrieved using the following endpoint.

Get site status

Response parameters

Parameter Description
status string
The restaurant's current status. Accepted values are OPEN, CLOSED or READY_TO_OPEN.

HTTP Request

GET /api/v1/brands/{brandId}/sites/{siteId}/status

Get site response body example:

{
    "status": "OPEN"
}

Update site status

When opening a site outside of its opening hours, its status will be set to READY_TO_OPEN.

Request parameters

Parameter Description
status string
The new status. Accepted values are OPEN or CLOSED.

Response

Status code Description
200 (OK) Completed successfully. Data is returned in the response body.
400 (Bad request) Typically, a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

HTTP Request

PUT /api/v1/brands/{brandId}/sites/{siteId}/status

Update site status request body example:

{
    "status": "CLOSED"
}

Time zone

Endpoints relating to the time zone of a site.

Get site time zone

Retrieves the time zone of a site.

Response parameters

Parameter Description
time_zone string
The time zone of the site.

HTTP Request

GET /api/v1/brands/{brandId}/sites/{siteId}/time_zone

Get site time zone response body example:

{
    "time_zone": "Europe/London"
}

Days off

Endpoints that allow a developer to control days off periods for a given site. Days off are exceptions to the normal operating hours of a site that are applied each day.

Get site days off

All days off defined for site can be retrieved. Note that this data is paginated.

HTTP Request

GET /api/v1/brands/{brandId}/sites/{siteId}/days_off?page_size={pageSize}&page_number={pageNumber}&upcoming={true|false}

Path parameters

Parameter Description
pageSize int
Max number of elements that can be present per page. (default is 20, maximum is 50)
pageNumber int
Number of the page. Starts at 1. (default value is 1)
upcoming (optional) bool
If true, only upcoming days off periods that are not cancelled will be retrieved.

Response parameters

Parameter Description
days_off array
Array of DaysOffPeriod.
page.number int
Page number.
page.size int
Page size.
page.total_items int
Number of defined days off periods for this site.
DaysOffPeriod
id int
Legacy unique identifier. Prefer using days_off_id.
days_off_id string
Unique identifier.
local_start_time string
Start datetime of the close period in the YYYY-MM-DD HH:MM format in the timezone where the site operates in.
local_end_time string
End datetime of the close period in the YYYY-MM-DD HH:MM format in the timezone where the site operates in.
reason string
Day off reason. Possible values are are DAYS_OFF,TABLET_OFFLINE,TOO_MANY,AUTO_REJECTS,UNKNOWN
cancelled_at string
The datetime when the days off period was cancelled in the YYYY-MM-DD HH:MM format in UTC timezone. If it is not cancelled, null is returned.

Get site days off response body example:

{
    "days_off": [
        {
            "id": 1,
            "days_off_id": "gb:fab7c7f3-e6eb-4eef-8d06-9f57aa521af5",
            "local_start_time": "2021-11-16 00:00",
            "local_end_time": "2021-12-17 23:00",
            "reason": "DAYS_OFF",
            "cancelled_at": null
        },
        {
            "id": 2,
            "days_off_id": "gb:6ae4516d-71c0-4d78-8a58-8015561cae51",
            "local_start_time": "2021-12-24 00:00",
            "local_end_time": "2021-12-26 10:00",
            "reason": "DAYS_OFF",
            "cancelled_at": "2021-04-30 14:26"
        }
    ],
    "page": {
        "number": 1,
        "size": 20,
        "total_items": 2
    }
}

Add new site days off period

A developer can add a new days off period which will be created with DAYS_OFF reason set by default. It is important to notice that this endpoint allows multiple days off periods with overlapping hours to be created.

HTTP Request

POST /api/v1/brands/{brandId}/sites/{siteId}/days_off

Request parameters

Parameter Description
local_start_time string
Start datetime of the close period in the YYYY-MM-DD HH:MM format.
local_end_time string
End datetime of the close period in the YYYY-MM-DD HH:MM format.

Response

Status code Description
200 (OK) Completed successfully. Data is returned in the response body.
400 (Bad request) Typically, a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
DaysOffPeriod

Add site days off period request body example:

{
    "local_start_time": "2020-11-24 00:00",
    "local_end_time": "2020-12-26 23:59",
}

Add site days off period response body example:

{
    "id": 15158,
    "days_off_id": "gb:fab7c7f3-e6eb-4eef-8d06-9f57aa521af5",
    "local_start_time": "2020-11-24 00:00",
    "local_end_time": "2020-12-26 23:59",
    "reason": "DAYS_OFF",
    "cancelled_at": null
}

Update a site days off period

A days off period can be updated using this endpoint. It is important to notice that this endpoint allows multiple days off periods with overlapping hours to be created. Only the start time and end time can be updated.

HTTP Request

PUT /api/v1/brands/{brandId}/sites/{siteId}/days_off/{daysOffId}

Path parameters

Parameter Description
daysOffId string
Unique days off period identifier. Can be either the days_off_id or the legacy id.

Request parameters

Parameter Description
local_start_time string
Start datetime of the close period in the YYYY-MM-DD HH:MM format.
local_end_time string
End datetime of the close period in the YYYY-MM-DD HH:MM format.

Response

Status code Description
200 (OK) Completed successfully. Data is returned in the response body.
400 (Bad request) Typically, a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
DaysOffPeriod

Add site days off period request body example:

{
    "days_off_id": "gb:fab7c7f3-e6eb-4eef-8d06-9f57aa521af5",
    "local_start_time": "2020-11-24 00:00",
    "local_end_time": "2020-12-26 23:59",
}

Add site days off period response body example:

{
    "id": 15158,
    "days_off_id": "gb:fab7c7f3-e6eb-4eef-8d06-9f57aa521af5",
    "local_start_time": "2020-11-24 00:00",
    "local_end_time": "2020-12-26 23:59",
    "reason": "DAYS_OFF",
    "cancelled_at": null
}

Cancel a site days off period

HTTP Request

DELETE /api/v1/brands/{brandId}/sites/{siteId}/days_off/{daysOffId}

Path parameters

Parameter Description
daysOffId string
Unique days off period identifier. Can be either the days_off_id or the legacy id.

Response

Status code Description
200 (OK) Completed successfully. Days off period data is returned in the response body.
400 (Bad request) Typically, a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
DaysOffPeriod

Cancel site days off period response body example:

{
    "id": 15158,
    "days_off_id": "gb:fab7c7f3-e6eb-4eef-8d06-9f57aa521af5",
    "local_start_time": "2020-11-24 00:00",
    "local_end_time": "2020-12-26 23:59",
    "reason": "DAYS_OFF",
    "cancelled_at": "2020-05-20 11:23"
}

Get a single a site days off period

HTTP Request

GET /api/v1/brands/{brandId}/sites/{siteId}/days_off/{daysOffId}

Path parameters

Parameter Description
daysOffId string
Unique days off period identifier. Can be either the days_off_id or the legacy id.

Response

Status code Description
200 (OK) Completed successfully. Days off period data is returned in the response body.
400 (Bad request) Typically, a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
DaysOffPeriod

Get site days off period response body example:

{
    "id": 15158,
    "days_off_id": "gb:fab7c7f3-e6eb-4eef-8d06-9f57aa521af5",
    "start_at": "2021-12-10 00:00",
    "end_at": "2021-12-12 23:59",
    "reason": "DAYS_OFF",
    "cancelled_at": null
}

Workload mode

The workload mode is used to set the current workload for a site. It is important to note that changing site's workload mode the corresponding time will be applied, increasing or decreasing site's preparation time. A mode can be set to QUIET or BUSY.

Get site workload mode

A site workload load mode can be retrieved using the following endpoint.

HTTP Request

GET /api/v1/brands/{brandId}/sites/{siteId}/workload/mode

Response

Status code Description
200 (OK) Completed successfully. Days off period data is returned in the response body.
400 (Bad request) Typically, a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
mode string
The current site workload. Possible values are QUIET and BUSY.

Get site workload mode response body example:

{
    "mode": "BUSY"
}

Set site workload mode

A site workload load mode can be set using the following endpoint.

HTTP Request

PUT /api/v1/brands/{brandId}/sites/{siteId}/workload/mode

Response

Status code Description
200 (OK) Completed successfully. Days off period data is returned in the response body.
400 (Bad request) Typically a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
mode string
The current site workload. Possible values are QUIET or BUSY.

Set site workload mode response body example:

{
    "mode": "BUSY"
}

Workload times

Each workload mode has its own corresponding preparation time. These times can be retrieved using the following endpoint. It is important to note that all time values in this endpoint are expressed in minutes.

Get site workload times

HTTP Request

GET /api/v1/brands/{brandId}/sites/{siteId}/workload/times?allowed_ranges={true|false}

Path parameters

Parameter Description
allowed_ranges (Optional) bool
If true, returns the allowed ranges for each workload mode.

Response

Status code Description
200 (OK) Completed successfully. Days off period data is returned in the response body.
400 (Bad request) Typically a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
quiet string
Prep time (in minutes) applied when site workload mode is QUIET.
busy string
Prep time (in minutes) applied when site workload mode is BUSY.
allowed_ranges (Optional) map
Map of range objects indexed by mode. This will be included only when allowed_ranges query parameter is set as true.
range object
Defines minimum and maximum values allowed (in minutes).

Get site's workload times response body example:

{
    "busy": 35,
    "quiet": 15,
    "allowed_ranges": {
        "busy": {
            "min": 25,
            "max": 240
        },
        "quiet": {
            "min": 20,
            "max": 60
        }
    }
}

Set site workload times

Workload times can be set individually for each workload mode. It is important to note that if a site wants to increment their busy prep time, this value must be greater than quiet value and the difference must be a multiple of 5. E.g. if a site's quiet is 10min, busy should be 15, 20, 25, 30, 35, etc. or any other increment that is multiple of 5.

HTTP Request

PUT /api/v1/brands/{brandId}/sites/{siteId}/workload/times

Response

Status code Description
200 (OK) Completed successfully. Days off period data is returned in the response body.
400 (Bad request) Typically a required parameter is missing or invalid.
401 (Unauthorized) The provided API key and API token is invalid or disabled.
>=500 Something went wrong on our end. You’ll have to try again later once we’ve fixed it.

Response parameters

Parameter Description
quiet string
Prep time (in minutes) applied when site workload mode is QUIET.
busy string
Prep time (in minutes) applied when site workload mode is BUSY.

Set site workload times request body example: json { "busy": 35, "quiet": 15 }

Set site workload times response body example:

{
    "busy": 35,
    "quiet": 15
}

Picking API

Introduction

The Deliveroo Picking API provides developers with a lightweight, robust integration solution to accept and reject orders and to update order item quantities in real time.

Verify API test credentials

Example request with cURL:

curl --user <test-api-key>:<test-api-secret> https://partners.deliveroo.com/api/v1/auth/verify

HTTP Request

GET /api/v1/auth/verify

Successful response:

{
  "api_key": "<test-api-key>",
  "test_mode": true
}

An HTTP 401 unauthorized error:

{
  "error": {
    "code": "unauthorized",
    "message": "api key or secret is invalid"
  }
}

Endpoints

Accept order

Accept order response body example:

{
  "order_id": "gb:28588c69-efc7-479f-b692-168fa910b19c",
  "status": "ACCEPTED"
}

Failed request, Accept order response body example:

{
  "error": {
    "message":"order status is not \"Placed\"",
    "code": "bad_request"
  }
}

Allows to accept an order. It can be only be called once per order.

PUT https://partners.deliveroo.com/api/v1/picking/orders/{order_id}/accept

Response Code Error Code
500 unknown_error
404 not_found
400 bad_request

Reject order

Reject order request body example:

{
  "reject_reason": "BUSY"
}

reject_reason can be any one of INGREDIENT_UNAVAILABLE, CLOSING_EARLY, BUSY, OTHER

Reject order response body example:

{
  "order_id": "gb:28588c69-efc7-479f-b692-168fa910b19c",
  "status": "REJECTED"
}

Failed request, Reject order response body example:

{
  "error": {
    "message":"order status is not \"Placed\"",
    "code": "bad_request"
  }
}
Response Code Error Code
500 unknown_error
404 not_found
400 bad_request

Allows the partner to reject an order. It can only be called once per order.

PUT https://partners.deliveroo.com/api/v1/picking/orders/{order_id}/reject

Fetch active orders

Allows to fetch all active orders for a specific branch.

GET https://partners.deliveroo.com/api/v1/picking/restaurants/:external_id/orders/active?page=<page>&per_page=<per_page>

Request parameters

Parameter Description
external_id string
Identifier for the restaurant.
page int
Current page.
per_page int
Number of items per page.

Response parameters

A successful response body example:

{
  "orders": [
    {
      "id": "4K6CexdNbessmia4HDVewu9",
      "location_id": "thrr13z1v3ut-UpgTOHtOgMY",
      "status_log": [
        {
          "at": "2021-04-07T10:11:49.044Z",
          "status": "PENDING"
        },
        {
          "at": "2021-04-07T10:11:49.079Z",
          "status": "PLACED"
        }
      ],
      "status": "PLACED",
      "display_id": "1244",
      "allergy_note": "string",
      "item_substitution": "",
      "rejection_reason": "string",
      "asap": true,
      "customer_order_count": 1,
      "order_type": "delivery",
      "subtotal_price": {
        "currency_code": "GBP",
        "fractional": 400
      },
      "total_after_substitutions": {
        "currency_code": "GBP",
        "fractional": 400
      },
      "subtotal_after_substitutions": {
        "currency_code": "GBP",
        "fractional": 400
      },
      "substituted_items_total": {
        "currency_code": "GBP",
        "fractional": 400
      },
      "total_price": {
        "currency_code": "GBP",
        "fractional": 440
      },
      "offer_discount": {
        "currency_code": "GBP",
        "fractional": 0
      },
      "items": [
        {
          "id": "string",
          "pos_item_id": "string",
          "quantity": 2,
          "name": "string",
          "operation_name": "string",
          "total_unit_price": {
            "currency_code": "GBP",
            "fractional": 400
          },
          "unit_price": {
            "currency_code": "GBP",
            "fractional": 400
          },
          "modifiers": [
            {
              "pos_item_id": "string",
              "quantity": 1,
              "name": "string",
              "operation_name": "string",
              "total_unit_price": {
                "currency_code": "GBP",
                "fractional": 140
              },
              "unit_price": {
                "currency_code": "GBP",
                "fractional": 140
              }
            }
          ]
        }
      ],
      "archived_items": [],
      "updated_at_epoch_ms": 1643736125493
    }
  ],
  "meta": {
    "total_count": 1,
    "page": 1,
    "per_page": 1,
    "page_count": 1
  }
}
Parameter Description
id string
Order's unique identification.
location_id string
Partner identifier.
display_id string
The customer facing 4-digit order number.
status string
Latest status of the order
status_log array
Append-only log of order status changes
rejection_reason string
Indicates the reason in case the order is rejected
allergy_note string
A plain text field in which the customer can specify dietary restrictions and other special requests.
asap boolean
Whether the order is an ASAP order.
prepare_for datetime
The time by which the order must be prepared.
customer_order_count int
Number of orders made by related customer in this place.
order_type string
delivery / pickup Order type.
subtotal money
The price of all of the items in the order.
subtotal_after_substitutions money
The price of all the available items in the order after taking into account any item substitutions.
substituted_items_total money
The total price of the substituted items..
total_price money
The total price of the order, including delivery but taking into account only the available items after making any substitutions.
total_after_substitutions money
The total price of all the available items in the order after taking into account any item substitutions.
offer_discount money
The offer discount used when the order was placed.
item_substitution - deprecated string
Indicates the customer's preference for item substitution for this order. Possible values: ""
This attribute is deprecated and therefore its value is always an empty string. You can use the allowed_actions_if_items_are_unavailable attribute of OrderItem for this purpose.
items array[OrderItem]
List of items in the order
archived_items array[OrderItem]
List of items that were refactored or amended
updated_at_epoch_ms int
Time at which this order was last updated (represented as unix time with ms precision)
OrderItem
id string
Order's unique identification.
pos_item_id string
Partner identifier, aka PLU.
quantity int
This holds the final amount of units expected to be delivered.
name string
Customer-facing name of the menu item..
operational_name string
Restaurant-facing name of the menu item.
total_unit_price money
Price for one of the items without Deliveroo fees
unit_price money
Price for one of this item with Deliveroo fee
discount_amount money
The discount amount on the item
modifiers array[OrderItem]
Contains any customizations to the menu item. These entities take the same shape as a top level menu item.
archived_reason string
Keeps the reason why this item is archived. Possible values: [REFACTORING, AMENDMENT, UNDO]
amends object
Keeps a reference to the order item that this item amends. It will be NULL if this item is not an amendment.
amends.quantity int
Quantity of order item that this item amends.
amends.id string
Identifier of the order item that this item amends.
amends.amendment_type string
Type of amendment. Possible values: [REMOVAL, SUBSTITUTION]
original object
Keeps a reference to the original order item that this item relates to. It is meant to keep a direct relationship between each item in the order and the original item/quantity it refers to. Cutting short all of the intermediate refactoring / amendment / undo operations. It will be NULL if this item is not an amendment.
original.quantity int
Quantity of the original order item.
original.id string
Identifier of the original order item.
original.amendment_type string
Type of amendment. Possible values: [REMOVAL, SUBSTITUTION]
refactors object
Refactors keeps a reference to the order item that this item amends. Refactors is NULL if the item was not refactored. This allows to keep the relationship between original order_items and their refactoring items.
refactors.quantity int
Quantity of the refactored order item.
refactors.id string
Identifier of the refactored order item.
refactors.original_id string
Original identifier of refactored order item.
allowed_actions_if_items_are_unavailable array
Keeps applicable actions for this order item in case it's unavailability. Possible values: [ITEM_REMOVAL, PARTNER_CHOSEN_SUBSTITUTION, CANCEL_ORDER.

Failed Get active orders response body example:

{
  "error": {
    "message": "restaurant was not found for provided external restaurant ID and partner ID",
    "code": "not_found"
  }
}
Response Code Error Code
400 bad_request
404 not_found

Update order items availability

Allows to update the quantities for order items. The endpoint accepts amendments for multiple items in a single call. It is recommended that the integrating partner batches all the substitutions for an order in a single call of this endpoint in order to avoid receiving a rate limit exceeded error.

PUT https://partners.deliveroo.com/api/v2/picking/orders/:order_id

Rate Limit

There's a rate limit of 1 requests per minute. If you get over the limit, you'll get "Too many requests" error.

Update order item quantities request body examples:

{
  "item_amendments": [
    {
      "amends": {
        "id": "XXX",
        "quantity": 2
      },
      "final_quantity": 1
    },
    {
      "amends": {
        "id": "YYY",
        "quantity": 4
      },
      "final_quantity": 2
    }
  ]
}

Request restrictions

Update order item quantities response body example:

{
  "order_id": "gb:28588c69-efc7-479f-b692-168fa910b19c",
  "status": "PLACED",
  "total_price": {
    "currency_code": "GBP",
    "fractional": 1400
  },
  "subtotal_price": {
    "currency_code": "GBP",
    "fractional": 1400
  },
  "total_after_substitutions": {
    "currency_code": "GBP",
    "fractional": 1400
  },
  "subtotal_after_substitutions": {
    "currency_code": "GBP",
    "fractional": 1400
  },
  "substituted_items_total": {
    "currency_code": "GBP",
    "fractional": 1400
  }
}

Failed Update order item quantities response body example:

{
  "error": {
    "message": "error: item[dbd71c82-8076-4eae-af52-7cf9c18ccef6] final quantity must be equal to or greater than 0",
    "code": "bad_request"
  }
}
Response Code Error Code
500 unknown_error
404 not_found
400 bad_request

Make amendments

Allows to make amendments to order items. The endpoint accepts amendments for multiple items in a single call. It is recommended that the integrating partner batches all the substitutions for an order in a single call of this endpoint in order to avoid receiving a rate limit exceeded error.

POST https://partners.deliveroo.com/api/v1/picking/orders/:order_id/amendments

Rate Limit

There's a rate limit of 1 requests per minute. If you get over the limit, you'll get "Too many requests" error.

How it works

Request parameters (item amendments)

Make amendments request body example:

{
  "item_amendments": [
    {
      "amends": {
        "id": "XXX",
        "quantity": 2
      },
      "final_quantity": 1
    },
    {
      "amends": {
        "id": "YYY",
        "quantity": 1
      },
      "final_quantity": 1,
      "substitution_id": "ZZZ"
    }
  ]
}

Parameter Description
amends.id string
Identifier for the order item to amend.
amends.quantity int
Quantity of order item that should be amended.
final_quantity int
Updated quantity of order item.
substitution_id string
Identifier of a substitution. Should be provided only when substituting order item. It's available in response of get allowed item substitutions endpoint

Response parameters

Make amendments response body example:

{
    "id": "gb:28588c69-efc7-479f-b692-168fa910b19c",
    "location_id": "thrr13z1v3ut-UpgTOHtOgMY",
    "display_id": "1244",
    "status": "PLACED",
    "status_log": [
      {
        "at": "2021-04-07T10:11:49.044Z",
        "status": "PENDING"
      },
      {
        "at": "2021-04-07T10:11:49.079Z",
        "status": "PLACED"
      }
    ],
    "rejection_reason": "string",
    "allergy_note": "string",
    "asap": true,
    "prepare_for": "2021-04-07T10:22:00Z",
    "customer_order_count": 1,
    "order_type": "delivery",
    "subtotal": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "subtotal_after_substitutions": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "substituted_items_total": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "total_price": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "total_after_substitutions": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "offer_discount": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "item_substitution": "",
    "items": [
      {
        "id": "XXX-2",
        "pos_item_id": "string",
        "quantity": 1,
        "original_quantity": 2,
        "final_quantity": 1,
        "name": "string",
        "operation_name": "string",
        "total_unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "discount_amount": {
          "currency_code": "GBP",
          "fractional": 0
        },
        "modifiers": [
          {
            "pos_item_id": "string",
            "quantity": 1,
            "name": "string",
            "operation_name": "string",
            "total_unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            },
            "unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            }
          }
        ],
        "amends": {
          "quantity": 2,
          "id": "XXX",
          "amendment_type": "SUBSTITUTION"
        },
        "original": {
          "quantity": 2,
          "id": "XXX",
          "amendment_type": "SUBSTITUTION"
        },
        "allowed_actions_if_items_are_unavailable": [
          "ITEM_REMOVAL",
          "PARTNER_CHOSEN_SUBSTITUTION",
          "CANCEL_ORDER"
        ]
      },
      {
        "id": "YYY-2",
        "pos_item_id": "string",
        "quantity": 1,
        "original_quantity": 1,
        "final_quantity": 1,
        "name": "string",
        "operation_name": "string",
        "total_unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "discount_amount": {
          "currency_code": "GBP",
          "fractional": 0
        },
        "modifiers": [
          {
            "pos_item_id": "string",
            "quantity": 1,
            "name": "string",
            "operation_name": "string",
            "total_unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            },
            "unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            }
          }
        ],
        "amends": {
          "quantity": 1,
          "id": "YYY",
          "amendment_type": "SUBSTITUTION"
        },
        "original": {
          "quantity": 1,
          "id": "YYY",
          "amendment_type": "SUBSTITUTION"
        },
        "allowed_actions_if_items_are_unavailable": [
          "ITEM_REMOVAL",
          "PARTNER_CHOSEN_SUBSTITUTION",
          "CANCEL_ORDER"
        ]
      },
      {
        "id": "YYY-3",
        "pos_item_id": "string",
        "quantity": 1,
        "original_quantity": 1,
        "final_quantity": 1,
        "name": "string",
        "operation_name": "string",
        "total_unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "discount_amount": {
          "currency_code": "GBP",
          "fractional": 0
        },
        "modifiers": [
          {
            "pos_item_id": "string",
            "quantity": 1,
            "name": "string",
            "operation_name": "string",
            "total_unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            },
            "unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            }
          }
        ],
        "refactors": {
          "quantity": 1,
          "id": "YYY",
          "original_id": "YYY"
        },
        "allowed_actions_if_items_are_unavailable": [
          "ITEM_REMOVAL",
          "PARTNER_CHOSEN_SUBSTITUTION",
          "CANCEL_ORDER"
        ]
      }
    ],
    "archived_items": [
      {
        "id": "XXX",
        "pos_item_id": "string",
        "quantity": 2,
        "original_quantity": 2,
        "final_quantity": 2,
        "name": "string",
        "operation_name": "string",
        "total_unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "discount_amount": {
          "currency_code": "GBP",
          "fractional": 0
        },
        "modifiers": [
          {
            "pos_item_id": "string",
            "quantity": 1,
            "name": "string",
            "operation_name": "string",
            "total_unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            },
            "unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            }
          }
        ],
        "archived_reason": "AMENDMENT",
        "allowed_actions_if_items_are_unavailable": [
          "ITEM_REMOVAL",
          "PARTNER_CHOSEN_SUBSTITUTION",
          "CANCEL_ORDER"
        ]
      },
      {
        "id": "YYY",
        "pos_item_id": "string",
        "quantity": 2,
        "original_quantity": 2,
        "final_quantity": 2,
        "name": "string",
        "operation_name": "string",
        "total_unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "discount_amount": {
          "currency_code": "GBP",
          "fractional": 0
        },
        "modifiers": [
          {
            "pos_item_id": "string",
            "quantity": 1,
            "name": "string",
            "operation_name": "string",
            "total_unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            },
            "unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            }
          }
        ],
        "archived_reason": "AMENDMENT",
        "allowed_actions_if_items_are_unavailable": [
          "ITEM_REMOVAL",
          "PARTNER_CHOSEN_SUBSTITUTION",
          "CANCEL_ORDER"
        ]
      }
    ],
    "updated_at_epoch_ms": 1643736125493
}
Parameter Description
id string
Order's unique identification.
location_id string
Partner identifier.
display_id string
The customer facing 4-digit order number.
status string
Latest status of the order
status_log array
Append-only log of order status changes
rejection_reason string
Indicates the reason in case the order is rejected
allergy_note string
A plain text field in which the customer can specify dietary restrictions and other special requests.
asap boolean
Whether the order is an ASAP order.
prepare_for datetime
The time by which the order must be prepared.
customer_order_count int
Number of orders made by related customer in this place.
order_type string
delivery / pickup Order type.
subtotal money
The price of all of the items in the order.
subtotal_after_substitutions money
The price of all the available items in the order after taking into account any item substitutions.
substituted_items_total money
The total price of the substituted items..
total_price money
The total price of the order, including delivery but taking into account only the available items after making any substitutions.
total_after_substitutions money
The total price of all the available items in the order after taking into account any item substitutions.
offer_discount money
The offer discount used when the order was placed.
item_substitution - deprecated string
Indicates the customer's preference for item substitution for this order. Possible values: [no_substitutions, allow_substitutions]
This attribute is deprecated. You can use the allowed_actions_if_items_are_unavailable attribute of OrderItem for this purpose.
items array[OrderItem]
List of items in the order
archived_items array[OrderItem]
List of items that were refactored or amended
updated_at_epoch_ms int
Time at which this order was last updated (represented as unix time with ms precision)
OrderItem
id string
Order's unique identification.
pos_item_id string
Partner identifier, aka PLU.
quantity int
This holds the final amount of units expected to be delivered.
name string
Customer-facing name of the menu item..
operational_name string
Restaurant-facing name of the menu item.
total_unit_price money
Price for one of the items without Deliveroo fees
unit_price money
Price for one of this item with Deliveroo fee
discount_amount money
The discount amount on the item
modifiers array[OrderItem]
Contains any customizations to the menu item. These entities take the same shape as a top level menu item.
archived_reason string
Keeps the reason why this item is archived. Possible values: [REFACTORING, AMENDMENT, UNDO]
amends object
Keeps a reference to the order item that this item amends. It will be NULL if this item is not an amendment.
amends.quantity int
Quantity of order item that this item amends.
amends.id string
Identifier of the order item that this item amends.
amends.amendment_type string
Type of amendment. Possible values: [REMOVAL, SUBSTITUTION]
original object
Keeps a reference to the original order item that this item relates to. It is meant to keep a direct relationship between each item in the order and the original item/quantity it refers to. Cutting short all of the intermediate refactoring / amendment / undo operations. It will be NULL if this item is not an amendment.
original.quantity int
Quantity of the original order item.
original.id string
Identifier of the original order item.
original.amendment_type string
Type of amendment. Possible values: [REMOVAL, SUBSTITUTION]
refactors object
Refactors keeps a reference to the order item that this item amends. Refactors is NULL if the item was not refactored. This allows to keep the relationship between original order_items and their refactoring items.
refactors.quantity int
Quantity of the refactored order item.
refactors.id string
Identifier of the refactored order item.
refactors.original_id string
Original identifier of refactored order item.
allowed_actions_if_items_are_unavailable array
Keeps applicable actions for this order item in case it's unavailability. Possible values: [ITEM_REMOVAL, PARTNER_CHOSEN_SUBSTITUTION, CANCEL_ORDER.

Failed Make amendments response body example:

{
  "error": {
    "message": "order status is not \"Placed\"",
    "code": ""
  }
}
Response Code Error Code
500 unknown_error
404 not_found
400 bad_request

Get allowed item substitutions

This API endpoint allows the partners to search for the allowed item substitutions for a given order item.

GET https://partners.deliveroo.com/api/v1/picking/orders/:external_id/substitute/:order_item_id?needle=<needle>&limit=<limit>&quantity=<quantity>

Request parameters

Parameter Description
external_id string
Identifier for the order.
order_item_id string
ID of the item to be substituted.
needle string
Search word describing the desired item(s) to be used as a substitute.
quantity uint
Quantity to substitute.
limit uint
Number of substitutions to return.

Response parameters

A successful response body example:

[
  {
    "substitution_id": "substitution_id_1",
    "plu": "plu-1",
    "quantity": 5,
    "category": "category-1",
    "name": "name-1",
    "operational_name": "operational-name-1",
    "price": 100
  },
  {
    "substitution_id": "substitution_id_2",
    "plu": "plu-2",
    "quantity": 5,
    "category": "category-1",
    "name": "name-2",
    "operational_name": "operational-name-2",
    "price": 110
  }
]
Parameter Description
substitution_id string
Identifier of substitution used for amending order item.
plu string
PLU (price lookup code) of the substitution item.
quantity number
Quantity of items that can be used for substitution.
category string
Category name of the substitution item.
name string
Name of the substitution item.
operational_name string
Operational name the restaurant uses in-house for the substitution item.
price number
Price in minor units of the currency.

A failed response body example:

{
  "error": {
    "message": "invalid limit param",
    "code": "bad_request"
  }
}
Response Code Error Code
500 unknown_error
404 not_found
400 bad_request

Webhook callbacks

Authentication

Upon registration, your account manager will provide you with a webhook-secret. This secret value will differ from the api-secret from your credentials. The webhook secret and a sequential globally unique identifier (GUID) are used to generate a Hash-based message authentication code (HMAC) of the order payload.

When you receive a POST webhook request, you will be able to compute a digest and verify that it’s a genuine, authorized request sent from Deliveroo.

Example webhook headers:

X-Deliveroo-Sequence-Guid: 16c3ec58343
X-Deliveroo-Hmac-Sha256: 2bf0ade9f5c33b266a8be1287d5af41864bc3a77ee9c53c75af979abc9a79b9e

Example to generate HMAC:

package main

import (
  "crypto/hmac"
  "crypto/sha256"
  "fmt"
)

func main() {
  webhook_secret := []byte("webhook-secret")
  sequence_guid := "deliveroo-sequence-guid"
  payload := "our-payload"

  mac := hmac.New(sha256.New, webhook_secret)
  message := fmt.Sprintf("%s %s", sequence_guid, payload)
  mac.Write([]byte(message))
  expected := mac.Sum(nil)

  fmt.Printf("%x", expected)
}
require "openssl"

webhook_secret = "webhook-secret"
sequence_guid = "deliveroo-sequence-guid"
payload = "our-payload"

digest = OpenSSL::Digest.new('sha256')
message = "#{sequence_guid} #{payload}"
expected = OpenSSL::HMAC.hexdigest(digest, webhook_secret, message)

puts expected

Delivery failure and retries

A successful webhook callback occurs when the server responds with an HTTP 2xx success range; any other HTTP status or a timeout will result in a retry.

Our servers will retry failed webhook callbacks applying exponential back-off delays and circuit breaking when failures are successive in a short amount of time.

When the circuit breaker is tripped, the total number of requests per minute is significantly reduced until the endpoint appears healthy again.

For order statuses, we "give up" and discard the event callback after 30 minutes.

Order status callback

The Order status notification webhook will be called from Deliveroo when an order is created in Deliveroo. This webhook is triggered on the following events during the order lifecycle:

Status Description
PLACED The order was created.
ACCEPTED The partner accepted the order.
REJECTED The partner rejected the order.
CANCELLED The partner cancelled the order.

Please notice that while every attempt is made to make callbacks in the order they occurred and in a timely manner, neither can be absolutely guaranteed. It is also possible to receive the same callback more than once.

HTTP Request

Order status callback example webhook notification:

{
  "event": "order.status_update",
  "order": {
    "id": "gb:28588c69-efc7-479f-b692-168fa910b19c",
    "location_id": "thrr13z1v3ut-UpgTOHtOgMY",
    "display_id": "1244",
    "status": "PLACED",
    "status_log": [
      {
        "at": "2021-04-07T10:11:49.044Z",
        "status": "PENDING"
      },
      {
        "at": "2021-04-07T10:11:49.079Z",
        "status": "PLACED"
      }
    ],
    "rejection_reason": "string",
    "allergy_note": "string",
    "asap": true,
    "prepare_for": "2021-04-07T10:22:00Z",
    "customer_order_count": 1,
    "order_type": "delivery",
    "subtotal": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "subtotal_after_substitutions": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "substituted_items_total": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "total_price": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "total_after_substitutions": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "offer_discount": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "bag_fee": {
      "currency_code": "GBP",
      "fractional": 1400
    },
    "item_substitution": "no_substitutions",
    "items": [
      {
        "id": "string",
        "pos_item_id": "string",
        "quantity": 2,
        "name": "string",
        "operation_name": "string",
        "total_unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "unit_price": {
          "currency_code": "GBP",
          "fractional": 1400
        },
        "discount_amount": {
          "currency_code": "GBP",
          "fractional": 0
        },
        "modifiers": [
          {
            "pos_item_id": "string",
            "quantity": 1,
            "name": "string",
            "operation_name": "string",
            "total_unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            },
            "unit_price": {
              "currency_code": "GBP",
              "fractional": 140
            }
          }
        ]
      }
    ],
    "archived_items": [],
    "updated_at_epoch_ms": 1643736125493
  }
}

POST https://partner-server.com/partner-picking-order-status-webhook

Parameter Description
event string
Event that triggered webhook
order Order
Order's details.
Order
id string
Order's unique identification.
location_id string
Partner identifier.
display_id string
The customer facing 4-digit order number.
status string
Latest status of the order
status_log array
Append-only log of order status changes
rejection_reason string
Indicates the reason in case the order is rejected
allergy_note string
A plain text field in which the customer can specify dietary restrictions and other special requests.
asap boolean
Whether the order is an ASAP order.
prepare_for datetime
The time by which the order must be prepared.
customer_order_count int
Number of orders made by related customer in this place.
order_type string
delivery / pickup Order type.
subtotal money
The price of all of the items in the order.
subtotal_after_substitutions money
The price of all the available items in the order after taking into account any item substitutions.
substituted_items_total money
The total price of the substituted items..
total_price money
The total price of the order, including delivery but taking into account only the available items after making any substitutions.
total_after_substitutions money
The total price of all the available items in the order after taking into account any item substitutions.
offer_discount money
The offer discount used when the order was placed.
item_substitution - deprecated string
Indicates the customer's preference for item substitution for this order. Possible values: [no_substitutions, allow_substitutions]
This attribute is deprecated. You can use the allowed_actions_if_items_are_unavailable attribute of OrderItem for this purpose.
items array[OrderItem]
List of items in the order
archived_items array[OrderItem]
List of items that were refactored or amended
updated_at_epoch_ms int
Time at which this order was last updated (represented as unix time with ms precision)
OrderItem
id string
Order's unique identification.
pos_item_id string
Partner identifier, aka PLU.
quantity int
This holds the final amount of units expected to be delivered.
name string
Customer-facing name of the menu item..
operational_name string
Restaurant-facing name of the menu item.
total_unit_price money
Price for one of the items without Deliveroo fees
unit_price money
Price for one of this item with Deliveroo fee
discount_amount money
The discount amount on the item
modifiers array[OrderItem]
Contains any customizations to the menu item. These entities take the same shape as a top level menu item.
archived_reason string
Keeps the reason why this item is archived. Possible values: [REFACTORING, AMENDMENT, UNDO]
amends object
Keeps a reference to the order item that this item amends. It will be NULL if this item is not an amendment.
amends.quantity int
Quantity of order item that this item amends.
amends.id string
Identifier of the order item that this item amends.
amends.amendment_type string
Type of amendment. Possible values: [REMOVAL, SUBSTITUTION]
original object
Keeps a reference to the original order item that this item relates to. It is meant to keep a direct relationship between each item in the order and the original item/quantity it refers to. Cutting short all of the intermediate refactoring / amendment / undo operations. It will be NULL if this item is not an amendment.
original.quantity int
Quantity of the original order item.
original.id string
Identifier of the original order item.
original.amendment_type string
Type of amendment. Possible values: [REMOVAL, SUBSTITUTION]
refactors object
Refactors keeps a reference to the order item that this item amends. Refactors is NULL if the item was not refactored. This allows to keep the relationship between original order_items and their refactoring items.
refactors.quantity int
Quantity of the refactored order item.
refactors.id string
Identifier of the refactored order item.
refactors.original_id string
Original identifier of refactored order item.
allowed_actions_if_items_are_unavailable array
Keeps applicable actions for this order item in case it's unavailability. Possible values: [ITEM_REMOVAL, PARTNER_CHOSEN_SUBSTITUTION, CANCEL_ORDER.

Webhook configuration

Retrieve Picking API webhook configuration

This API endpoint allows the partners to retrieve their Picking API Webhook configuration for the integrator.

GET https://partners.deliveroo.com/api/v1/picking/webhooks

Retrieve webhook configuration response body example:

{
  "picking_status_url": "https://example.com/webhook",
  "has_unique_webhook_urls": false
}

Configure Picking API webhook

This API endpoint allows the partner to configure the Picking API webhook URL for the integrator.

HTTP request

PUT https://partners.deliveroo.com/api/v1/picking/webhooks

Request parameters

Parameter Description
picking_status_url string
The single webhook for the integrator.
has_unique_webhook_urls boolean
Whether every partner (within an integrator) should be able to have a different webhook.

Configure webhook request body example:

{
  "picking_status_url": "https://example.com/webhook",
  "has_unique_webhook_urls": false
}

Configure webhook response body example:

{
  "picking_status_url": "https://example.com/webhook",
  "has_unique_webhook_urls": false
}

Failed Configure webhook response body example:

{
  "error": {
    "message": "URLs must start with https://",
    "code": "bad_request"
  }
}
Response Code Error Code
400 bad_request

Partner Webhook configuration

Partner webhook configuration will be used in case has_unique_webhook_urls flag is enabled.

Retrieve webhook configuration for a partner

This API endpoint allows the partners to retrieve their Picking API Webhook configuration.

GET https://partners.deliveroo.com/api/v1/picking/brands/:brand_id/webhooks

Request parameters

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).

Retrieve webhook configuration response body example:

{
  "picking_status_url": "https://example.com/webhook"
}

Failed Configure webhook response body example:

{
  "error": {
    "message": "restaurant brand does not exist",
    "code": "not_found"
  }
}
Response Code Error Code
404 not_found

Configure Picking API webhook for a partner

This API endpoint allows the partner to configure the Picking API webhook url.

HTTP request

PUT https://partners.deliveroo.com/api/v1/picking/brands/:brand_id/webhooks

Request parameters

Parameter Description
brand_id string
The unique identifier for the brand (Deliveroo's integration team will provide this).

Configure webhook request body example:

{
  "picking_status_url": "https://example.com/webhook"
}

Configure webhook response body example:

{
  "picking_status_url": "https://example.com/webhook"
}

Failed Configure webhook response body example:

{
  "error": {
    "message": "restaurant brand does not exist",
    "code": "not_found"
  }
}
Response Code Error Code
400 bad_request
404 not_found

Release Notes

6 Sep 2022 - Updated request details for the "Update order items availability" endpoint.

1 Aug 2022 - Payload field item_substitution is deprecated.

Frequently Asked Questions

Q: Can I turn off the 'Scheduled for later' option for all my integrations

A: Yes, you can choose to disable scheduled orders. The restaurant will need to contact their Deliveroo account manager or reach out to email our Restaurants team.

Q: Can I disable the 'notes' field on my integrations?

A: Yes, you can choose to disable 'notes'. The restaurant will need to contact their Deliveroo account manager or reach out to our Restaurants team.

Q: Can I set operating hours of the restaurant from the API?

A: Yes, you can control opening and closing hours via the Site API.

Q: Can I open or close a restaurant using the API?

A: Yes, you can control your restaurant opening and closing via the Site API..

Q: Can I push a discount on a menu via the API?

A: No, you cannot configure discounts via the API. Restaurants can run offers and promotions from Marketer in their Restaurant Hub Portal.

NOTE that item-specific discounts, free item, and PLUS offers do not work with all POS integrations and need to be tested separately in advance.

Q: Can I push a site to be integrated via the API?

A: No, you cannot push sites to integrate directly to the API. You will need to submit an integration request on the form you’ve been previously provided.

Q: How long does it take to complete an integration?

A: POS integrations take approximately 4-6 weeks to complete.

Menu integrations take approximately 1-2 weeks to complete.

A simultaneous POS and Menu integration takes approximately 4-6 weeks to complete.

Q: If I change the menu, does that deactivate the integration?

A: No, the integration stays enabled until you ask someone from the Integrations Team to disable it.

Q: Do I need a tablet if I have an integration?

A: Yes - every restaurant on Deliveroo is required to have a tablet even if integrated. We do not currently offer a tabletless integration.