diff options
Diffstat (limited to 'lib/Postdelay/TimeSpec.hs')
-rw-r--r-- | lib/Postdelay/TimeSpec.hs | 26 |
1 files changed, 23 insertions, 3 deletions
diff --git a/lib/Postdelay/TimeSpec.hs b/lib/Postdelay/TimeSpec.hs index a72f87e..8244885 100644 --- a/lib/Postdelay/TimeSpec.hs +++ b/lib/Postdelay/TimeSpec.hs | |||
@@ -16,7 +16,8 @@ import Control.Monad.IO.Class | |||
16 | import Control.Applicative | 16 | import Control.Applicative |
17 | import Control.Lens hiding ((#)) | 17 | import Control.Lens hiding ((#)) |
18 | import Control.Exception (IOException) | 18 | import Control.Exception (IOException) |
19 | import Control.Monad.Catch | 19 | import Control.Monad.Catch hiding (try) |
20 | import Control.Monad.RWS hiding ((<>)) | ||
20 | 21 | ||
21 | import Data.Bool | 22 | import Data.Bool |
22 | import Data.Semigroup hiding (option) | 23 | import Data.Semigroup hiding (option) |
@@ -36,11 +37,30 @@ utcOffset :: Iso' TimeZone Time | |||
36 | utcOffset = iso ((% Minute) . fromIntegral . timeZoneMinutes) (minutesToTimeZone . round . (# Minute)) | 37 | utcOffset = iso ((% Minute) . fromIntegral . timeZoneMinutes) (minutesToTimeZone . round . (# Minute)) |
37 | 38 | ||
38 | 39 | ||
39 | timeSpec :: StringParser s m => m (Endo LocalTime) | 40 | timeSpec :: forall s m. StringParser s m => m (Endo LocalTime) |
40 | timeSpec = label "Relative time specification" $ | 41 | timeSpec = label "Relative time specification" $ |
41 | choice [ lexeme (string' "now") *> offsets True | 42 | choice [ flip (<>) <$> lexeme specBase <*> option mempty (offsets True) |
43 | , lexeme (string' "now") *> offsets True | ||
42 | , offsets False | 44 | , offsets False |
43 | ] | 45 | ] |
46 | where | ||
47 | specBase = foldMap toEndo <$> mkGramSepBy spaces [ absDate | ||
48 | , timeOfDay | ||
49 | ] | ||
50 | |||
51 | toEndo :: RWS LocalTime () LocalTime a -> Endo LocalTime | ||
52 | toEndo act = Endo $ \t -> fst $ execRWS act t t | ||
53 | |||
54 | timeOfDay, absDate :: StringParser s m => m (RWS LocalTime () LocalTime ()) | ||
55 | timeOfDay = label "Time of day" $ assign time <$> choice | ||
56 | [ TimeOfDay 0 0 0 <$ string' "midnight" | ||
57 | , TimeOfDay 12 0 0 <$ string' "noon" | ||
58 | , TimeOfDay 16 0 0 <$ string' "teatime" | ||
59 | ] | ||
60 | absDate = label "Date" . (fmap . (=<<) . assign $ date) $ choice | ||
61 | [ view date <$ string' "today" | ||
62 | , views date succ <$ string' "tomorrow" | ||
63 | ] | ||
44 | 64 | ||
45 | offsets :: forall s m. StringParser s m | 65 | offsets :: forall s m. StringParser s m |
46 | => Bool -- ^ Require sign on first offset? | 66 | => Bool -- ^ Require sign on first offset? |