From bb78fe4cbac510b54d49f41efbdb35ffe7175299 Mon Sep 17 00:00:00 2001 From: Julien Dessaux Date: Thu, 18 Mar 2021 20:12:43 +0100 Subject: Added api module with departures feature --- api/client.go | 21 + api/client_test.go | 37 + api/departures.go | 59 ++ api/departures_test.go | 48 ++ api/invalid.json | 1 + api/normal-crepieux.json | 2135 ++++++++++++++++++++++++++++++++++++++++++++++ go.mod | 3 + go.sum | 0 8 files changed, 2304 insertions(+) create mode 100644 api/client.go create mode 100644 api/client_test.go create mode 100644 api/departures.go create mode 100644 api/departures_test.go create mode 100644 api/invalid.json create mode 100644 api/normal-crepieux.json create mode 100644 go.mod create mode 100644 go.sum diff --git a/api/client.go b/api/client.go new file mode 100644 index 0000000..79c8314 --- /dev/null +++ b/api/client.go @@ -0,0 +1,21 @@ +package api + +import ( + "fmt" + "net/http" + "time" +) + +type Client struct { + baseURL string + httpClient *http.Client +} + +func NewClient(token string) *Client { + return &Client{ + baseURL: fmt.Sprintf("https://%s@api.sncf.com/v1", token), + httpClient: &http.Client{ + Timeout: time.Minute, + }, + } +} diff --git a/api/client_test.go b/api/client_test.go new file mode 100644 index 0000000..c6146d4 --- /dev/null +++ b/api/client_test.go @@ -0,0 +1,37 @@ +package api + +import ( + "fmt" + "io/ioutil" + "net/http" + "net/http/httptest" + "testing" +) + +// package utilities +func NewTestClient(ts *httptest.Server) *Client { + return &Client{ + baseURL: fmt.Sprintf(ts.URL), + httpClient: ts.Client(), + } +} + +func NewTestClientFromFilename(t *testing.T, filename string) (*Client, *httptest.Server) { + ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + page, err := ioutil.ReadFile(filename) + if err != nil { + t.Fatalf("Could not open test file : %s", err) + } + w.Write(page) + })) + return NewTestClient(ts), ts +} + +// tests +func TestNewClient(t *testing.T) { + client := NewClient("test") + want := "https://test@api.sncf.com/v1" + if client.baseURL != want { + t.Fatal("Invalid new client") + } +} diff --git a/api/departures.go b/api/departures.go new file mode 100644 index 0000000..b87e35b --- /dev/null +++ b/api/departures.go @@ -0,0 +1,59 @@ +package api + +import ( + "encoding/json" + "fmt" + "net/http" +) + +type DeparturesResponse struct { + Disruptions []interface{} `json:"disruptions"` + Notes []interface{} `json:"notes"` + Departures []struct { + DisplayInformations struct { + Direction string `json:"direction"` + Code string `json:"code"` + Network string `json:"network"` + Links []interface{} `json:"links"` + Color string `json:"color"` + Name string `json:"name"` + PhysicalMode string `json:"physical_mode"` + Headsign string `json:"headsign"` + Label string `json:"label"` + Equipments []interface{} `json:"equipments"` + TextColor string `json:"text_color"` + TripShortName string `json:"trip_short_name"` + CommercialMode string `json:"commercial_mode"` + Description string `json:"description"` + } `json:"display_informations"` + StopDateTime struct { + Links []interface{} `json:"links"` + ArrivalDateTime string `json:"arrival_date_time"` + AdditionalInformations []interface{} `json:"additional_informations"` + DepartureDateTime string `json:"departure_date_time"` + BaseArrivalDateTime string `json:"base_arrival_date_time"` + BaseDepartureDateTime string `json:"base_departure_date_time"` + DataFreshness string `json:"data_freshness"` + } `json:"stop_date_time"` + } `json:"departures"` + Context struct { + Timezone string `json:"timezone"` + CurrentDatetime string `json:"current_datetime"` + } `json:"context"` +} + +func (c *Client) GetDepartures() (departures *DeparturesResponse, err error) { + req, err := http.NewRequest("GET", fmt.Sprintf("%s/coverage/sncf/stop_areas/stop_area:SNCF:87723502/departures", c.baseURL), nil) + if err != nil { + return nil, err + } + resp, err := c.httpClient.Do(req) + if err != nil { + return nil, err + } + defer resp.Body.Close() + if err = json.NewDecoder(resp.Body).Decode(&departures); err != nil { + return nil, err + } + return +} diff --git a/api/departures_test.go b/api/departures_test.go new file mode 100644 index 0000000..b0a5dc5 --- /dev/null +++ b/api/departures_test.go @@ -0,0 +1,48 @@ +package api + +import ( + "net/http" + "net/http/httptest" + "testing" +) + +func TestGetDepartures(t *testing.T) { + // invalid characters in token + client := NewClient("}") + _, err := client.GetDepartures() + if err == nil { + t.Fatalf("invalid characters in token should raise an error") + } + // unreachable server + client = NewClient("https://") + _, err = client.GetDepartures() + if err == nil { + t.Fatalf("unreachable server should raise an error") + } + // invalid json + client, ts := NewTestClientFromFilename(t, "invalid.json") + defer ts.Close() + _, err = client.GetDepartures() + if err == nil { + t.Fatalf("invalid json should raise an error") + } + // http error + ts = httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + w.WriteHeader(http.StatusNotFound) + })) + client = NewTestClient(ts) + _, err = client.GetDepartures() + if err == nil { + t.Fatalf("404 should raise an error") + } + // normal working request + client, ts = NewTestClientFromFilename(t, "normal-crepieux.json") + defer ts.Close() + departures, err := client.GetDepartures() + if err != nil { + t.Fatalf("could not get normal-crepieux departures : %s", err) + } + if len(departures.Departures) != 10 { + t.Fatalf("did not decode normal-crepieux departures properly, got %d departures when expected 10", len(departures.Departures)) + } +} diff --git a/api/invalid.json b/api/invalid.json new file mode 100644 index 0000000..98232c6 --- /dev/null +++ b/api/invalid.json @@ -0,0 +1 @@ +{ diff --git a/api/normal-crepieux.json b/api/normal-crepieux.json new file mode 100644 index 0000000..19a635a --- /dev/null +++ b/api/normal-crepieux.json @@ -0,0 +1,2135 @@ +{ + "pagination": { + "start_page": 0, + "items_on_page": 10, + "items_per_page": 10, + "total_result": 10 + }, + "links": [ + { + "href": "https://api.sncf.com/v1/coverage/sncf/stop_points/{stop_point.id}", + "type": "stop_point", + "rel": "stop_points", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/commercial_modes/{commercial_modes.id}", + "type": "commercial_modes", + "rel": "commercial_modes", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/stop_areas/{stop_area.id}", + "type": "stop_area", + "rel": "stop_areas", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/physical_modes/{physical_modes.id}", + "type": "physical_modes", + "rel": "physical_modes", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/routes/{route.id}", + "type": "route", + "rel": "routes", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/commercial_modes/{commercial_mode.id}", + "type": "commercial_mode", + "rel": "commercial_modes", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/vehicle_journeys/{vehicle_journey.id}", + "type": "vehicle_journey", + "rel": "vehicle_journeys", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/lines/{line.id}", + "type": "line", + "rel": "lines", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/physical_modes/{physical_mode.id}", + "type": "physical_mode", + "rel": "physical_modes", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/networks/{network.id}", + "type": "network", + "rel": "networks", + "templated": true + }, + { + "href": "https://api.sncf.com/v1/coverage/sncf/stop_areas/stop_area:OCE:SA:87723502/departures", + "type": "first", + "templated": false + } + ], + "disruptions": [], + "notes": [], + "feed_publishers": [], + "departures": [ + { + "display_informations": { + "direction": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886823", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886823", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-743716-BV" + }, + { + "type": "UIC8", + "value": "87743716" + }, + { + "type": "external_code", + "value": "OCE87743716" + } + ], + "name": "Ambérieu-en-Bugey", + "links": [], + "coord": { + "lat": "45.954008", + "lon": "5.342313" + }, + "label": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87743716" + }, + "quality": 0, + "name": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "id": "stop_area:OCE:SA:87743716" + }, + "name": "St-Etienne-Châteaucreux vers Ambérieu-en-Bugey (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "forward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886823F29029_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T131800", + "additional_informations": [], + "departure_date_time": "20210218T131800", + "base_arrival_date_time": "20210218T131800", + "base_departure_date_time": "20210218T131800", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "St-Etienne-Châteaucreux (Saint-Étienne)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886726", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886726", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-726000-BV" + }, + { + "type": "UIC8", + "value": "87726000" + }, + { + "type": "external_code", + "value": "OCE87726000" + } + ], + "name": "St-Etienne-Châteaucreux", + "links": [], + "coord": { + "lat": "45.443382", + "lon": "4.399996" + }, + "label": "St-Etienne-Châteaucreux (Saint-Étienne)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87726000" + }, + "quality": 0, + "name": "St-Etienne-Châteaucreux (Saint-Étienne)", + "id": "stop_area:OCE:SA:87726000" + }, + "name": "Ambérieu-en-Bugey vers St-Etienne-Châteaucreux (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "backward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886726F35035_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T134100", + "additional_informations": [], + "departure_date_time": "20210218T134100", + "base_arrival_date_time": "20210218T134100", + "base_departure_date_time": "20210218T134100", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886827", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886827", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-743716-BV" + }, + { + "type": "UIC8", + "value": "87743716" + }, + { + "type": "external_code", + "value": "OCE87743716" + } + ], + "name": "Ambérieu-en-Bugey", + "links": [], + "coord": { + "lat": "45.954008", + "lon": "5.342313" + }, + "label": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87743716" + }, + "quality": 0, + "name": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "id": "stop_area:OCE:SA:87743716" + }, + "name": "St-Etienne-Châteaucreux vers Ambérieu-en-Bugey (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "forward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886827F22022_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T141800", + "additional_informations": [], + "departure_date_time": "20210218T141800", + "base_arrival_date_time": "20210218T141800", + "base_departure_date_time": "20210218T141800", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "St-Etienne-Châteaucreux (Saint-Étienne)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886728", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886728", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-726000-BV" + }, + { + "type": "UIC8", + "value": "87726000" + }, + { + "type": "external_code", + "value": "OCE87726000" + } + ], + "name": "St-Etienne-Châteaucreux", + "links": [], + "coord": { + "lat": "45.443382", + "lon": "4.399996" + }, + "label": "St-Etienne-Châteaucreux (Saint-Étienne)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87726000" + }, + "quality": 0, + "name": "St-Etienne-Châteaucreux (Saint-Étienne)", + "id": "stop_area:OCE:SA:87726000" + }, + "name": "Ambérieu-en-Bugey vers St-Etienne-Châteaucreux (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "backward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886728F16016_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T144100", + "additional_informations": [], + "departure_date_time": "20210218T144100", + "base_arrival_date_time": "20210218T144100", + "base_departure_date_time": "20210218T144100", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886871", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886871", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-743716-BV" + }, + { + "type": "UIC8", + "value": "87743716" + }, + { + "type": "external_code", + "value": "OCE87743716" + } + ], + "name": "Ambérieu-en-Bugey", + "links": [], + "coord": { + "lat": "45.954008", + "lon": "5.342313" + }, + "label": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87743716" + }, + "quality": 0, + "name": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "id": "stop_area:OCE:SA:87743716" + }, + "name": "St-Etienne-Châteaucreux vers Ambérieu-en-Bugey (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "forward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886871F27027_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T151800", + "additional_informations": [], + "departure_date_time": "20210218T151800", + "base_arrival_date_time": "20210218T151800", + "base_departure_date_time": "20210218T151800", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886837", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886837", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-743716-BV" + }, + { + "type": "UIC8", + "value": "87743716" + }, + { + "type": "external_code", + "value": "OCE87743716" + } + ], + "name": "Ambérieu-en-Bugey", + "links": [], + "coord": { + "lat": "45.954008", + "lon": "5.342313" + }, + "label": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87743716" + }, + "quality": 0, + "name": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "id": "stop_area:OCE:SA:87743716" + }, + "name": "St-Etienne-Châteaucreux vers Ambérieu-en-Bugey (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "forward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886837F18018_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T161800", + "additional_informations": [], + "departure_date_time": "20210218T161800", + "base_arrival_date_time": "20210218T161800", + "base_departure_date_time": "20210218T161800", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "St-Etienne-Châteaucreux (Saint-Étienne)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886734", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886734", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-726000-BV" + }, + { + "type": "UIC8", + "value": "87726000" + }, + { + "type": "external_code", + "value": "OCE87726000" + } + ], + "name": "St-Etienne-Châteaucreux", + "links": [], + "coord": { + "lat": "45.443382", + "lon": "4.399996" + }, + "label": "St-Etienne-Châteaucreux (Saint-Étienne)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87726000" + }, + "quality": 0, + "name": "St-Etienne-Châteaucreux (Saint-Étienne)", + "id": "stop_area:OCE:SA:87726000" + }, + "name": "Ambérieu-en-Bugey vers St-Etienne-Châteaucreux (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "backward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886734F19019_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T164100", + "additional_informations": [], + "departure_date_time": "20210218T164100", + "base_arrival_date_time": "20210218T164100", + "base_departure_date_time": "20210218T164100", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886839", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886839", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-743716-BV" + }, + { + "type": "UIC8", + "value": "87743716" + }, + { + "type": "external_code", + "value": "OCE87743716" + } + ], + "name": "Ambérieu-en-Bugey", + "links": [], + "coord": { + "lat": "45.954008", + "lon": "5.342313" + }, + "label": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87743716" + }, + "quality": 0, + "name": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "id": "stop_area:OCE:SA:87743716" + }, + "name": "St-Etienne-Châteaucreux vers Ambérieu-en-Bugey (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "forward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886839F10010_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T164800", + "additional_informations": [], + "departure_date_time": "20210218T164800", + "base_arrival_date_time": "20210218T164800", + "base_departure_date_time": "20210218T164800", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886843", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886843", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-743716-BV" + }, + { + "type": "UIC8", + "value": "87743716" + }, + { + "type": "external_code", + "value": "OCE87743716" + } + ], + "name": "Ambérieu-en-Bugey", + "links": [], + "coord": { + "lat": "45.954008", + "lon": "5.342313" + }, + "label": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87743716" + }, + "quality": 0, + "name": "Ambérieu-en-Bugey (Ambérieu-en-Bugey)", + "id": "stop_area:OCE:SA:87743716" + }, + "name": "St-Etienne-Châteaucreux vers Ambérieu-en-Bugey (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "forward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886843F24024_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87726000-87743716" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T171800", + "additional_informations": [], + "departure_date_time": "20210218T171800", + "base_arrival_date_time": "20210218T171800", + "base_departure_date_time": "20210218T171800", + "data_freshness": "base_schedule" + } + }, + { + "display_informations": { + "direction": "St-Etienne-Châteaucreux (Saint-Étienne)", + "code": "", + "network": "SNCF", + "links": [], + "color": "000000", + "name": "St-Etienne - Lyon - Ambérieu", + "physical_mode": "Train régional / TER", + "headsign": "886738", + "label": "St-Etienne - Lyon - Ambérieu", + "equipments": [], + "text_color": "FFFFFF", + "trip_short_name": "886738", + "commercial_mode": "TER", + "description": "" + }, + "stop_point": { + "commercial_modes": [ + { + "id": "commercial_mode:ter", + "name": "TER" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "equipments": [], + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "fare_zone": { + "name": "0" + }, + "id": "stop_point:OCE:SP:TrainTER-87723502", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-723502-00" + }, + { + "type": "UIC8", + "value": "87723502" + }, + { + "type": "external_code", + "value": "OCE87723502" + } + ], + "name": "Crépieux-la-Pape", + "links": [], + "coord": { + "lat": "45.803921", + "lon": "4.892737" + }, + "label": "Crépieux-la-Pape (Rillieux-la-Pape)", + "administrative_regions": [ + { + "insee": "69286", + "name": "Rillieux-la-Pape", + "level": 8, + "coord": { + "lat": "45.823514", + "lon": "4.8994366" + }, + "label": "Rillieux-la-Pape (69140)", + "id": "admin:fr:69286", + "zip_code": "69140" + } + ], + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87723502" + } + }, + "route": { + "direction": { + "embedded_type": "stop_area", + "stop_area": { + "codes": [ + { + "type": "CR-CI-CH", + "value": "0087-726000-BV" + }, + { + "type": "UIC8", + "value": "87726000" + }, + { + "type": "external_code", + "value": "OCE87726000" + } + ], + "name": "St-Etienne-Châteaucreux", + "links": [], + "coord": { + "lat": "45.443382", + "lon": "4.399996" + }, + "label": "St-Etienne-Châteaucreux (Saint-Étienne)", + "timezone": "Europe/Paris", + "id": "stop_area:OCE:SA:87726000" + }, + "quality": 0, + "name": "St-Etienne-Châteaucreux (Saint-Étienne)", + "id": "stop_area:OCE:SA:87726000" + }, + "name": "Ambérieu-en-Bugey vers St-Etienne-Châteaucreux (Train TER)", + "links": [], + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "is_frequence": "False", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "direction_type": "backward", + "line": { + "code": "", + "name": "St-Etienne - Lyon - Ambérieu", + "links": [], + "color": "000000", + "geojson": { + "type": "MultiLineString", + "coordinates": [] + }, + "text_color": "FFFFFF", + "physical_modes": [ + { + "id": "physical_mode:LocalTrain", + "name": "Train régional / TER" + } + ], + "codes": [], + "closing_time": "221200", + "opening_time": "053500", + "commercial_mode": { + "id": "commercial_mode:ter", + "name": "TER" + }, + "id": "line:OCE:199" + }, + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + "links": [ + { + "type": "line", + "id": "line:OCE:199" + }, + { + "type": "vehicle_journey", + "id": "vehicle_journey:OCE:SN886738F27027_dst_1" + }, + { + "type": "route", + "id": "route:OCE:199-TrainTER-87743716-87726000" + }, + { + "type": "commercial_mode", + "id": "commercial_mode:ter" + }, + { + "type": "physical_mode", + "id": "physical_mode:LocalTrain" + }, + { + "type": "network", + "id": "network:sncf" + } + ], + "stop_date_time": { + "links": [], + "arrival_date_time": "20210218T174100", + "additional_informations": [], + "departure_date_time": "20210218T174100", + "base_arrival_date_time": "20210218T174100", + "base_departure_date_time": "20210218T174100", + "data_freshness": "base_schedule" + } + } + ], + "context": { + "timezone": "Europe/Paris", + "current_datetime": "20210218T125549" + }, + "exceptions": [] +} diff --git a/go.mod b/go.mod new file mode 100644 index 0000000..542b54e --- /dev/null +++ b/go.mod @@ -0,0 +1,3 @@ +module git.adyxax.org/adyxax/trains + +go 1.16 diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..e69de29 -- cgit v1.2.3