Hotel guides

Collecting traveller details

The traveller list on a booking has to mirror the search exactly — the same rooms, adults and children's ages — and name real people. Here's how to build it.

One traveller per guest you searched for

Send a travelers entry for every adult and child in the search, grouped into rooms with roomIndex. Room numbers count from 0 in the order of your occupancy array.

The search
"occupancy": [
  { "adults": 2, "childrenAges": [] },
  { "adults": 1, "childrenAges": [4, 9] }
]
The matching booking
"travelers": [
  { "title": "Ms",     "firstName": "Anna",  "lastName": "Smith", "email": "anna.smith@example.com", "phone": "+447700900123", "nationality": "GB", "roomIndex": 0 },
  { "title": "Mr",     "firstName": "Ben",   "lastName": "Smith", "roomIndex": 0 },
  { "title": "Mrs",    "firstName": "Priya", "lastName": "Shah",  "roomIndex": 1 },
  { "title": "Master", "firstName": "Dev",   "lastName": "Shah",  "type": "child", "age": 4, "roomIndex": 1 },
  { "title": "Miss",   "firstName": "Mira",  "lastName": "Shah",  "type": "child", "age": 9, "roomIndex": 1 }
]
  • The first traveller is the lead guest. Rooms are held in their name. Roave emails the confirmation to the booking's agent — for bookings made with an API key, the admin who created the key — not to the traveller. Send travellers their voucher yourself, or with email-client.
  • Children need type: "child" and the same age you searched with. A child searched as 9 must be booked as 9.
  • Order within a room doesn't matter, but every room must have exactly the adults and child ages you searched.

If the list doesn't match, the booking is refused before anything is charged:

Response · 400
{
  "data": null,
  "meta": {},
  "error": {
    "code": "traveler_manifest_mismatch",
    "message": "Traveler manifest must match each searched room and contain 3 adult(s) and 2 child(ren) with the searched ages",
    "details": []
  }
}

If the party has changed since the search, run a new search — prices can differ for a different party.

Always send the lead guest's email and phone

Some inventory can't be booked without a contact for the lead guest, and you can't tell from the rate which. Send both on travelers[0] for every booking. Without them some bookings return 400 supplier_contact_required.

Use the traveller's own contact details where you can. Hotels use them for arrival questions and changes on the day.

Real names only

Collect a real name for every guest before you book. Don't send placeholders such as “TBA”, “Guest 2” or the agent's own name: rooms and tickets are issued in the names you send, placeholders can be refused at check-in, and changing a name after booking isn't always possible.

Titles

Some inventory needs a title for the people it books, and refuses the booking without one. Send title as one of Mr, Mrs, Ms, Miss, Master or Dr:

  • Hotels: on every traveller when the rate row or the price-checked quote has requiresGuestTitle: true.
  • Activities and transfers: always on the lead traveller. The quote doesn't tell you which ones need it.
  • Flights: on every passenger.

A missing or unrecognised title returns 400 traveler_title_required before anything is charged; message says which travellers need one. Collecting a title for everyone is the simplest way to never see it.

Nationality and residency

The search's residency is the lead guest's passport country, and the booking's lead nationality should be the same. The API doesn't check this for you. Some rates are only sold to certain nationalities, and the hotel may check. If the lead guest changes to someone with a different passport, search again with the new residency.

Traveller fields

Only the fields below are accepted; anything else is rejected with 400 validation_error. Some product-specific fields are checked before anything is charged — titles, and for some flights the passport details — but not all of them for every rate. Always send every field your product needs (below); otherwise the booking can fail.

FieldDescription
firstNamestring, 1–60requiredGiven name as it appears on the traveller's ID.
lastNamestring, 1–60requiredFamily name as it appears on the traveller's ID.
emailstringlead travellerSend on travelers[0]. Some inventory requires it and passes it to the hotel; without it those bookings return 400 supplier_contact_required.
phonestringlead travellerSend on travelers[0], in international format, e.g. +447700900123. Required by the same inventory as email.
roomIndexinteger, 0–8Which room this guest sleeps in, counting from 0 in the order of your search's occupancy. Defaults to 0.
type"adult" | "child" | "infant"Defaults to adult. Send child for every guest searched as a child. Use infant only for activities; for hotels, send infants as children with their age.
ageinteger, 0–120childrenRequired for children; must match the age you searched with. Activities also need it for adults (18–120).
nationalityISO 3166-1 alpha-2flightsPassport country. Send it for every flight passenger. For hotels, send it on the lead traveller; it should match the search's residency (the API doesn't check this).
titlestring, 1–8see belowOne of Mr, Mrs, Ms, Miss, Master, Dr (any case; a trailing dot is fine). Required on every traveller when a hotel quote has requiresGuestTitle: true, and on the lead traveller for activities and transfers; send it for every flight passenger. See Titles.
dateOfBirthYYYY-MM-DDflightsSend it for every flight passenger. Validate the format yourself; some flights refuse a missing or unreadable date with 400 travel_documents_required.
gender"m" | "f"flightsSend it for every flight passenger.
passportNumberstring, 1–20flightsSend it for every flight passenger, domestic journeys included.
passportExpiryYYYY-MM-DDflightsSend it for every flight passenger. Validate the format yourself. Passports that expire within 6 months of travel can be refused with 400 travel_documents_required.
carrierNamestring, 1–60some transfersThe flight's airline, when a transfer returns requiresFlightDetails: true. See Transfers.
flightNumberstring, 1–7some transfersThe flight number, e.g. EK003.
flightTimeHH:MMThe flight's local time. Kept for our operations team; it isn't passed to the operator.

What each product needs

ProductEvery travellerLead traveller also
HotelsName; roomIndex; type and age for children; title when the quote has requiresGuestTitle: trueEmail, phone, nationality
FlightsName, title, dateOfBirth, gender, passportNumber, passportExpiry, nationalityEmail, phone
ActivitiesName; age for every adult (18–120) and childEmail, phone, title
TransfersNameEmail, phone, title; the flight when required

Hotel special requests

For hotels you can pass the guests' requests with the booking in hotelPreferences:

  • specialRequest — a note for the whole booking, up to 500 characters.
  • rooms[] — per room: roomIndex (as on the travellers), smoking (boolean) and specialRequest (up to 500 characters).

These are requests, not guarantees. They are passed to the hotel where the rate supports them; some inventory takes only one note for the whole booking, and a smoking preference isn't passed on everywhere. Don't promise a request to the traveller, and don't use it for anything the stay depends on — book a room type that includes it instead. Other products ignore hotelPreferences.