Skip to content

Latest commit

 

History

History
86 lines (60 loc) · 2.69 KB

CONTRACT.md

File metadata and controls

86 lines (60 loc) · 2.69 KB

Meeting Room Booking API — Contract v1

This document is the source of truth for the API. All bodies are JSON.

Rooms

The service starts with three rooms. Rooms cannot be created or changed.

id name capacity
mistborn Mistborn 4
martian The Martian 8
stormlight Stormlight 12

GET /rooms

200 — [{ "id": "mistborn", "name": "Mistborn", "capacity": 4 }, ...]

Time rules

  • Request times are ISO 8601 strings with an offset: 2026-10-14T09:00:00Z or 2026-10-14T11:00:00+02:00. A time without an offset is invalid.
  • Response times are always UTC, in the form 2026-10-14T09:00:00Z.
  • A booking covers the half-open interval [start, end). A booking that ends at 10:00 and a booking that starts at 10:00 do not overlap.
  • start and end must be on a 15-minute grid (minutes 00, 15, 30, 45; seconds 0).
  • start must be before end. The maximum duration is 4 hours.

Bookings

POST /bookings

Request:

{ "roomId": "mistborn", "title": "Weekly sync", "start": "2026-10-14T09:00:00Z", "end": "2026-10-14T10:00:00Z", "attendees": 3 }

The service checks the request in this order:

  1. Body shape: all fields present, title a non-empty string, attendees an integer >= 1, times valid ISO 8601 with an offset. Else 422.
  2. Room exists. Else 404.
  3. Booking rules: the time rules above, attendees <= capacity. Else 422.
  4. No overlap with an existing booking in the same room. Else 409.

Responses:

Status Body
201 { "id": "<string>", "roomId": "mistborn", "title": "Weekly sync", "start": "2026-10-14T09:00:00Z", "end": "2026-10-14T10:00:00Z", "attendees": 3 }
404 { "error": "room_not_found" }
409 { "error": "conflict", "conflictingBookingId": "<id>" }
422 { "error": "validation_failed", "message": "<text>" }

Invalid JSON also gives 422.

DELETE /bookings/:id

Status Body
204 (empty)
404 { "error": "booking_not_found" }

Availability

GET /rooms/:id/availability?date=YYYY-MM-DD

Returns the free intervals of the room for the UTC day [date 00:00Z, next day 00:00Z). Intervals are sorted, do not overlap, and are not empty.

200:

{
  "roomId": "mistborn",
  "date": "2026-10-14",
  "free": [
    { "start": "2026-10-14T00:00:00Z", "end": "2026-10-14T09:00:00Z" },
    { "start": "2026-10-14T10:00:00Z", "end": "2026-10-15T00:00:00Z" }
  ]
}
Status Body
404 { "error": "room_not_found" }
422 { "error": "validation_failed", "message": "<text>" } — date missing or not a real YYYY-MM-DD date

Use the provided freeSlots / free_slots function to compute free.