Menu Product Configuration

Modifiers and modifier groups

To explain what modifiers and modifier groups are, consider the following example.

Say that a restaurant sells a product "Build your own pizza" and the restaurant wants to offer the first topping i.e., "Pepperoni" and also the ability to add extra topping "Bacon" and "Mushroom" which has a price.

In Deliverect, this will be modeled using modifiers and modifier groups. Each topping is a modifier, which will end up looking like this in the JSON sent in a menu push request:


  "modifiers": {
    "63578d7b678870d57eb70996": {
                    "name": "Pepperoni",
                    "productType": 2,
                    "plu": "PEPP-#O0#-",
                    "price": 0,
                        }
...
 "63578d7b678870d57eb7099d": {
                    "name": "Bacon",
                    "productType": 2,
                    "plu": "BAC-#O1#-",
                    "price": 100,
                        }   
...
"63578d7b678870d57eb7099f": {
                    "name": "Mushroom",
                    "productType": 2,
                    "plu": "MUSH-#O1#-",
                    "price": 100,

To group the different choices (modifiers), we create a modifier group. The group should have a customer-facing name (e.g., "Choose your First Topping")

The IDs of the modifiers corresponding to each topping are in the subProductsarray,

"modifierGroups": {

"63578d7b678870d57eb7099b": {
                    "name": "Choose your First Two Toppings",
                    "productType": 3,
  ...
                    "plu": "FREE-TOP",
                    "subProducts": [
                        "63578d7b678870d57eb70996",
                        "63578d7b678870d57eb70997",
                        "63578d7b678870d57eb70998",
                        "63578d7b678870d57eb70999",
                        "63578d7b678870d57eb7099a"
                    ],
                    "max": 2,
                    "min": 2,
                    "multiMax":2
...
                },

Modifier groups can also contain regular products "productType": 1 inside apart from modifiers "productType": 2.

Minimum, Maximum, Multi-Max and

In the example above, you will see the "max", "min" and "multiMax" attributes, these represent certain ordering constraints set when ordering from this group of options.

Certain scenarios as follows can be expected, depending on different configurations of these attributes;

Optional Choice

Where a choice is optional, then you should expect"min": 0to be set.

Required Choice

Where a choice is required, then you should expect"min": 1to be set

Maximum Total Limit (per group)

If customers want to limit the total number of extra toppings to five within any one product selection, you would expect "max": 5.

Maximum Total Limit (per individual option)

If customers want to limit the total number of any one topping to two you would expect "multiMax": 2

Nested Modifiers

These are modifiers that are part of a modifier group which is nested within another modifier group. In the specific example, Chicken Sate, you can select your dish and add a modifier from Rice or Noodles selection. After you do that, you will be asked to choose additional modifiers, like the sate or hot sauce which are nested.

  • Product Type: 1 Chicken Sate
    • Product Type 3: Rice Selection
      • Product Type 2: White Rice
        • Product Type 3: Choose a Sauce
          • Product Type 2: Sate Sauce
          • Product Type 2: Hot Sauce

Bundles

Bundles groups together product options in much the same way a modifier group, groups together modifiers. Also, like a modifier group, a bundle could never be sold on it's own, as it will always belong within a subProducts array.

Using the example below, the product "Burger Combo (Drink Not Included)" represents a typical meal deal which includes the bundle "Burger Selection" that consists of three burger options. It could include any number of bundles and also can be configured with additional modifier groups e.g. upsells like 'Add a Drink? (not included)'

Note that each burger option is a product type 1, which means that these burgers could be available to order on their own elsewhere in a menu where they would have their own price set.

As it is set within a bundle however, Deliverect will ensure that channels receive them with zero price. The only price that would then apply is the cost of the Burger Combo itself *see note below on nesting modifier groups.

The first part of the JSON will look like the following, where the bundle is set within the subProducts array.

"6336b884013cfff666ab5131": {
    "name": "Burger Combo (Drink not Included)",
    "productType": 1,
...
                    "plu": "P-BRGR",
    "price": 950,
...
                    "subProducts": [
        "6336b884013cfff666ab5132",
    ],
  ...
},

The bundle "Burger Selection" is then specified as below and which can include minimum maximum and multiMax attributes.

"bundles": {
    "6336b884013cfff666ab5132": {
        "name": "Burger Selection",
        "productType": 4,
        "plu": "BNDL-BRG",
        "subProducts": [
            "6336b884013cfff666ab5133-B",
            "6336b884013cfff666ab5134-B",
            "6336b884013cfff666ab5135-B"
        ],
        "max": 1,
        "min": 1,
    },
    "6336b884013cfff666ab5134-B": {
        "name": "Cheeseburger",
        "productType": 1,
        "plu": "P-BURG-CHE###",
        "price": 0,
    }
...

📘

Bundle Products > Modifier Groups

Although bundle products will default to being zero priced items, modifier groups can be set which offer additional priced options e.g."Fries Selection" where different product options can be sold.

subProducts, parentId, PLU

You can find the products that exist for each category and/or group (bundles, modifier groups) under subProducts. Do not reference the parentId parameter as this is deprecated.

Default Quantity (pre-selected)

An attribute "defaultQuantity" can be included to a sub-item to instructs whether it should be 'pre-selected'.

e.g. where "defaultQuantity": 1, or any quantity > 0 the channel should ensure the item is pre-selected. Typically this will only display '1', although higher default quantities can also be set if pre-selecting a specific quantity is supported.

Multi-select modifiers

In some cases, it must be possible for modifiers in a modifier group to be selected more than once.

Have a look at the JSON menu push example. Look for the modifier group with PLU 2744, more specifically, how max and multiMax are used.

The max field gets a value of two, which indicates the maximum number of modifiers. As there are only two modifiers in the group, this in itself wouldn't make much of a difference when the modifiers are only selectable once.

Adding multiMax indicates that modifiers in this modifier group should be selectable more than once. Because it has a value of two, each modifier should be selectable at most two times.

Maximum Total Limit per Product

Sometimes, merchants would like to restrict the number of products that can be sold within one order. For example, think of medicine products where only one of the medications is allowed to be sold per customer order. This will show in the menu push under the product information with the multiMax value. For example, "multiMax": 1, under a product (not a modifier or option), means that this product can only be sold one time in a given order basket.

To test this scenario, you can add this in the menu sample of your test account, using the Deliverect menu builder. For example, if the product can only be sold one time, then go to Edit menu and edit the product by adding 1 under "Max order limit".

Bottle Deposit

In some countries it is mandatory to charge a deposit for glass bottles and to record this in a POS.

Deliverect can support this by allowing a single 'Bottle Deposit' product with unique PLU to exist in an account.

With this PLU mapped within the POS settings, any order for a product stored with bottledeposit will then also add the specific bottle deposit product to the order sent to the POS.

A channel receiving a product with a bottle deposit will not need to make additional calulcations, as the product price will be inclusive of any deposit price specified. The deposit amount is included for reference and can be displayed to end-users if required "bottleDepositPrice"

"products": {
            "6**f578fa205bc3eca854***": {
                "name": "Ginger Beer",
                "description": "Australia's favourite ginger beer!",
       					 ...
                "_id": "6**f645fa205bc3eca854***",
                "account": "6**f894fa205bc3eca854***",
                "location": "6**f241fa205bc3eca854***",
                "productType": 1,
                "plu": "DRNK-03",
                "multiply": 1,
                 ...
                "price": 500,
                "bottleDepositPrice": 100,
                 ...
            }
        },

Variants

A product may have different price based on a variance. For example, chicken tenders may have different price based on the size, 3, 6 or 9 pieces. In this case in the menu push request, you will find the main product with its own price, and the modifiers will come with an additional price. The first modifier that is the smallest size will have a price of 0 and the rest of the modifiers will have their own price that is added to the price product.

You will see in the payload that the main item "Chicken Tenders" will have an attribute "isVariant": true

The modifier group "How many pieces" will have the attribute "isVariantGroup": true

For your implementation, this is the same as any product with modifiers. If the ordering customer selects Chicken Tenders of 3 pieces, they will pay 8 euro and if they select 6 pieces, they will pay 11 euro (8+3).

Product tags: consumable types and allergens

A product can have one or more product tag and these are stored with key productTags. Product tags are used to indicate consumable types and or allergens, which your channel should show in menus to customers.

To retrieve a list of up to date tags see the endpoint GET Allergens & Tags

▶ See Product Tags

See example snippet below which shows a "Chicken Sate" product as containing Nuts and Eggs via the array of productTags

},
            "62334e600cf177afb8bad2b1": {
                "name": "Chicken Sate",
                "description": "Product contains nuts",
                ...
                ],
                "productTags": [
                    104,
                    109
                ],
                "posCategoryIds": [
                    "SATE"
                ]
                ...
            },

Calories

If the calories are sent from the POS or added in Deliverect, it will be sent to channel in Menu Push as per the sample below

ParameterMeaningtype
caloriesThis is the base calorie amount, where a maximum calories is set, this should be interpreted as the 'minimum'integer or float
caloriesRangeHighThe maximum calorie amount of an iteminteger or float
},
            "62334e600cf177afb8bad2b1": {
                    "name": "Cheeseburger",
                    "description": "Burger with Cheese",
                     ...
                    "calories": 500,
                    "caloriesRangeHigh": 750,
                    "price": 900,
                    ...
                }

Nutritional Information

If nutritional information is sent by the POS, you will also receive it for each product via the menu push. The unit of the values is gram.

Notice, that ingredients and additives are lists of strings. You may or may not receive food business information (fbo) depends on local regulation.

[
"products": {
...     "name": "Coca Cola",
        "beverageInfo": {
            "caffeine": 10,
            "alcohol": 0
        },
        "calories": 180,
        "caloriesRangeHigh": 0,
....
        "nutritionalInfo": {
            "fat": 3,
            "sugar": 10,
            "saturatedFat": 21,
            "carbohydrates": 10,
            "protein": 0,
            "salt": 0,
            "servingSize": {
                "amount": 330,
                "unitType": 1,
                "countUnitDescription": "ml"
            },
            "netQuantity": {
                "amount": 1,
                "unitType": 1,
                "countUnitDescription": "bottle"
            }
        },
        "packaging": {
            "count": 1,
            "reusable": false,
            "storageInstructions": "Keep refrigerated"
        },
        ....
        "productTags": [
            7,
            10,
            128
        ],
...
        "supplementalInfo": {
            "legalName": "Coke",
            "instructionsForUse": "Serve chilled",
            "ingredients": [
                "Carbonated Water",
                "Sugar"
            ],
            "additives": [
                "E150d - Sulphite ammonia caramel",
                "E338 - Phosphoric acid",
                "E951 - Aspartame"
            ],
            "prepackaged": true,
            "deposit": 15,
            "fbo": {
                "name": "Coca-Cola GmbH Germany",
                "address": "Stralauer Allee 4, 10245 Berlin, Germany"
            }
        },
...
    }
]