Skip to main content

Bookings

Customer-facing booking endpoints. Every endpoint here calls requireSession, so a valid Better Auth session cookie is required. Bookings are scoped to the signed-in customer — you can only read or cancel your own.
Base URL: https://theroyalglow.in · Auth: Better Auth session; minimum role customer on all endpoints below (any authenticated user is at least a customer). Money is an integer in paise; dates are YYYY-MM-DD; times are HH:mm (24-hour). Requests without a session return UNAUTHENTICATED (401).

POST /api/bookings

Creates a booking request for the signed-in customer. The booking is created with status pending and a generated booking number. Pricing and total duration are computed server-side from the selected services (GST-inclusive paise), and endTime is derived from startTime + total duration. Minimum role: customer (requireSession)

Request body

Validated by createBookingSchema (@rgss/types).

Response

Returns 201 Created. The payload contains the new booking’s id, generated booking number, and status.
The booking number format is BK-{branchCode}-{YYMM}-{H|S}-{5 digits}H for salon, S for spa.

Errors

No active session.
Body fails createBookingSchema; branch not found or not operational; a service id is unknown, inactive, or a type mismatch; or no active staff is available.
Unexpected/transient failure. retryable: true.
All pre-condition failures (branch state, service existence/activeness, type mismatch, no available staff) are raised as badRequest, so they surface as VALIDATION_ERROR with a 400 — not as booking-domain codes.

GET /api/bookings

Lists all bookings for the signed-in customer, newest first. Each booking includes its services (the booking_service snapshot rows, ordered by displayOrder). Minimum role: customer (requireSession)

Response

Errors

No active session.
Unexpected/transient failure. retryable: true.

GET /api/bookings/[id]

Returns a single booking (with its services) owned by the signed-in customer. Minimum role: customer (requireSession)

Path parameters

If the booking does not exist or belongs to another customer, the handler returns 404 NOT_FOUND (not 403) so it never reveals which booking ids exist.

Response

Errors

No active session.
Booking does not exist or is not owned by the caller.
Unexpected/transient failure. retryable: true.

POST /api/bookings/[id]/cancel

Cancels a booking owned by the signed-in customer. Only bookings in status pending or confirmed can be cancelled. Sets status to cancelled and records the reason and timestamp. Minimum role: customer (requireSession)

Path parameters

Request body

The body is optional and validated by cancelBookingSchema. An empty or missing body is accepted.

Response

Errors

No active session.
Booking does not exist or is not owned by the caller.
Booking is not in a cancellable status (pending or confirmed) — e.g. already cancelled, completed, in_progress, no_show, or rejected.
Unexpected/transient failure. retryable: true.
Last modified on August 29, 2026