handle bad data
where by "handle" we mean that Track.parse now returns an Either instead of making up data points that lie on the equator
This commit is contained in:
parent
a3d48100ae
commit
e15c42ff4a
48
lib/Track.hs
48
lib/Track.hs
@ -53,16 +53,12 @@ gpxNS localName =
|
|||||||
tpxNS localName =
|
tpxNS localName =
|
||||||
Name localName (Just "http://www.garmin.com/xmlschemas/TrackPointExtension/v2") Nothing
|
Name localName (Just "http://www.garmin.com/xmlschemas/TrackPointExtension/v2") Nothing
|
||||||
|
|
||||||
mkPoint pos =
|
|
||||||
Point
|
|
||||||
pos
|
|
||||||
Nothing
|
|
||||||
(UTCTime (toEnum 60631) 43200)
|
|
||||||
Nothing
|
|
||||||
Nothing
|
|
||||||
Nothing
|
|
||||||
|
|
||||||
elToPoint :: Cursor -> Point
|
data BadFile = BadFile deriving (Show)
|
||||||
|
|
||||||
|
instance Exception BadFile
|
||||||
|
|
||||||
|
elToPoint :: Cursor -> Either SomeException Point
|
||||||
elToPoint c =
|
elToPoint c =
|
||||||
case node c of
|
case node c of
|
||||||
NodeElement (Element _ attrs _) ->
|
NodeElement (Element _ attrs _) ->
|
||||||
@ -86,25 +82,27 @@ elToPoint c =
|
|||||||
>>= element (Name "PowerInWatts" (Just "http://www.garmin.com/xmlschemas/PowerExtension/v1") Nothing)
|
>>= element (Name "PowerInWatts" (Just "http://www.garmin.com/xmlschemas/PowerExtension/v1") Nothing)
|
||||||
>>= child
|
>>= child
|
||||||
>>= content
|
>>= content
|
||||||
in Point
|
parsedTime =
|
||||||
(Pos lat lon)
|
listToMaybe ts
|
||||||
( (listToMaybe ele) >>= return . asFloat )
|
>>= (Data.Time.ISO8601.parseISO8601 . Data.Text.unpack)
|
||||||
( case ts of
|
in case parsedTime of
|
||||||
[e] -> case Data.Time.ISO8601.parseISO8601 (Data.Text.unpack e) of
|
Nothing -> Left (toException BadFile)
|
||||||
Just utime -> utime
|
Just utime ->
|
||||||
_ -> UTCTime (toEnum 0) 0
|
Right $
|
||||||
_ -> UTCTime (toEnum 0) 0
|
Point
|
||||||
)
|
(Pos lat lon)
|
||||||
( (listToMaybe cadence) >>= return . asInt)
|
(listToMaybe ele >>= return . asFloat)
|
||||||
( (listToMaybe power) >>= return . asInt)
|
utime
|
||||||
Nothing
|
(listToMaybe cadence >>= return . asInt)
|
||||||
|
(listToMaybe power >>= return . asInt)
|
||||||
|
Nothing
|
||||||
where
|
where
|
||||||
asFloat v = (read (Data.Text.unpack v) :: Float)
|
asFloat v = (read (Data.Text.unpack v) :: Float)
|
||||||
asInt v = (read (Data.Text.unpack v) :: Int)
|
asInt v = (read (Data.Text.unpack v) :: Int)
|
||||||
getAttr name = maybe 0 asFloat (Map.lookup name attrs)
|
getAttr name = maybe 0 asFloat (Map.lookup name attrs)
|
||||||
_ -> mkPoint (Pos 0 0)
|
_ -> Left (toException BadFile)
|
||||||
|
|
||||||
getPoints :: Cursor -> [Point]
|
getPoints :: Cursor -> Either SomeException [Point]
|
||||||
getPoints c =
|
getPoints c =
|
||||||
let trkpts =
|
let trkpts =
|
||||||
element (gpxNS "gpx") c
|
element (gpxNS "gpx") c
|
||||||
@ -112,12 +110,12 @@ getPoints c =
|
|||||||
>>= element (gpxNS "trk")
|
>>= element (gpxNS "trk")
|
||||||
>>= descendant
|
>>= descendant
|
||||||
>>= element (gpxNS "trkpt")
|
>>= element (gpxNS "trkpt")
|
||||||
in List.map elToPoint trkpts
|
in traverse elToPoint trkpts
|
||||||
|
|
||||||
parse :: String -> Either SomeException [Point]
|
parse :: String -> Either SomeException [Point]
|
||||||
parse str = do
|
parse str = do
|
||||||
gpx <- parseText def (T.pack str)
|
gpx <- parseText def (T.pack str)
|
||||||
return (getPoints (fromDocument gpx))
|
getPoints (fromDocument gpx)
|
||||||
|
|
||||||
length :: Track -> Int
|
length :: Track -> Int
|
||||||
length = Data.List.length
|
length = Data.List.length
|
||||||
|
@ -34,7 +34,9 @@ onepoint =
|
|||||||
wrap
|
wrap
|
||||||
[r|
|
[r|
|
||||||
<trk> <trkseg>
|
<trk> <trkseg>
|
||||||
<trkpt lat="51" lon="-0.1"> </trkpt>
|
<trkpt lat="51" lon="-0.1">
|
||||||
|
<time>2024-10-23T08:34:59.779+01:00</time>
|
||||||
|
</trkpt>
|
||||||
</trkseg> </trk>
|
</trkseg> </trk>
|
||||||
|]
|
|]
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user