Concept · JSON travel itinerary
A travel itinerary in JSON
Roadbook is an open JSON interchange format for complete travel itineraries. Here is why JSON is a good fit, what the smallest valid file looks like, and how validation and portability follow from it.
Why JSON works well for an itinerary#
- Universally readable. Every language, platform and browser parses JSON natively; so do large language models. No SDK is required to read or write a Roadbook.
- Structured but human-readable. A trip is nested data — days contain items, bookings contain tickets — and JSON expresses nesting and references without ceremony. You can still open the file in a text editor and understand it.
- Schema-friendly. JSON Schema describes the structure precisely; generic validators (AJV, jsonschema, …) and structured-output features of AI APIs consume it directly.
- Small. A four-day trip with bookings and tickets is a few tens of kilobytes — it fits in an e-mail, a QR-code-linked download, a sync payload or a model's context window. Media (photos, vouchers) stay outside the file as URLs.
- Extensible without breaking. Unknown fields are ignored and preserved by readers, so minor versions add fields without invalidating older tools or files.
The minimal valid Roadbook#
Six required root fields — id, name, start, end, members, days — plus formatVersion to say which version you wrote. Each day needs an id, an index, a date, a title and items; each item an id, a title, a type and a status.
{
"formatVersion": "1.2",
"id": "minimal-example",
"name": "A day in Lille",
"start": "2026-09-05",
"end": "2026-09-05",
"members": [
{ "id": "m1", "name": "Alex", "role": "owner", "kind": "adult" }
],
"days": [
{
"id": "d1", "index": 1, "date": "2026-09-05", "title": "Old Lille",
"items": [
{ "id": "i1", "time": "10:00", "title": "Stroll through Old Lille",
"type": "heritage", "status": "planned",
"place": "Place du Général-de-Gaulle, Lille" },
{ "id": "i2", "time": "12:30", "title": "Lunch",
"type": "meal", "status": "planned" }
]
}
]
}
This is examples/minimal.roadbook.json — validate it. From there, add bookings, tickets, alternatives, options, people, vehicles, checklists as the trip requires; the examples show each feature in context.
Conventions that keep the JSON unambiguous#
| Concept | Rule |
|---|---|
dates | ISO YYYY-MM-DD. |
times | 24-hour HH:MM, always the local wall-clock time where the item happens; optional IANA timezone fields carry the zone. |
enums | English tokens ("meal", "confirmed", "to_book"…), used verbatim in the file and translated by the player at display time. |
ids | Non-empty strings, unique within their collection; references (bookingId, memberIds, personIds, vehicleId, chosenOptionId) must resolve. |
currency | ISO 4217; a trip-level default (absent = EUR), overridable per price. |
media | URLs (or relative paths next to the file) — never inline binaries. |
Schema validation#
Two layers. The JSON Schema checks structure and types with any generic validator. The reference validator (zero-dependency ESM, browser/Node/CLI) additionally checks what a schema cannot express: id uniqueness, day dates inside the trip range, consistent day indexes, resolving references. Errors are path + message pairs — designed to be pasted back to the tool or model that produced the file.
import { validateRoadbook } from 'https://roadbookformat.org/roadbook-validate.mjs'
const { ok, version, errors, warnings } = validateRoadbook(json)
// errors: [{ path: "$.days[1].date", message: "Day 2026-09-07 falls outside the trip period …" }]
With AJV (JSON Schema 2020-12):
import Ajv2020 from 'ajv/dist/2020.js'
const schema = await (await fetch('https://roadbookformat.org/roadbook.schema.json')).json()
const validate = new Ajv2020({ strict: false }).compile(schema)
validate(json) || console.log(validate.errors)
Portability#
A Roadbook is a file you own: my-trip.roadbook.json, UTF-8, media type application/json. It can be e-mailed, stored in a drive, versioned in git, imported into a player, exported back out, and diffed. Because every file declares its formatVersion and readers must preserve unknown fields, a file written today stays readable by tomorrow's tools and vice-versa within the same major version. See itinerary interchange.
AI generation#
The same properties make Roadbook easy for an assistant to produce: regular structure, public spec at a stable URL, explicit rules, a schema usable for structured output, and a validator whose messages close the loop. The AI page has a prompt builder and the full workflow; AI travel itinerary explains when the format is the right answer.