Create a Meeting Room
End to end flow for getting a meeting room into the system with working office hours. Three writes, in order:
- Create the bookable (the meeting room itself).
- Create the timeslot row (the schedule that defines office hours).
- Attach the timeslot to the bookable.
Without step 3 the timeslot exists but does not constrain the bookable, and POST /booking will accept any time on it. See Calendar and Availability for why.
1. Create the Bookable
POST /bookable
{
"name": "Meeting Room 1",
"description": "Glass walled room on the second floor, seats six.",
"owner_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"location_id": "b2c3d4e5-f6a7-8901-bcde-f23456789012"
}Response:
{
"data": {
"id": "c3d4e5f6-a7b8-9012-cdef-345678901234",
"name": "Meeting Room 1",
"description": "Glass walled room on the second floor, seats six.",
"owner_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"location_id": "b2c3d4e5-f6a7-8901-bcde-f23456789012",
"created_at": "2026-05-11T22:12:44.817293Z",
"updated_at": "2026-05-11T22:12:44.817293Z"
},
"count": 1
}Capture data.id as bookable_id for the next steps.
2. Create the Timeslot
POST /timeslot
{
"name": "Office Hours",
"description": "Mon to Fri, 08:00 to 18:00 Oslo time.",
"owner_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"schedule": {
"start_date": "2026-01-01T00:00:00Z",
"end_date": "2026-12-31T23:59:59Z",
"time_zone": "Europe/Oslo",
"available": true,
"pattern": {
"type": "weekly",
"interval": 1,
"days_of_week": [1, 2, 3, 4, 5],
"times": ["08:00/PT10H"]
}
}
}WARNING
available: true is required on a timeslot schedule. Omit it and the row stores available: false, which the booking engine reads as a blocking window. Every booking inside the time range then returns 409 Conflict with "outside of defined timeslots". See Schedule.
Response:
{
"data": {
"id": "d4e5f6a7-b8c9-0123-def4-567890123456",
"name": "Office Hours",
"description": "Mon to Fri, 08:00 to 18:00 Oslo time.",
"schedule": {
"id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"start_date": "2026-01-01T00:00:00Z",
"end_date": "2026-12-31T23:59:59Z",
"time_zone": "Europe/Oslo",
"available": true,
"pattern": {
"type": "weekly",
"interval": 1,
"days_of_week": [1, 2, 3, 4, 5],
"times": ["08:00/PT10H"]
}
},
"owner_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"created_at": "2026-05-11T22:14:28.192411Z",
"updated_at": "2026-05-11T22:14:28.192411Z"
},
"count": 1
}Capture data.id as timeslot_id.
3. Attach the Timeslot to the Bookable
POST /timeslot/{timeslot_id}/object
{
"object_id": "c3d4e5f6-a7b8-9012-cdef-345678901234",
"object_type": "public.bookable",
"priority": 0
}object_type is the schema qualified type. For meeting rooms this is always public.bookable. The same endpoint accepts public.bookable_type, claimius.location or claimius.organization to attach the same timeslot at a higher scope; the per bookable booking handler only honors timeslots attached directly to the bookable row, so for a meeting room with its own opening hours the right target is the bookable.
Response:
{
"data": {
"id": "e5f6a7b8-c9d0-1234-ef56-789012345678",
"timeslot_id": "d4e5f6a7-b8c9-0123-def4-567890123456",
"object_id": "c3d4e5f6-a7b8-9012-cdef-345678901234",
"object_type": "public.bookable",
"priority": 0,
"owner_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"created_at": "2026-05-11T22:15:10.384729Z",
"updated_at": "2026-05-11T22:15:10.384729Z"
},
"count": 1
}Verify
GET /bookable/{bookable_id}/available?start_date=2026-05-11T00:00:00Z&end_date=2026-05-18T00:00:00Z
The response should show Mon to Fri 08:00 to 18:00 Oslo open and the weekend closed. A booking inside those hours goes through; a booking outside them returns 409 Conflict.
See Book Resource for the booking call and List Bookings for reading what is already booked on the room.