📊 Example API Output

Real-time London Underground Train Data

Example Request

Here's an example of how to request real-time train data for the Metropolitan line:

GET /live/metropolitan/line/latest.json?key=YOUR_API_KEY

⚠️ Note: A valid API key is required to access live data endpoints. The examples below show the structure of the response data.

Response Structure

The API returns a JSON object with the following main sections:

Field Type Description
as_of string ISO 8601 timestamp when this snapshot was generated
sources object Metadata about data sources, either TfL's TrackerNet or Unified API
status object Health of the generated output based on amount of data returned from upstream sources
stats object Statistics about build time, pre and post processing train counts, and network coverage
next_platforms array Some stations report the next platforms for the next departing trains
trains array Array of train objects with real-time positions and metadata

Example Response

Complete JSON Output

{
  "as_of": "2025-12-15T22:26:58.994Z",
  "sources": {
    "unified": "disabled",
    "trackernet": "ok"
  },
  "status": "ok",
  "stats": {
    "as_of": "2025-12-15T22:26:58.994Z",
    "build_ms": 3194,
    "stations": 18,
    "detailedXmls": 31,
    "unified": {
      "pre_all": 0,
      "pre_line": 1,
      "post_map": 1,
      "zero_seen": 1,
      "zero_synth": 1,
      "exact_dropped": 0
    },
    "trackernet": {
      "pre": 436,
      "post": 90,
      "loc_indexed": 89,
      "id_dropped": 310,
      "status": "ok",
      "fallback_until": 0
    },
    "merged": {
      "count": 40,
      "by_source": {
        "unified": 1,
        "trackernet": 63
      },
      "alias_by_location": 0,
      "prefer_tr": 0,
      "prefer_unified": 0
    },
    "unknown_location_count": 0
  },
  "next_platforms": [
    {
      "station": "Baker Street",
      "platform": "Platform 2"
    },
    {
      "station": "Aldgate",
      "platform": "Platform 3"
    }
  ],
  "trains": [
    {
      "id": "metropolitan:1114341",
      "lineId": "metropolitan",
      "vehicleId": "436",
      "leadingcarno": "21049",
      "trackCode": "TF80251",
      "lcid": "561",
      "setNo": "436",
      "tripNo": "17",
      "departTime": "22:26:47",
      "source": "trackernet",
      "currentLocation": "Between Neasden and Wembley Park",
      "stationName": "Harrow on the Hill",
      "platformName": "Northbound Fast - Platform 3",
      "destinationName": "Uxbridge",
      "direction": "inbound",
      "towards": "Uxbridge",
      "inputDest": "UXB4 (UXB4/M-W-NP-XXXX-X/UXB4)",
      "destCode": "445",
      "stoppingPattern": "All Stations",
      "timestamp": "2025-12-15T22:26:51.000Z",
      "legacyTrainId": "1114341",
      "secondsTo": 547,
      "destBookedPlatNo": "UXB4",
      "isMaybeStalled": false,
      "stallDurationSeconds": 34,
      "stallSince": "2025-12-15T22:26:24.532Z",
      "stallUpdatedAt": "2025-12-15T22:26:58.994Z",
      "currentLocationFirstSeen": "2025-12-15T22:26:24.532Z",
      "currentLocationLastSeen": "2025-12-15T22:26:58.994Z",
      "currentLocationDurationSeconds": 34,
      "locationAvgSeconds": 29.232426360541034,
      "locationSampleCount": 88,
      "isSlowerThanAverage": false,
      "isReformed": false
    },
    {
      "id": "metropolitan:465",
      "lineId": "metropolitan",
      "vehicleId": "465",
      "leadingcarno": "21109",
      "trackCode": "TJAEHOH",
      "lcid": "621",
      "setNo": "000",
      "tripNo": "13",
      "departTime": "22:26:26",
      "source": "trackernet",
      "currentLocation": "At Harrow on the Hill Platform 3",
      "stationName": "Harrow on the Hill",
      "platformName": "Northbound Fast - Platform 3",
      "destinationName": "Amersham",
      "direction": "inbound",
      "towards": "Amersham",
      "inputDest": "2027",
      "destCode": "31",
      "stoppingPattern": "~ All Stations",
      "timestamp": "2025-12-15T22:26:51.000Z",
      "legacyTrainId": "1118371",
      "secondsTo": 0,
      "destBookedPlatNo": "AME2",
      "vehicleIdInferred": true,
      "isMaybeStalled": false,
      "stallDurationSeconds": 0,
      "stallSince": "2025-12-15T22:26:58.994Z",
      "stallUpdatedAt": "2025-12-15T22:26:58.994Z",
      "currentLocationFirstSeen": "2025-12-15T22:26:58.994Z",
      "currentLocationLastSeen": "2025-12-15T22:26:58.994Z",
      "currentLocationDurationSeconds": 0,
      "locationAvgSeconds": 2.4600000000000004,
      "locationSampleCount": 2,
      "isSlowerThanAverage": false,
      "isReformed": false
    }
  ]
}

Train Object Fields

Each train object in the trains array contains the following fields:

Field Type Description
id string Unique identifier in format {lineId}:{vehicleId}
lineId string Line identifier (e.g., "metropolitan", "central")
vehicleId string Used for the train running number, a train will be allocated a train number at the start of the day and will usually follow this booked working. Physical trains can be reformed/reallocated on to different train numbers during the day. You can follow a trains booked working by following the train number in the Working Timetable (WTT). The term "vehicleId" is from upstream and is different from the physical train identifier.
leadingcarno string Leading Car Number: Physical car number of the leading carriage of the train, this will change during the day as a train reverses direction.
trackCode string Raw track code from TfL used for location inference. This is based on real world signalling systems and may be used to infer the train's precise location, a lot more accurate than just "Between Station X and Station Y". We use this to improve the "currentLocation" field.
lcid string Local Computer ID from TfL TrackerNet, used for internal tracking and identification purposes within the TfL system. Has no external significance.
setNo string This is the same output as "vehicleId". The TrackerNet upstream data uses "SetNo" to refer to the train running number and the Unified feeds use "vehicleId".
tripNo string Trip number from TfL scheduling data, can be used to correlate with timetable information
departTime string Computed departure time from current location in HH:MM:SS format, not actual scheduled departure time
source string Data source - typically "trackernet" or "unified". We prioritize data from "TrackerNet" when available for more detailed and accurate information. We have an automatic fallback to "unified" if "TrackerNet" data is not available.
currentLocation string Normalized, human-readable location description
stationName string Station name that was used to request the train data.
platformName string Platform identifier with direction (e.g., "Northbound Fast - Platform 3")
destinationName string The final destination station name of the train.
direction string Normalized direction: "inbound" or "outbound". This is derived from upstream data. We want to improve this to a normalized format of "northbound", "southbound", "eastbound", or "westbound" in the future.
towards string Destination station of the train and sometimes a "via" description indicating the route taken, for example "Hainault via Newbury Park".
inputDest string Raw destination code/string from TfL before processing. The quality of this varies per line and data source. On the Metropolitan line, this can be used to determine Fast, Semi-Fast or All Stations service patterns but only if the train is in the new CBTC signalling area.
destCode string This is provided from upstream. Not currently used in our processing.
stoppingPattern string Service pattern (e.g., "All Stations", "Fast", "~ All Stations"). We also use this field to append additional information about the train, such as stall status.
timestamp string ISO 8601 timestamp when this train record was last updated in the upstream data source
legacyTrainId string Original TfL train ID for reference, can normally be used to uniquely identify a trains data.
secondsTo number Seconds until arrival at "stationName", the station used to request the train data.
destBookedPlatNo string Booked platform code at final destination, derived from "inputDest" and cached for when a train loses this information when leaving the new CBTC signalling area.
vehicleIdInferred boolean True if vehicle ID was inferred rather than directly provided. We do a lot of work to infer vehicle IDs when they are missing from the raw data using various heuristics such as "legacyTrainId", "leadingCarNo" and other related fields. The "vehicleId" will be updated with the inferred data and this flag indicates that the value is not directly from the raw data.
isMaybeStalled boolean Indicates if train may be stalled based on location duration. Flips to true when conditions are met, current minimum stall time is 5 minutes, unless a train is reported in a depot or siding.
stallDurationSeconds number How long the train has been at current location
stallSince string ISO timestamp when potential stall began
stallUpdatedAt string ISO timestamp of last stall status update
currentLocationFirstSeen string ISO timestamp when train first appeared at this location
currentLocationLastSeen string ISO timestamp when train was last seen at this location
currentLocationDurationSeconds number Total seconds the train has been at current location
locationAvgSeconds number Historical average time trains spend at this location. This is based on a rolling average of past train durations at this location. Very basic sampling and averaging at the moment.
locationSampleCount number Number of historical samples used for location average. This is a rolling count of how many past train durations have been included in the average calculation.
isSlowerThanAverage boolean True if current duration exceeds historical average
isReformed boolean True if train set was recently reformed. This means the "leadingcarno" has been put on to a new train working and received a new "vehicleId"/"setNo".)

Key Features in the Output

🎯 Normalized Location Data

Station names and locations are standardized and cleaned, removing inconsistencies from the raw TfL data. Trains between stations are clearly identified with "Between [Station A] and [Station B]" format.

🧭 Direction & Destination Information

Each train includes normalized direction (e.g., "inbound", "outbound"), destination, and "towards" information that's been cleaned and validated. Metropolitan line trains include destination codes and stopping patterns.

⏱️ Real-time Position Updates

The secondsTo field provides arrival time for the next station, with times automatically calculated from TfL's raw data. Historical averages help identify delays.

🚦 Stall Detection

Advanced stall detection tracks how long trains remain at each location and compares against historical averages to identify potential service disruptions.

📈 Processing Statistics

The stats object provides detailed metrics about data processing, including how many trains were filtered from raw TfL data, merge operations between data sources, and build performance.

🚂 Vehicle & Formation Tracking

Train metadata includes vehicle IDs, set numbers, leading car numbers, and reformation detection for comprehensive fleet tracking.

Available Endpoints

Endpoint Description
/live/{lineId}/line/latest.json Full train data for a specific line (compressed)
/live/{lineId}/line/latest-plain.json Full train data (uncompressed)
/live/{lineId}/line/latest-stats.json Statistics only (no train array)
/live/{lineId}/map/latest.json Map-optimized data with area groupings
/live/all/line/latest.json All lines combined

Supported Lines

bakerloo, central, circle, district, hammersmith-city, jubilee, metropolitan, northern, piccadilly, victoria, waterloo-city

🔑 Need API Access? Contact the administrator to request an API key for accessing live data.