Segments

STIB: brussels metro, tram and bus operator

Format
GeoJSON
Updates
Daily (derived from the STIB shapefile and stops)
Latest snapshot
Snapshots stored
about 777
curl -H "Authorization: Bearer $MOBILITYTWIN_TOKEN" "https://api.mobilitytwin.brussels/stib/segments"
Get a token

The STIB/MIVB network cut into segments, derived from the shapefile and the stops.

Which days have data

Data from 21 Aug 2024 to 2 Nov 2026, on 762 days. 30 of the last 30 days have data. A typical day holds 1 snapshot. Days are in UTC.

2026
JanFebMarAprMayJunJulAugSepOctNovDec
2025
JanFebMarAprMayJunJulAugSepOctNovDec
2024
JanFebMarAprMayJunJulAugSepOctNovDec
  • Full day
  • Partial, 50–90% of a typical day
  • Low, under 50%
  • No snapshot
  • Not expected

Click a day above, or pick a date, to get its requests.

Parameters

NameMeaning
timestampReturn the last snapshot at or before this moment, in Unix seconds or ISO 8601 (e.g. 2026-05-06T12:00:00Z). Without it, the latest snapshot is returned.

Response fields

A GeoJSON FeatureCollection. Field names without a prefix are in each feature's properties.

FieldTypeMeaning
line_idstringSTIB line number (GTFS route_short_name)
directionintegerDirection of the line, 1 or 2
startintegerStop id where the segment starts
endintegerStop id where the segment ends
distancenumberPosition of the start stop along the line's shape, projected in Belgian Lambert 72 (EPSG:31370), increasing along the direction of travel. Use it to order the segments of a line; it is not the length of the segment.
colorstringLine colour, hex

Python example

import requests
import geopandas as gpd

from datetime import datetime, timedelta, timezone

yesterday_noon = (datetime.now(timezone.utc) - timedelta(days=1)).replace(
    hour=12, minute=0, second=0, microsecond=0
)
params = {
    "timestamp": yesterday_noon.isoformat(),   # ISO accepted; epoch also works
}

url = "https://api.mobilitytwin.brussels/stib/segments"

data = requests.get(url, headers={
        'Authorization': 'Bearer [MY_API_KEY]'
}, params=params).json()

gdf = gpd.GeoDataFrame.from_features(data["features"], crs=4326)

# One stop-to-stop segment per feature; `distance` orders them along the line
line = gdf[(gdf['line_id'] == '71') & (gdf['direction'] == 1)].sort_values('distance')
line['length_m'] = line.to_crs(31370).geometry.length   # Belgian Lambert 72, metres
print(line[['start', 'end', 'length_m']].round(0).to_string(index=False))

# Plot the whole network in the lines' own colours
gdf.plot(figsize=(12, 10), color=gdf['color'], linewidth=1)