-
Notifications
You must be signed in to change notification settings - Fork 0
/
api.go
108 lines (93 loc) · 2.75 KB
/
api.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
package app
import (
"encoding/xml"
"errors"
"fmt"
"io"
"net/http"
"strconv"
"strings"
"time"
)
var locations = map[string]string{
"Adelaide": "Australia/Adelaide",
"Alice Springs": "Australia/Darwin",
"Brisbane": "Australia/Brisbane",
"Canberra": "Australia/Sydney",
"Casey": "Antarctica/Casey",
"Darwin": "Australia/Darwin",
"Davis": "Antarctica/Davis",
"Emerald": "Australia/Brisbane",
"Gold Coast": "Australia/Brisbane",
"Kingston": "Australia/Hobart",
"Macquarie Island": "Antarctica/Macquarie",
"Mawson": "Antarctica/Mawson",
"Melbourne": "Australia/Melbourne",
"Newcastle": "Australia/Sydney",
"Perth": "Australia/Perth",
"Sydney": "Australia/Sydney",
"Townsville": "Australia/Brisbane",
}
type XMLStations struct {
XMLName xml.Name `xml:"stations"`
Locations []XMLLocation `xml:"location"`
}
type XMLLocation struct {
XMLName xml.Name `xml:"location"`
Id string `xml:"id,attr"`
Name string `xml:"name"`
Index string `xml:"index"`
Time string `xml:"time"`
Date string `xml:"date"`
FullDate string `xml:"fulldate"`
UTCDateTime string `xml:"utcdatetime"`
Status string `xml:"status"`
}
func (xmlStations *XMLStations) Stations() []Station {
var stations []Station
for _, xmlLoc := range xmlStations.Locations {
stations = append(stations, xmlLoc.Station())
}
return stations
}
func (xmlLoc *XMLLocation) Station() Station {
station := Station{
Id: strings.ToUpper(xmlLoc.Name),
Name: xmlLoc.Id,
Available: xmlLoc.Status == "ok",
}
station.UVIndex, _ = strconv.ParseFloat(xmlLoc.Index, 64)
station.Time, _ = time.Parse("2006/01/02 15:04", xmlLoc.UTCDateTime)
if locName, err := getLocationName(station.Name); err == nil {
loc, _ := time.LoadLocation(locName)
station.Time = station.Time.In(loc)
}
if xmlLoc.Status != "ok" {
station.Status = xmlLoc.Status
}
return station
}
func getLocationName(stationName string) (string, error) {
if name, ok := locations[stationName]; !ok {
return name, fmt.Errorf("no time zone configured for station %v", stationName)
} else {
return name, nil
}
}
func getStations() ([]Station, error) {
resp, err := http.Get("https://uvdata.arpansa.gov.au/xml/uvvalues.xml")
if err != nil {
return nil, errors.New("ARPANSA data file unavailable")
}
defer resp.Body.Close()
body, err := io.ReadAll(resp.Body)
if err != nil {
return nil, errors.New("unable to read ARPANSA data file")
}
var xmlStations XMLStations
err = xml.Unmarshal(body, &xmlStations)
if err != nil {
return nil, errors.New("unexpected format of ARPANSA data file")
}
return xmlStations.Stations(), nil
}