Create a booking page
Makes a page that takes bookings at once. Only `name` is required.
Runs the real call on your workspace.
POST /booking-pages
Makes a page that takes bookings at once. Only name is required.
Example
Needs calendar:write and emails:send. Left to its defaults, a page is open on weekdays from 09:00 to 17:00, offers 30 minute meetings, asks for four hours of notice, and sends from the first address the person may send from.
curl -X POST "$OE/booking-pages" -H "$AUTH" -H 'content-type: application/json' -d '{ "name": "Intro call", "timezone": "Europe/Berlin", "config": { "description": "A first chat about your project.", "location": { "kind": "video", "value": "https://meet.example.com/hana" }, "rules": { "bufferAfterMinutes": 15 } }}'{ "object": "booking_page", "id": "bkp_5c1e9a7b3d2f48e6a0b4c7d1", "slug": "intro-call", "name": "Intro call", "status": "active", "url": "https://nextmail.sh/book/intro-call", "problem": null, "config": { "description": "A first chat about your project.", "hostName": "Hana Sato", "durations": [30], "location": { "kind": "video", "value": "https://meet.example.com/hana" }, "availability": { "timezone": "Europe/Berlin", "weekly": [ [], [{ "start": 540, "end": 1020 }], [{ "start": 540, "end": 1020 }], [{ "start": 540, "end": 1020 }], [{ "start": 540, "end": 1020 }], [{ "start": 540, "end": 1020 }], [] ], "overrides": [{ "date": "2026-12-24", "ranges": [] }] }, "rules": { "noticeMinutes": 240, "horizonDays": 60, "intervalMinutes": null, "bufferBeforeMinutes": 0, "bufferAfterMinutes": 15, "dailyLimit": null }, "approval": false, "fromEmail": "hana@acme.com", "notifyHost": true, "questions": [ { "id": "notes", "kind": "long-text", "label": "Anything we should know?", "required": false, "options": [] } ], "confirmation": "", "redirectUrl": "", "appearance": { "accent": "#2563eb", "theme": "auto", "showAvatar": true, "background": "default", "fonts": { "primary": null, "secondary": null }, "backgroundImage": null }, "guestChanges": { "cancel": true, "reschedule": true, "cutoffMinutes": 120 }, "busy": { "addresses": null, "subscriptions": true, "outOfOffice": true }, "seo": { "title": "", "description": "", "indexable": false }, "extraGuests": 0 }, "counts": { "upcoming": 3, "pending": 0 }, "away": [ { "address": "hana@acme.com", "startsAt": "2026-12-22T00:00:00.000Z", "endsAt": "2027-01-02T00:00:00.000Z" } ], "createdAt": "2026-10-13T07:00:05.870Z", "updatedAt": "2026-10-13T07:00:05.870Z"}Anything in config replaces the default for that setting. Inside location, availability, rules, appearance, guestChanges, busy and seo each field is set on its own, so the example changes one rule and keeps the rest.
Left out, slug is made from the name. A slug another page uses answers 409 booking_link_taken.
A link with characters it may not have, a sender the person may not send from, or a video meeting with no link answers 422 invalid_booking_page, and the message says which.
Google Workspace