From 86c6ad8781f73979dc8532a59a46e5ef38c13a10 Mon Sep 17 00:00:00 2001 From: Janne Mareike Koschinski <janne@kuschku.de> Date: Sat, 27 Apr 2019 00:13:26 +0200 Subject: [PATCH] Implement suggestions API --- client.go | 52 ++++++++++++++++++++++----- external_suggestion.go | 81 ++++++++++++++++++++++++++++++++++++++++++ model_suggestion.go | 16 +++++++++ 3 files changed, 140 insertions(+), 9 deletions(-) create mode 100644 external_suggestion.go create mode 100644 model_suggestion.go diff --git a/client.go b/client.go index 80ea638..62c865d 100644 --- a/client.go +++ b/client.go @@ -4,12 +4,15 @@ import ( "fmt" "net/http" "time" + + "net/url" ) type ApiClient struct { IrisBaseUrl string CoachSequenceBaseUrl string - HttpClient *http.Client + HafasBaseUrl string + HttpClient *http.Client } func (c *ApiClient) Station(evaId int64) ([]Station, error) { @@ -62,12 +65,12 @@ func (c *ApiClient) Timetable(evaId int64, date time.Time) (Timetable, error) { func (c *ApiClient) RealtimeAll(evaId int64, date time.Time) (Timetable, error) { var err error - url := fmt.Sprintf("%s/timetable/fchg/%d", c.IrisBaseUrl, evaId) + uri := fmt.Sprintf("%s/timetable/fchg/%d", c.IrisBaseUrl, evaId) var timetable Timetable var response *http.Response - if response, err = c.HttpClient.Get(url); err != nil { + if response, err = c.HttpClient.Get(uri); err != nil { return timetable, err } @@ -85,12 +88,12 @@ func (c *ApiClient) RealtimeAll(evaId int64, date time.Time) (Timetable, error) func (c *ApiClient) RealtimeRecent(evaId int64, date time.Time) (Timetable, error) { var err error - url := fmt.Sprintf("%s/timetable/rchg/%d", c.IrisBaseUrl, evaId) + uri := fmt.Sprintf("%s/timetable/rchg/%d", c.IrisBaseUrl, evaId) var timetable Timetable var response *http.Response - if response, err = c.HttpClient.Get(url); err != nil { + if response, err = c.HttpClient.Get(uri); err != nil { return timetable, err } @@ -108,12 +111,12 @@ func (c *ApiClient) RealtimeRecent(evaId int64, date time.Time) (Timetable, erro func (c *ApiClient) WingDefinition(parent string, wing string) (WingDefinition, error) { var err error - url := fmt.Sprintf("%s/timetable/wingdef/%s/%s", c.IrisBaseUrl, parent, wing) + uri := fmt.Sprintf("%s/timetable/wingdef/%s/%s", c.IrisBaseUrl, parent, wing) var wingDefinition WingDefinition var response *http.Response - if response, err = c.HttpClient.Get(url); err != nil { + if response, err = c.HttpClient.Get(uri); err != nil { return wingDefinition, err } @@ -131,12 +134,12 @@ func (c *ApiClient) WingDefinition(parent string, wing string) (WingDefinition, func (c *ApiClient) CoachSequence(line string, date time.Time) (CoachSequence, error) { var err error - url := fmt.Sprintf("%s/%s/%s", c.CoachSequenceBaseUrl, line, date.Format(TimeLayoutShort)) + uri := fmt.Sprintf("%s/%s/%s", c.CoachSequenceBaseUrl, line, date.Format(TimeLayoutShort)) var coachSequence CoachSequence var response *http.Response - if response, err = c.HttpClient.Get(url); err != nil { + if response, err = c.HttpClient.Get(uri); err != nil { return coachSequence, err } @@ -150,3 +153,34 @@ func (c *ApiClient) CoachSequence(line string, date time.Time) (CoachSequence, e return coachSequence, err } + +func (c *ApiClient) Suggestions(line string, date time.Time) ([]Suggestion, error) { + var err error + + uri := fmt.Sprintf("%s/trainsearch.exe/dn", c.HafasBaseUrl) + + var suggestions []Suggestion + + DateFormat := "02.01.2006" + body := url.Values{ + "maxResults": []string{"50"}, + "trainname": []string{line}, + "date": []string{date.Format(DateFormat)}, + "L": []string{"vs_json.vs_hap"}, + } + + var response *http.Response + if response, err = c.HttpClient.PostForm(uri, body); err != nil { + return suggestions, err + } + + if suggestions, err = SuggestionsFromReader(response.Body); err != nil { + return suggestions, err + } + + if err = response.Body.Close(); err != nil { + return suggestions, err + } + + return suggestions, err +} diff --git a/external_suggestion.go b/external_suggestion.go new file mode 100644 index 0000000..954a1d2 --- /dev/null +++ b/external_suggestion.go @@ -0,0 +1,81 @@ +package bahn + +import ( + "encoding/json" + "io" + "time" +) + +func SuggestionsFromReader(source io.Reader) ([]Suggestion, error) { + var raw rawSuggestions + if err := json.NewDecoder(source).Decode(&raw); err != nil { + return make([]Suggestion, 0), err + } + return parseSuggestions(raw), nil +} + +func SuggestionsFromBytes(source []byte) ([]Suggestion, error) { + var raw rawSuggestions + if err := json.Unmarshal(source, &raw); err != nil { + return make([]Suggestion, 0), err + } + return parseSuggestions(raw), nil +} + +type rawSuggestions struct { + Suggestions []rawSuggestion +} + +func parseSuggestions(data rawSuggestions) []Suggestion { + result := make([]Suggestion, len(data.Suggestions)) + for i, element := range data.Suggestions { + result[i] = parseSuggestion(element) + } + return result +} + +type rawSuggestion struct { + Value string `json:"value"` + Cycle string `json:"cycle"` + Pool string `json:"pool"` + Id string `json:"id"` + TrainLink string `json:"trainLink"` + JourneyParams string `json:"journParam"` + PublishedTime string `json:"pubTime"` + PublishedDate string `json:"pubDate"` + DepartureStation string `json:"dep"` + DepartureDate string `json:"depDate"` + DepartureTime string `json:"depTime"` + ArrivalStation string `json:"arr"` + ArrivalTime string `json:"arrTime"` + ArrivalDate string `json:"arrDate"` +} + +func parseTime(dateStr string, timeStr string) *time.Time { + DateFormat := "02.01.2006" + DateTimeFormat := "02.01.2006 15:04" + if dateStr == "" { + dateStr = time.Now().Format(DateFormat) + } + + dateTime, err := time.Parse(DateTimeFormat, dateStr+" "+timeStr) + if err != nil { + return nil + } + return &dateTime +} + +func parseSuggestion(data rawSuggestion) Suggestion { + return Suggestion{ + Value: data.Value, + Cycle: data.Cycle, + Pool: data.Pool, + Id: data.Id, + TrainLink: data.TrainLink, + PublishedTime: parseTime(data.PublishedDate, data.PublishedTime), + DepartureStation: data.DepartureStation, + DepartureTime: parseTime(data.DepartureDate, data.DepartureTime), + ArrivalStation: data.ArrivalStation, + ArrivalTime: parseTime(data.ArrivalDate, data.ArrivalTime), + } +} diff --git a/model_suggestion.go b/model_suggestion.go new file mode 100644 index 0000000..26a5dfb --- /dev/null +++ b/model_suggestion.go @@ -0,0 +1,16 @@ +package bahn + +import "time" + +type Suggestion struct { + Value string + Cycle string + Pool string + Id string + TrainLink string + PublishedTime *time.Time + DepartureStation string + DepartureTime *time.Time + ArrivalStation string + ArrivalTime *time.Time +} -- GitLab