You can run the script with various options to customize its behavior. Use:
bun book [options]
| Option | Description | Example |
|---|---|---|
-t, --od |
Set the origin-destination pair (city, 3-letter code, or UIC). | |
| Recognized cities: london, paris, lille, marseille, disneyland, lyon, avignon, dijon, bruges, ghent, geneva, zurich, amsterdam, cologne, dusseldorf. | ||
| 3-letter shortcuts (first 3 letters) are also accepted. | ||
| Examples: | ||
-t par-bru (Paris to Bruges) |
-t par-bru |
|
-t gen (London to Geneva, default origin is London) |
-t gen |
|
-t 7015400-8727100 (London to Paris by UIC) |
-t 7015400-8727100 |
|
-d, --date |
Specify the travel date | -d 2025-08-11 |
| Outbound 5 days from now | -d 5 |
|
| Outbound 5 days from now, return 2 days later | -d 5,2 |
|
| On Dec 1st | -d 2025-12-01 |
|
| On Dec 1st, return a week later | -d 2025-12-01,7 |
|
-p, --pax |
Number of passengers | -p 2 |
| Just a number defaults to adults | -p 2 |
|
| Example: 1 adult, 2 children | -p 1a,2c |
|
| Example: 2 seniors | -p 2s |
|
-m, --market |
Set the market (country-language) | --market uk |
eg.: country uk, fr, nldefault laguage and currency will be used |
--market fr |
|
eg.: country-language uk-en, be-fr, be-en, be-nluse when you need to be more specific |
--market fr-fr |
|
-c, --class |
Class of service. Possible values: STD, PLUS, PREMIER | -c PLUS |
--train <number> |
Pick the journey with the specified train number | --train 9012 |
--time <string> |
Pick the journey with the specified departure time | --time 09:31 |
For return journeys, you can set different values for outbound and return legs using --out:* and --rtn:* prefixes:
| Option | Description | Example |
|---|---|---|
--out:class |
Class of service for outbound journey | --out:class PLUS |
--out:train |
Train number for outbound journey | --out:train 9012 |
--out:time |
Departure time for outbound journey | --out:time 08:15 |
--out:date |
Date for outbound journey | --out:date 2026-03-15 |
--out:nth |
Select outbound journey by position | --out:nth 2nd |
--rtn:class |
Class of service for return journey | --rtn:class STD |
--rtn:train |
Train number for return journey | --rtn:train 9055 |
--rtn:time |
Departure time for return journey | --rtn:time 18:30 |
--rtn:date |
Date for return journey | --rtn:date 2026-03-17 |
--rtn:nth |
Select return journey by position | --rtn:nth last |
These override the general options (-c, --train, --time) for that specific direction. For example:
# PLUS class outbound, STD class return
bun book -d 14,2 --out:class PLUS --rtn:class STD
# Same train class, but specific train numbers for each leg
bun book -d 14,2 -c PLUS --out:train 9012 --rtn:train 9055
For convenience, you can specify multiple journey parameters in a single comma-separated value using --out and --rtn:
| Option | Description | Example |
|---|---|---|
--out |
Outbound journey shorthand | --out 2026-03-15,STD,9012 |
--rtn |
Return journey shorthand | --rtn PLUS,18:30,2nd |
Components are auto-detected by format:
| Component | Format | Examples |
|---|---|---|
| Date | ISO format (YYYY-MM-DD) | 2026-03-15 |
| Date | Relative days from today (1-366) | 14, 30 |
| Class | Class alias | STD, PLUS, PREMIER, S, P, * |
| Train | 4-digit train number | 9012, 6129 |
| Time | 24h format (HH:MM) | 08:15, 18:30 |
| Time | Hour wildcard (HH:*) | 11:* (first train in that hour) |
| Nth | Ordinal position | 1st, 2nd, 3rd, first, last |
Examples:
# Full shorthand: date, class, train, and time
bun book -t paris --out 2026-03-15,STD,9012 --rtn 2026-03-17,PLUS,18:30
# Shorthand with position selection
bun book -t paris --out 14,PLUS,1st --rtn 16,STD,last
# Mixed: shorthand for class/time, explicit for train
bun book -t paris --out PLUS,08:* --out:train 9012
# Hour wildcard: first train departing in the 11:00 hour
bun book -t paris --out 11:*
Explicit direction options (--out:class, --out:train, etc.) override shorthand values when both are provided.
Select journeys by their position in search results using --nth:
| Option | Description | Example |
|---|---|---|
--nth |
Select journey by position (both) | --nth 2 |
--out:nth |
Select outbound journey by position | --out:nth 1st |
--rtn:nth |
Select return journey by position | --rtn:nth last |
Accepted values:
1, 2, 3, etc.1st, 2nd, 3rd, 4th... up to 9thfirst, last# Select the 2nd journey in results
bun book -t paris --nth 2
# First outbound, last return
bun book -t paris -d 14,2 --out:nth first --rtn:nth last
# Can combine with class filters
bun book -t paris -c PREMIER --nth 2
Two mutually-exclusive booking modes mirror snap-app's discount/last-minute experiences. They drive both the journeySearch query (different productFamilies, maxTransfers: 0, restricted class filters) and createCart (channel: SNAP).
| Option | Description | Example |
|---|---|---|
--snap |
Snap mode: search LASTMIN inventory, direct trains only, standard class only. Mirrors snap-app's main flow. | --snap |
--unallocated, --unalloc |
Unallocated mode: search RED_US inventory, direct trains only, UNASSIGNED class only. | --unallocated |
--product-family <CODE>, --family |
Override productFamilies (e.g. LASTMIN, RED_US, PUB). With --snap/--unallocated, overrides the family but keeps the mode's other constraints. |
--product-family LASTMIN |
--snap and --unallocated cannot be combined; the parser will error if both are passed. Inventory is route-specific:
| Mode | Routes with confirmed inventory on staging |
|---|---|
--snap |
lon-par, par-lon (London ↔ Paris) |
--unallocated |
par-bxl, bxl-par (Paris ↔ Brussels) |
Other routes will return shells with no bookable fares; the bot will fail fast with a message naming alternative routes. Use short dates (1–7 days out) - these modes are last-minute by nature.
# Book a snap (last-minute) train London → Paris tomorrow
bun book -t lon-par -d 1 --snap
# Book an unallocated seat Paris → Brussels in 2 days
bun book -t par-bxl -d 2 --unallocated
# Research: snap-style search but on a different product family
bun book -t lon-par --snap --product-family RED_US
--package <destination> books a hotel + return-train package instead of a train-only journey. It runs a dedicated pipeline (PackagesSearch → PackageHotelRooms → PackageTrains → createCart with channel: PKG), separate from the train pipeline. See packages.md for the full flow and the destination dataset.
| Option | Description | Example |
|---|---|---|
--package <slug>, --pkg |
Destination region slug (e.g. antwerp, paris). Enables packages mode. Mutually exclusive with --snap/--unallocated. |
--package antwerp |
--from <slug>, --departing |
Origin region slug. Default london. |
--from brussels |
--nights <N>, --duration |
Stay length in nights. Defaults to the -d return gap (e.g. -d 34,7 = arrive in 34 days, stay 7 nights), else 2. |
--nights 3 |
--hotel <substr> |
Pick a hotel by case-insensitive substring of its name. Default: a known test hotel for the region, else cheapest. | --hotel hampton |
--room <substr> |
Pick a room by case-insensitive substring of its name/type. | --room triple |
--cancellation <FULL|PARTIAL> |
Pick a room offering that cancellation refund type. Distinct from --cancel (after-sales). |
--cancellation FULL |
Arrival date reuses -d (first token); the second -d token sets the stay length (e.g. -d 34,7 arrives in 34 days for 7 nights) unless --nights is given. Room occupancy reuses -p. Trains default to the gateway's pre-selected service per bound; any --out/--rtn/--out:train/--out:time/--out:nth flag overrides the selection.
# Cheapest known-test-hotel package, London → Antwerp, arriving in 14 days, 2 nights, 2 adults
bun book --package antwerp -p 2a
# Specific hotel + room + fully-refundable rate, London → Paris on a fixed date, 3 nights
bun book --package paris -d 2026-07-10 --nights 3 --hotel belta --room twin --cancellation FULL
# Package from Brussels with a chosen outbound train
bun book --package paris --from brussels --out:train 9004
| Option | Description | Example |
|---|---|---|
-w, --wait |
Time to wait between runs (e.g., 1s, 5m) | -w 5s |
-j, --jitter |
Add noise to wait time (e.g., 0.5, 1s) | -j 1s |
-i, --iterations |
Number of iterations to run | -i 10 |
-b, --batch |
Run many bookings from a JSON file (see batch.md) | -b runs.json |
-o, --open |
Open a window during or after the booking process | -o search |
| Example: Opens customer dashboard | -o myb |
|
| Example: Opens voyager | -o voyager |
|
| Example: Opens provisional booking for manual checkout | -o checkout |
|
--manual |
Open a window to complete process manually, interrupts process | --manual checkout |
| Example: Opens provisional booking for manual checkout | --manual checkout |
|
| Example: Opens search results | --manual search |
| Option | Description | Example |
|---|---|---|
-v, --verbose |
Enable verbose output | -v |
-s, --save |
Save HTTP scripts to re-run the requests manually | -s |
--dry-run |
Run without making bookings | --dry-run |
--log <file> |
Output log to specified file | --log results.log |
By default the bot calls the public Site-API (site-api-staging.eurostar.com) and mimics browser headers - no VPN required. Pass --gateway to talk to a specific internal gateway directly (VPN required); providing a gateway override automatically switches modes.
| Option | Description | Example |
|---|---|---|
-g, --gateway <PR-or-URL> |
Hit a specific gateway directly. PR number resolves via prStacks, or pass a full URL. Auto-enables internal mode. |
--gateway 1270 / --gateway https://... |
--site-api <URL> |
Override the public Site-API URL (external mode only). | --site-api https://site-api-staging.eurostar.com |
--ua, --useragent <preset-or-string> |
UA for outgoing requests (external mode). Preset key (chrome, safari_ios, chrome_v147_mac, …) or a literal UA string. |
--ua safari_ios |
--cookie, --cookies <string> |
Cookie header value (external mode). Forwarded opaquely. | --cookies "session=abc; cf=xyz" |
--header, --headers <string> |
Extra HTTP headers for outgoing requests, as key=value;key=value. Parsed into distinct headers. |
--headers "x-debug=1;x-trace=abc" |
# External (default) - no VPN, mimics Chrome 147 mac
eil-book -t par -d 14
# Internal - talk to gateway PR 1270 directly (VPN required)
eil-book -t par --gateway 1270
# External with Safari iOS UA + a captured cookie
eil-book -t par --ua safari_ios --cookies "session=abc"
# Attach extra HTTP headers to outgoing requests
eil-book -t par --headers "x-debug=1;x-trace=abc"
Cancel bookings — either chained onto a fresh booking, or standalone against an existing PNR. The same flows are exposed in the Web UI under Advanced → Cancellation.
| Option | Description | Example |
|---|---|---|
--cancel |
Cancel a booking. With --pnr, refunds the given booking directly; without, books first and then cancels the new PNR. |
--cancel |
--pnr, --reference |
Booking reference to cancel. Use with --cancel to skip the booking step. |
--cancel --pnr ABC123 |
--surname, --last-name |
Surname on the booking. Required when --pnr points at a booking the bot didn't create. |
--surname Smith |
--refund-method <CC|VOUCHER> |
Refund destination: card (CC, default) or Eurostar voucher. |
--refund-method VOUCHER |
--cancel-bound <outbound|inbound> |
Restrict cancellation to one bound; the other is left intact. | --cancel-bound outbound |
--cancel-leg <N> |
1-indexed leg position within the chosen bound (for connections, e.g. London → Lyon via Paris). Requires --cancel-bound. |
--cancel-bound outbound --cancel-leg 2 |
--cancel-pax <ids> |
Comma-separated passenger IDs to refund (1,2 or passenger_1,passenger_2). |
--cancel-pax 1,2 |
# Book and immediately cancel for a card refund
bun book -t par -d 14 --cancel
# Cancel an existing PNR for a voucher refund
bun book --cancel --pnr ABC123 --surname Smith --refund-method VOUCHER
The HTTP equivalent is POST /api/cancel; the chained form is the cancel field on POST /api/booking.
| Option | Description | Example |
|---|---|---|
-h, --help |
Show help information | -h |
For a full list of options, run:
bun book --help
See also:
Both methods can be used together, with CLI options taking precedence.