diff --git a/src/Web/Internal/HttpApiData.hs b/src/Web/Internal/HttpApiData.hs index 3051680..6246ed2 100644 --- a/src/Web/Internal/HttpApiData.hs +++ b/src/Web/Internal/HttpApiData.hs @@ -456,24 +456,31 @@ timeToUrlPiece :: FormatTime t => String -> t -> Text timeToUrlPiece fmt = T.pack . formatTime defaultTimeLocale (iso8601DateFormat (Just fmt)) -- | --- >>> toUrlPiece $ LocalTime (fromGregorian 2015 10 03) (TimeOfDay 14 55 01) --- "2015-10-03T14:55:01" +-- >>> toUrlPiece $ TimeOfDay 14 55 23.1 +-- "14:55:23.1" +instance ToHttpApiData TimeOfDay where + toUrlPiece = T.pack . formatTime defaultTimeLocale "%H:%M:%S%Q" + toEncodedUrlPiece = unsafeToEncodedUrlPiece + +-- | +-- >>> toUrlPiece $ LocalTime (fromGregorian 2015 10 03) (TimeOfDay 14 55 21.687) +-- "2015-10-03T14:55:21.687" instance ToHttpApiData LocalTime where - toUrlPiece = timeToUrlPiece "%H:%M:%S" + toUrlPiece = timeToUrlPiece "%H:%M:%S%Q" toEncodedUrlPiece = unsafeToEncodedUrlPiece -- | --- >>> toUrlPiece $ ZonedTime (LocalTime (fromGregorian 2015 10 03) (TimeOfDay 14 55 01)) utc --- "2015-10-03T14:55:01+0000" +-- >>> toUrlPiece $ ZonedTime (LocalTime (fromGregorian 2015 10 03) (TimeOfDay 14 55 51.001)) utc +-- "2015-10-03T14:55:51.001+0000" instance ToHttpApiData ZonedTime where - toUrlPiece = timeToUrlPiece "%H:%M:%S%z" + toUrlPiece = timeToUrlPiece "%H:%M:%S%Q%z" toEncodedUrlPiece = unsafeToEncodedUrlPiece -- | --- >>> toUrlPiece $ UTCTime (fromGregorian 2015 10 03) 864 --- "2015-10-03T00:14:24Z" +-- >>> toUrlPiece $ UTCTime (fromGregorian 2015 10 03) 864.5 +-- "2015-10-03T00:14:24.5Z" instance ToHttpApiData UTCTime where - toUrlPiece = timeToUrlPiece "%H:%M:%SZ" + toUrlPiece = timeToUrlPiece "%H:%M:%S%QZ" toEncodedUrlPiece = unsafeToEncodedUrlPiece instance ToHttpApiData NominalDiffTime where @@ -580,7 +587,12 @@ instance FromHttpApiData L.Text where parseUrlPiece = Right . L.fromStrict -- | -- >>> toGregorian <$> parseUrlPiece "2016-12-01" -- Right (2016,12,1) -instance FromHttpApiData Day where parseUrlPiece = runAtto Atto.day +instance FromHttpApiData Day where parseUrlPiece = runAtto Atto.day + +-- | +-- >>> parseUrlPiece "14:55:01.333" :: Either Text TimeOfDay +-- Right 14:55:01.333 +instance FromHttpApiData TimeOfDay where parseUrlPiece = runAtto Atto.timeOfDay -- | -- >>> parseUrlPiece "2015-10-03T14:55:01" :: Either Text LocalTime diff --git a/test/Web/Internal/HttpApiDataSpec.hs b/test/Web/Internal/HttpApiDataSpec.hs index 51e4eef..d9f3eb8 100644 --- a/test/Web/Internal/HttpApiDataSpec.hs +++ b/test/Web/Internal/HttpApiDataSpec.hs @@ -76,6 +76,7 @@ spec = do checkUrlPiece (Proxy :: Proxy T.Text) "Text.Strict" checkUrlPiece (Proxy :: Proxy L.Text) "Text.Lazy" checkUrlPiece (Proxy :: Proxy Day) "Day" + checkUrlPiece' timeOfDayGen "TimeOfDay" checkUrlPiece' localTimeGen "LocalTime" checkUrlPiece' zonedTimeGen "ZonedTime" checkUrlPiece' utcTimeGen "UTCTime" @@ -112,6 +113,7 @@ spec = do checkEncodedUrlPiece (Proxy :: Proxy T.Text) "Text.Strict" checkEncodedUrlPiece (Proxy :: Proxy L.Text) "Text.Lazy" checkEncodedUrlPiece (Proxy :: Proxy Day) "Day" + checkEncodedUrlPiece' timeOfDayGen "TimeOfDay" checkEncodedUrlPiece' localTimeGen "LocalTime" checkEncodedUrlPiece' zonedTimeGen "ZonedTime" checkEncodedUrlPiece' utcTimeGen "UTCTime" @@ -144,9 +146,13 @@ uuidGen = UUID.fromWords <$> arbitrary <*> arbitrary <*> arbitrary <*> arbitrary -- TODO: this generators don't generate full range items localTimeGen :: Gen LocalTime -localTimeGen = LocalTime - <$> arbitrary - <*> liftA3 TimeOfDay (choose (0, 23)) (choose (0, 59)) (fromInteger <$> choose (0, 60)) +localTimeGen = LocalTime <$> arbitrary <*> timeOfDayGen + +timeOfDayGen :: Gen TimeOfDay +timeOfDayGen = TimeOfDay + <$> choose (0, 23) + <*> choose (0, 59) + <*> fmap (\x -> 0.1 * fromInteger x) (choose (0, 600)) zonedTimeGen :: Gen ZonedTime zonedTimeGen = ZonedTime