diff --git a/.gitignore b/.gitignore index f3c7a7c..63b9df5 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ Makefile +gpxhydrant diff --git a/hydrant.go b/hydrant.go new file mode 100644 index 0000000..de52da3 --- /dev/null +++ b/hydrant.go @@ -0,0 +1,138 @@ +package main + +import ( + "fmt" + "regexp" + "strconv" + + "github.com/Luzifer/gpxhydrant/gpx" + "github.com/Luzifer/gpxhydrant/osm" +) + +type hydrant struct { + /* + + + + + + + + + */ + ID int64 + Name string + Latitude float64 + Longitude float64 + Diameter int64 + Position string + Pressure int64 + Type string + Version int64 +} + +func parseWaypoint(in gpx.Waypoint) (*hydrant, error) { + infoRegex := regexp.MustCompile(`([SPLG])([UOWP])(\?|[0-9]{2,3})`) + if !infoRegex.MatchString(in.Comment) { + return nil, errWrongGPXComment + } + + matches := infoRegex.FindStringSubmatch(in.Comment) + out := &hydrant{ + Name: in.Name, + Latitude: roundPrec(in.Latitude, 7), + Longitude: roundPrec(in.Longitude, 7), + Pressure: cfg.Pressure, + } + + switch matches[1] { + case "S": + out.Position = "sidewalk" + case "P": + out.Position = "parking_lot" + case "L": + out.Position = "lane" + case "G": + out.Position = "green" + } + + switch matches[2] { + case "U": + out.Type = "underground" + case "O": + out.Type = "pillar" + case "W": + out.Type = "wall" + case "P": + out.Type = "pond" + } + + if matches[3] != "?" { + diameter, err := strconv.ParseInt(matches[3], 10, 64) + if err != nil { + return nil, err + } + out.Diameter = diameter + } + + return out, nil +} + +func fromNode(in *osm.Node) (*hydrant, error) { + var e error + + out := &hydrant{ + ID: in.ID, + Version: in.Version, + Latitude: in.Latitude, + Longitude: in.Longitude, + } + + validFireHydrant := false + + for _, t := range in.Tags { + switch t.Key { + case "emergency": + if t.Value == "fire_hydrant" { + validFireHydrant = true + } + case "fire_hydrant:diameter": + if out.Diameter, e = strconv.ParseInt(t.Value, 10, 64); e != nil { + return nil, e + } + case "fire_hydrant:position": + out.Position = t.Value + case "fire_hydrant:pressure": + if out.Pressure, e = strconv.ParseInt(t.Value, 10, 64); e != nil { + return nil, e + } + case "fire_hydrant:type": + out.Type = t.Value + } + } + + if !validFireHydrant { + return nil, fmt.Errorf("Did not find required 'emergency=fire_hydrant' tag.") + } + + return out, nil +} + +func (h hydrant) ToNode() *osm.Node { + out := &osm.Node{ + ID: h.ID, + Version: h.Version, + Latitude: h.Latitude, + Longitude: h.Longitude, + } + + out.Tags = append(out.Tags, osm.Tag{Key: "emergency", Value: "fire_hydrant"}) + if h.Diameter > 0 { + out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:diameter", Value: strconv.FormatInt(h.Diameter, 10)}) + } + out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:position", Value: h.Position}) + out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:pressure", Value: strconv.FormatInt(h.Pressure, 10)}) + out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:type", Value: h.Type}) + + return out +} diff --git a/main.go b/main.go index 58fa194..adbb56e 100644 --- a/main.go +++ b/main.go @@ -5,7 +5,6 @@ import ( "fmt" "log" "os" - "regexp" "strconv" "github.com/Luzifer/go_helpers/position" @@ -34,134 +33,6 @@ var ( errWrongGPXComment = errors.New("GPX comment does not match expected format") ) -type hydrant struct { - /* - - - - - - - - - */ - ID int64 - Name string - Latitude float64 - Longitude float64 - Diameter int64 - Position string - Pressure int64 - Type string - Version int64 -} - -func parseWaypoint(in gpx.Waypoint) (*hydrant, error) { - infoRegex := regexp.MustCompile(`([SPLG])([UOWP])(\?|[0-9]{2,3})`) - if !infoRegex.MatchString(in.Comment) { - return nil, errWrongGPXComment - } - - matches := infoRegex.FindStringSubmatch(in.Comment) - out := &hydrant{ - Name: in.Name, - Latitude: roundPrec(in.Latitude, 7), - Longitude: roundPrec(in.Longitude, 7), - Pressure: cfg.Pressure, - } - - switch matches[1] { - case "S": - out.Position = "sidewalk" - case "P": - out.Position = "parking_lot" - case "L": - out.Position = "lane" - case "G": - out.Position = "green" - } - - switch matches[2] { - case "U": - out.Type = "underground" - case "O": - out.Type = "pillar" - case "W": - out.Type = "wall" - case "P": - out.Type = "pond" - } - - if matches[3] != "?" { - diameter, err := strconv.ParseInt(matches[3], 10, 64) - if err != nil { - return nil, err - } - out.Diameter = diameter - } - - return out, nil -} - -func fromNode(in *osm.Node) (*hydrant, error) { - var e error - - out := &hydrant{ - ID: in.ID, - Version: in.Version, - Latitude: in.Latitude, - Longitude: in.Longitude, - } - - validFireHydrant := false - - for _, t := range in.Tags { - switch t.Key { - case "emergency": - if t.Value == "fire_hydrant" { - validFireHydrant = true - } - case "fire_hydrant:diameter": - if out.Diameter, e = strconv.ParseInt(t.Value, 10, 64); e != nil { - return nil, e - } - case "fire_hydrant:position": - out.Position = t.Value - case "fire_hydrant:pressure": - if out.Pressure, e = strconv.ParseInt(t.Value, 10, 64); e != nil { - return nil, e - } - case "fire_hydrant:type": - out.Type = t.Value - } - } - - if !validFireHydrant { - return nil, fmt.Errorf("Did not find required 'emergency=fire_hydrant' tag.") - } - - return out, nil -} - -func (h hydrant) ToNode() *osm.Node { - out := &osm.Node{ - ID: h.ID, - Version: h.Version, - Latitude: h.Latitude, - Longitude: h.Longitude, - } - - out.Tags = append(out.Tags, osm.Tag{Key: "emergency", Value: "fire_hydrant"}) - if h.Diameter > 0 { - out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:diameter", Value: strconv.FormatInt(h.Diameter, 10)}) - } - out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:position", Value: h.Position}) - out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:pressure", Value: strconv.FormatInt(h.Pressure, 10)}) - out.Tags = append(out.Tags, osm.Tag{Key: "fire_hydrant:type", Value: h.Type}) - - return out -} - func init() { rconfig.Parse(&cfg)