Skip to main content

Resource add-ons API

A resource add-on is an add-on backed by a bookable resource, such as a party room or a sauna. It has its own time window before, during or after the main activity, and its own duration and pricing rules.

The link between an add-on and a resource is a resource add-on configuration. You manage configurations with the admin API, and you can read them and check their availability with the public API.

Booking resource add-ons is not supported yet

You cannot currently add a resource add-on to a booking through the public API. The booking widget hides the step, and resource add-ons are not included in the booking price. Use the endpoints on this page to set up configurations and to check availability only.

Admin: manage configurations​

All admin endpoints need a staff JWT with the admin:write permission.

MethodPathDescription
GET/api/v1/admin/addons/{addonId}/resourcesList the configurations for an add-on.
POST/api/v1/admin/addons/{addonId}/resourcesLink a resource to an add-on.
GET/api/v1/admin/addons/{addonId}/resources/{configId}Get one configuration.
PATCH/api/v1/admin/addons/{addonId}/resources/{configId}Update a configuration.
DELETE/api/v1/admin/addons/{addonId}/resources/{configId}Remove a configuration.
GET/api/v1/admin/resources/{resourceId}/addon-configsList the configurations that use a resource.

The list endpoint accepts the query parameters resourceId, isActive and includeResource.

Configuration fields​

FieldTypeDescription
resourceIdstringRequired on create. The resource that is booked.
durationModestringFIXED (default), SELECTABLE or CUSTOM. See below.
fixedDurationMinsintegerDuration for FIXED.
selectableDurationsinteger[]Allowed durations for SELECTABLE, for example [30, 60, 90].
minDurationMinsintegerShortest duration for CUSTOM.
maxDurationMinsintegerLongest duration for CUSTOM.
durationStepMinsintegerStep for CUSTOM, for example 15.
pricingModestringFLAT, PER_HOUR, PER_PERSON or COMPOSITE. See below.
flatPricedecimalPrice for FLAT.
perHourPricedecimalHourly price for PER_HOUR.
perPersonPricedecimalPer-person price for PER_PERSON and COMPOSITE.
basePricedecimalBase fee for COMPOSITE.
allowBeforebooleanThe resource can be booked before the activity.
allowDuringbooleanThe resource can be booked during, or overlapping, the activity.
allowAfterbooleanThe resource can be booked after the activity.
bufferMinsBeforeintegerSet-up time blocked before the resource window.
bufferMinsAfterintegerClean-up time blocked after the resource window.
maxCapacityintegerCapacity override. Leave empty to use the resource's own capacity.
isActivebooleanInactive configurations are not offered.
sortOrderintegerDisplay order.

Duration modes​

ModeThe customer...Fields used
FIXEDgets one fixed duration.fixedDurationMins
SELECTABLEpicks one duration from a list.selectableDurations
CUSTOMpicks any duration in a range and step.minDurationMins, maxDurationMins, durationStepMins

Pricing modes​

ModePrice
FLATflatPrice, whatever the duration.
PER_HOURperHourPrice × duration in hours.
PER_PERSONperPersonPrice × party size.
COMPOSITEbasePrice + perPersonPrice × party size.

Public: read configurations and availability​

These endpoints need no login. Send your tenant ID in the x-tenant-id header.

MethodPathDescription
GET/api/v1/availability/resource-addons/configsConfigurations linked to a product, without availability.
GET/api/v1/availability/resource-addonsConfigurations that have capacity and a free window for a slot.
GET/api/v1/availability/resource-addons/{configId}/time-windowsThe time windows you can choose for one configuration.

List configurations for a product​

GET /api/v1/availability/resource-addons/configs?productId=p_demo
x-tenant-id: t_demo

The only query parameter is productId. The response is { "resourceAddons": [...] }; the item shape is described below.

List available resource add-ons for a slot​

GET /api/v1/availability/resource-addons?productId=p_demo&slotId=sl_123&partySize=8&activityStartsAt=2026-10-15T14:00:00Z&activityEndsAt=2026-10-15T15:00:00Z
x-tenant-id: t_demo
ParameterRequiredDescription
productIdYesThe main activity's product.
slotIdYesThe selected slot.
partySizeYesNumber of people.
activityStartsAtYesActivity start, ISO 8601.
activityEndsAtYesActivity end, ISO 8601.

Response:

{
"resourceAddons": [
{
"configId": "rac_party_room",
"addonId": "addon_party_room",
"addonName": "Party Room",
"resourceId": "res_party_room_1",
"resourceName": "Party Room A",
"resourceType": "ROOM",
"durationMode": "SELECTABLE",
"selectableDurations": [60, 90],
"pricingMode": "FLAT",
"displayPrice": "€120",
"flatPrice": 120,
"allowBefore": true,
"allowDuring": false,
"allowAfter": true,
"bufferBeforeMins": 15,
"bufferAfterMins": 15,
"maxCapacity": 20,
"partySize": 8,
"capacityAvailable": true,
"availableWindows": 4
}
]
}

Get time windows for one configuration​

GET /api/v1/availability/resource-addons/{configId}/time-windows?activityStartsAt=2026-10-15T14:00:00Z&activityEndsAt=2026-10-15T15:00:00Z&partySize=8
x-tenant-id: t_demo
ParameterRequiredDescription
activityStartsAtYesActivity start, ISO 8601.
activityEndsAtYesActivity end, ISO 8601.
partySizeYesNumber of people.
excludeBookingIdNoA booking to ignore when checking for conflicts.

Response:

{
"configId": "rac_party_room",
"resourceName": "Party Room A",
"addonName": "Party Room",
"timeWindows": [
{
"startsAt": "2026-10-15T15:00:00Z",
"endsAt": "2026-10-15T16:00:00Z",
"durationMins": 60,
"position": "AFTER",
"price": 120,
"available": true
}
]
}

position is BEFORE, DURING, AFTER or OVERLAP. When available is false, conflictReason says why.