Trainline APItrainline.eu ↗
Search Trainline stations by name, get URNs, and find available train journeys across the UK and Europe with schedules, duration, and CO2 data.
What is the Trainline API?
The Trainline API exposes 3 endpoints for working with train travel data across the UK and Europe. Use search_locations to resolve station names into URNs, search_journeys to retrieve up to 8 journeys between two stations with departure times, durations, distances, and CO2 emissions, and get_routes_from_station to list all reachable destinations from a given origin along with frequency and schedule data.
curl -X GET 'https://api.parse.bot/scraper/447b13bc-e3c7-4dca-a183-dbdaa6edee8a/search_locations?query=London' \ -H 'X-API-Key: $PARSE_API_KEY'
Typed, relational, agent-ready
A generated client with real types, enums, and the links between objects — the structure a flat JSON response can't carry. Autocompletes in your editor and reads cleanly to coding agents.
- Fully typed · autocompletes
- Objects link to objects
- Typed errors & pagination
Typed Python client. Set up the SDK in your uv project, then pull this API’s typed client:
uv add parse-sdk uv run parse init uv run parse add --marketplace trainline-eu-api
uv run parse add --marketplace pulls a pinned snapshot of this canonical API — it won’t change underneath you. To customize it, subscribe and swap to your own copy.
"""Trainline API — search stations, discover routes, and find journeys."""
from parse_apis.Trainline_API import Trainline, StationNotFound
client = Trainline()
# Search for stations by name
for station in client.stations.search(query="Manchester", limit=3):
print(station.name, station.urn, station.country)
# Get a station and list routes reachable from it
london = client.station(urn="urn:trainline:generic:loc:182gb")
for route in london.routes.list(limit=3):
print(route.destination_name, route.destination_country, route.duration, route.trains_per_day)
# Search for journeys between two stations
for journey in client.journeys.search(
origin="urn:trainline:generic:loc:182gb",
destination="urn:trainline:generic:loc:115gb",
departure_date="2026-08-04",
limit=3,
):
print(journey.departure_time, journey.arrival_time, journey.duration, journey.num_legs)
# Typed error handling
try:
result = client.stations.search(query="Xyzzyville", limit=1).first()
print(result.name if result else "No station found")
except StationNotFound as exc:
print(f"Station not found: {exc}")
print("exercised: stations.search / station.routes.list / journeys.search / StationNotFound catch")
Search for train station locations by name. Returns station URNs, coordinates, and metadata. Each station has a URN that uniquely identifies it and can be used as origin or destination in search_journeys. Results include both individual stations and station groups (e.g. 'London' encompasses multiple terminals). Partial name matching is supported.
| Param | Type | Description |
|---|---|---|
| queryrequired | string | Station name or partial name to search for (e.g. 'London', 'Manchester', 'Paris'). |
{
"type": "object",
"fields": {
"locations": "array of station objects with name, urn, country, type, timezone, latitude, longitude"
},
"sample": {
"data": {
"locations": [
{
"urn": "urn:trainline:generic:loc:182gb",
"name": "London",
"type": "stationGroup",
"country": "GB",
"latitude": null,
"timezone": "Europe/London",
"longitude": null
},
{
"urn": "urn:trainline:generic:loc:EUS1444gb",
"name": "London Euston",
"type": "station",
"country": "GB",
"latitude": 51.5284,
"timezone": "Europe/London",
"longitude": -0.1346
}
]
},
"status": "success"
}
}About the Trainline API
Station Search and URN Resolution
The search_locations endpoint accepts a partial or full station name via the query parameter and returns an array of matching location objects. Each object includes the station's name, urn, country, type, timezone, latitude, and longitude. Both individual stations and station groups (such as "London") appear in results. The urn field is the key identifier used as origin and destination in downstream requests — it takes the form urn:trainline:generic:loc:<id>.
Journey Search
search_journeys accepts two URNs (origin and destination) and an optional departure_date. The date can be supplied as YYYY-MM-DD (defaults to 09:00 local time) or as a full ISO datetime string. The response includes a total count and a journeys array. Each journey object carries id, departure_time, arrival_time, duration, direction, distance_km, co2_grams, and num_legs. Results are sorted by departure time and capped at 8 journeys per call.
Route Discovery from a Station
get_routes_from_station takes a station_urn and returns all destinations reachable from that station. The routes array contains objects with destination_name, destination_slug, destination_country, duration, trains_per_day, first_departure, and last_departure. The response also includes a resolved station_name for the supplied URN. This endpoint is useful for mapping out a network of connections before committing to a specific journey search.
The Trainline API is a managed, monitored endpoint for trainline.eu — not a raw scraper you maintain. Every endpoint is automatically health-checked on a schedule, and when trainline.eu changes and a check fails, the API is automatically queued for repair and re-verified. It is built to keep working as the site underneath it changes.
This isn't an official trainline.eu API — it's an independent, maintained REST wrapper over public data. Where the source has no official API (or only a limited one), Parse gives you a stable contract over a source that never promised one, and keeps it current. Need a new endpoint or field? You can revise it yourself in plain English and the agent rebuilds it against the live site in minutes — contributing the change back to the shared API is free.
Will this API break when the source site changes?+
Is this an official API from the source site?+
Can I fix or extend this API myself if I need a new endpoint or field?+
What happens if I call an endpoint that has an issue?+
- Build a route planner that resolves city names to URNs and displays available journeys with CO2 comparisons.
- Calculate carbon footprint estimates for train trips using the
co2_gramsfield returned per journey. - Generate a connection map for a major hub by calling
get_routes_from_stationand charting all reachable destinations. - Automate journey-time lookups for a travel-time matrix between multiple European city pairs.
- Display typical daily train frequency and first/last departure times for a given station to inform trip planning.
- Enrich transport data pipelines with station coordinates (
latitude,longitude) and timezone metadata fromsearch_locations. - Compare multi-leg journey counts across routes using the
num_legsfield to identify direct versus connecting services.
| Tier | Price | Credits/month | Rate limit |
|---|---|---|---|
| Free | $0/mo | 200 | 5 req/min |
| Hobby | $30/mo | 1,000 | 20 req/min |
| Developer | $100/mo | 5,000 | 100 req/min |
| Team | $300/mo | 20,000 | 300 req/min |
| Company | $1,000/mo | 100,000 | 500 req/min |
Each endpoint has a fixed posted price per successful call — most fall between 1 and 10 credits — shown on this API's page before you run it. Exceeding the rate limit returns a 429 response. Authenticate with the X-API-Key header.
Does Trainline have an official public developer API?+
What does search_journeys return, and does it include ticket prices?+
departure_time, arrival_time, duration, distance_km, co2_grams, and num_legs. Ticket pricing is not currently returned by this endpoint. The API covers schedule and logistics data for available journeys. You can fork it on Parse and revise to add a pricing-focused endpoint if that data becomes accessible.Are all European countries covered by search_locations?+
Does the API return real-time disruption or live delay information?+
How many journeys does search_journeys return per call, and can results be paginated?+
departure_date input to a later date or time.