{-# LANGUAGE Safe #-}

{-# OPTIONS -fno-warn-orphans #-}

module Data.Time.Format.Parse.Instances (
    ) where

import Control.Applicative ((<|>))
import Data.Char
import Data.Fixed
import Data.List (elemIndex, find)
import Data.Ratio
import Data.Time.Calendar.CalendarDiffDays
import Data.Time.Calendar.Days
import Data.Time.Calendar.Gregorian
import Data.Time.Calendar.Month
import Data.Time.Calendar.OrdinalDate
import Data.Time.Calendar.Private (clipValid)
import Data.Time.Calendar.WeekDate
import Data.Time.Clock.Internal.DiffTime
import Data.Time.Clock.Internal.NominalDiffTime
import Data.Time.Clock.Internal.UTCTime
import Data.Time.Clock.Internal.UniversalTime
import Data.Time.Clock.POSIX
import Data.Time.Format.Locale
import Data.Time.Format.Parse.Class
import Data.Time.LocalTime.Internal.CalendarDiffTime
import Data.Time.LocalTime.Internal.LocalTime
import Data.Time.LocalTime.Internal.TimeOfDay
import Data.Time.LocalTime.Internal.TimeZone
import Data.Time.LocalTime.Internal.ZonedTime
import Data.Traversable
import Text.Read (readMaybe)

data DayComponent
    = DCCentury Integer -- century of all years
    | DCCenturyYear Integer -- 0-99, last two digits of both real years and week years
    | DCYearMonth MonthOfYear -- 1-12
    | DCMonthDay DayOfMonth -- 1-31
    | DCYearDay DayOfYear -- 1-366
    | DCWeekDay Int -- 1-7 (mon-sun)
    | DCYearWeek
        WeekType
        WeekOfYear -- 1-53 or 0-53

data WeekType
    = ISOWeek
    | SundayWeek
    | MondayWeek

makeDayComponent :: TimeLocale -> Char -> String -> Maybe [DayComponent]
makeDayComponent :: TimeLocale -> Char -> [Char] -> Maybe [DayComponent]
makeDayComponent TimeLocale
l Char
c [Char]
x = let
    ra :: (Read a) => Maybe a
    ra :: forall a. Read a => Maybe a
ra = [Char] -> Maybe a
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
x
    zeroBasedListIndex :: [String] -> Maybe Int
    zeroBasedListIndex :: [[Char]] -> Maybe Int
zeroBasedListIndex [[Char]]
ss = [Char] -> [[Char]] -> Maybe Int
forall a. Eq a => a -> [a] -> Maybe Int
elemIndex ((Char -> Char) -> [Char] -> [Char]
forall a b. (a -> b) -> [a] -> [b]
map Char -> Char
toUpper [Char]
x) ([[Char]] -> Maybe Int) -> [[Char]] -> Maybe Int
forall a b. (a -> b) -> a -> b
$ ([Char] -> [Char]) -> [[Char]] -> [[Char]]
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap ((Char -> Char) -> [Char] -> [Char]
forall a b. (a -> b) -> [a] -> [b]
map Char -> Char
toUpper) [[Char]]
ss
    oneBasedListIndex :: [String] -> Maybe Int
    oneBasedListIndex :: [[Char]] -> Maybe Int
oneBasedListIndex [[Char]]
ss = do
        index <- [[Char]] -> Maybe Int
zeroBasedListIndex [[Char]]
ss
        return $ 1 + index
    in case Char
c of
        -- %C: century (all but the last two digits of the year), 00 - 99
        Char
'C' -> do
            a <- Maybe Integer
forall a. Read a => Maybe a
ra
            return [DCCentury a]
        -- %f century (all but the last two digits of the year), 00 - 99
        Char
'f' -> do
            a <- Maybe Integer
forall a. Read a => Maybe a
ra
            return [DCCentury a]
        -- %Y: year
        Char
'Y' -> do
            a <- Maybe Integer
forall a. Read a => Maybe a
ra
            return [DCCentury (a `div` 100), DCCenturyYear (a `mod` 100)]
        -- %G: year for Week Date format
        Char
'G' -> do
            a <- Maybe Integer
forall a. Read a => Maybe a
ra
            return [DCCentury (a `div` 100), DCCenturyYear (a `mod` 100)]
        -- %y: last two digits of year, 00 - 99
        Char
'y' -> do
            a <- Maybe Integer
forall a. Read a => Maybe a
ra
            return [DCCenturyYear a]
        -- %g: last two digits of year for Week Date format, 00 - 99
        Char
'g' -> do
            a <- Maybe Integer
forall a. Read a => Maybe a
ra
            return [DCCenturyYear a]
        -- %B: month name, long form (fst from months locale), January - December
        Char
'B' -> do
            a <- [[Char]] -> Maybe Int
oneBasedListIndex ([[Char]] -> Maybe Int) -> [[Char]] -> Maybe Int
forall a b. (a -> b) -> a -> b
$ (([Char], [Char]) -> [Char]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap ([Char], [Char]) -> [Char]
forall a b. (a, b) -> a
fst ([([Char], [Char])] -> [[Char]]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> a -> b
$ TimeLocale -> [([Char], [Char])]
months TimeLocale
l
            return [DCYearMonth a]
        -- %b: month name, short form (snd from months locale), Jan - Dec
        Char
'b' -> do
            a <- [[Char]] -> Maybe Int
oneBasedListIndex ([[Char]] -> Maybe Int) -> [[Char]] -> Maybe Int
forall a b. (a -> b) -> a -> b
$ (([Char], [Char]) -> [Char]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap ([Char], [Char]) -> [Char]
forall a b. (a, b) -> b
snd ([([Char], [Char])] -> [[Char]]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> a -> b
$ TimeLocale -> [([Char], [Char])]
months TimeLocale
l
            return [DCYearMonth a]
        -- %m: month of year, leading 0 as needed, 01 - 12
        Char
'm' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 1 12 raw
            return [DCYearMonth a]
        -- %d: day of month, leading 0 as needed, 01 - 31
        Char
'd' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 1 31 raw
            return [DCMonthDay a]
        -- %e: day of month, leading space as needed, 1 - 31
        Char
'e' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 1 31 raw
            return [DCMonthDay a]
        -- %V: week for Week Date format, 01 - 53
        Char
'V' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 1 53 raw
            return [DCYearWeek ISOWeek a]
        -- %U: week number of year, where weeks start on Sunday (as sundayStartWeek), 00 - 53
        Char
'U' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 0 53 raw
            return [DCYearWeek SundayWeek a]
        -- %W: week number of year, where weeks start on Monday (as mondayStartWeek), 00 - 53
        Char
'W' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 0 53 raw
            return [DCYearWeek MondayWeek a]
        -- %u: day for Week Date format, 1 - 7
        Char
'u' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 1 7 raw
            return [DCWeekDay a]
        -- %a: day of week, short form (snd from wDays locale), Sun - Sat
        Char
'a' -> do
            a' <- [[Char]] -> Maybe Int
zeroBasedListIndex ([[Char]] -> Maybe Int) -> [[Char]] -> Maybe Int
forall a b. (a -> b) -> a -> b
$ (([Char], [Char]) -> [Char]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap ([Char], [Char]) -> [Char]
forall a b. (a, b) -> b
snd ([([Char], [Char])] -> [[Char]]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> a -> b
$ TimeLocale -> [([Char], [Char])]
wDays TimeLocale
l
            let
                a =
                    if Int
a' Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0
                        then Int
7
                        else Int
a'
            return [DCWeekDay a]
        -- %A: day of week, long form (fst from wDays locale), Sunday - Saturday
        Char
'A' -> do
            a' <- [[Char]] -> Maybe Int
zeroBasedListIndex ([[Char]] -> Maybe Int) -> [[Char]] -> Maybe Int
forall a b. (a -> b) -> a -> b
$ (([Char], [Char]) -> [Char]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap ([Char], [Char]) -> [Char]
forall a b. (a, b) -> a
fst ([([Char], [Char])] -> [[Char]]) -> [([Char], [Char])] -> [[Char]]
forall a b. (a -> b) -> a -> b
$ TimeLocale -> [([Char], [Char])]
wDays TimeLocale
l
            let
                a =
                    if Int
a' Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0
                        then Int
7
                        else Int
a'
            return [DCWeekDay a]
        -- %w: day of week number, 0 (= Sunday) - 6 (= Saturday)
        Char
'w' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a' <- clipValid 0 6 raw
            let
                a =
                    if Int
a' Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0
                        then Int
7
                        else Int
a'
            return [DCWeekDay a]
        -- %j: day of year for Ordinal Date format, 001 - 366
        Char
'j' -> do
            raw <- Maybe Int
forall a. Read a => Maybe a
ra
            a <- clipValid 1 366 raw
            return [DCYearDay a]
        -- unrecognised, pass on to other parsers
        Char
_ -> [DayComponent] -> Maybe [DayComponent]
forall a. a -> Maybe a
forall (m :: * -> *) a. Monad m => a -> m a
return []

makeDayComponents :: TimeLocale -> [(Char, String)] -> Maybe [DayComponent]
makeDayComponents :: TimeLocale -> [(Char, [Char])] -> Maybe [DayComponent]
makeDayComponents TimeLocale
l [(Char, [Char])]
pairs = do
    components <- [(Char, [Char])]
-> ((Char, [Char]) -> Maybe [DayComponent])
-> Maybe [[DayComponent]]
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
t a -> (a -> f b) -> f (t b)
for [(Char, [Char])]
pairs (((Char, [Char]) -> Maybe [DayComponent])
 -> Maybe [[DayComponent]])
-> ((Char, [Char]) -> Maybe [DayComponent])
-> Maybe [[DayComponent]]
forall a b. (a -> b) -> a -> b
$ \(Char
c, [Char]
x) -> TimeLocale -> Char -> [Char] -> Maybe [DayComponent]
makeDayComponent TimeLocale
l Char
c [Char]
x
    return $ concat components

safeLast :: a -> [a] -> a
safeLast :: forall a. a -> [a] -> a
safeLast a
x [a]
xs = [a] -> a
forall a. HasCallStack => [a] -> a
last (a
x a -> [a] -> [a]
forall a. a -> [a] -> [a]
: [a]
xs)

instance ParseTime Day where
    substituteTimeSpecifier :: Proxy Day -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy Day
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy Day
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy Day
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe Day
buildTime TimeLocale
l [(Char, [Char])]
pairs = do
        cs <- TimeLocale -> [(Char, [Char])] -> Maybe [DayComponent]
makeDayComponents TimeLocale
l [(Char, [Char])]
pairs
        -- 'Nothing' indicates a parse failure,
        -- while 'Just []' means no information
        let
            y = let
                d :: Integer
d = Integer -> [Integer] -> Integer
forall a. a -> [a] -> a
safeLast Integer
70 [Integer
x | DCCenturyYear Integer
x <- [DayComponent]
cs]
                c :: Integer
c =
                    Integer -> [Integer] -> Integer
forall a. a -> [a] -> a
safeLast
                        ( if Integer
d Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= Integer
69
                            then Integer
19
                            else Integer
20
                        )
                        [Integer
x | DCCentury Integer
x <- [DayComponent]
cs]
                in Integer
100 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
c Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
d
            rest (DCYearMonth Int
m : [DayComponent]
_) = let
                d :: Int
d = Int -> [Int] -> Int
forall a. a -> [a] -> a
safeLast Int
1 [Int
x | DCMonthDay Int
x <- [DayComponent]
cs]
                in Integer -> Int -> Int -> Maybe Day
fromGregorianValid Integer
y Int
m Int
d
            rest (DCYearDay Int
d : [DayComponent]
_) = Integer -> Int -> Maybe Day
fromOrdinalDateValid Integer
y Int
d
            rest (DCYearWeek WeekType
wt Int
w : [DayComponent]
_) = let
                d :: Int
d = Int -> [Int] -> Int
forall a. a -> [a] -> a
safeLast Int
4 [Int
x | DCWeekDay Int
x <- [DayComponent]
cs]
                in case WeekType
wt of
                    WeekType
ISOWeek -> Integer -> Int -> Int -> Maybe Day
fromWeekDateValid Integer
y Int
w Int
d
                    WeekType
SundayWeek -> Integer -> Int -> Int -> Maybe Day
fromSundayStartWeekValid Integer
y Int
w (Int
d Int -> Int -> Int
forall a. Integral a => a -> a -> a
`mod` Int
7)
                    WeekType
MondayWeek -> Integer -> Int -> Int -> Maybe Day
fromMondayStartWeekValid Integer
y Int
w Int
d
            rest (DayComponent
_ : [DayComponent]
xs) = [DayComponent] -> Maybe Day
rest [DayComponent]
xs
            rest [] = [DayComponent] -> Maybe Day
rest [Int -> DayComponent
DCYearMonth Int
1]
        rest cs

instance ParseTime Month where
    substituteTimeSpecifier :: Proxy Month -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy Month
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy Month
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy Month
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe Month
buildTime TimeLocale
l [(Char, [Char])]
pairs = do
        cs <- TimeLocale -> [(Char, [Char])] -> Maybe [DayComponent]
makeDayComponents TimeLocale
l [(Char, [Char])]
pairs
        -- 'Nothing' indicates a parse failure,
        -- while 'Just []' means no information
        let
            y = let
                d :: Integer
d = Integer -> [Integer] -> Integer
forall a. a -> [a] -> a
safeLast Integer
70 [Integer
x | DCCenturyYear Integer
x <- [DayComponent]
cs]
                c :: Integer
c =
                    Integer -> [Integer] -> Integer
forall a. a -> [a] -> a
safeLast
                        ( if Integer
d Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= Integer
69
                            then Integer
19
                            else Integer
20
                        )
                        [Integer
x | DCCentury Integer
x <- [DayComponent]
cs]
                in Integer
100 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
c Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
d
            rest (DCYearMonth Int
m : [DayComponent]
_) = Integer -> Int -> Maybe Month
fromYearMonthValid Integer
y Int
m
            rest (DayComponent
_ : [DayComponent]
xs) = [DayComponent] -> Maybe Month
rest [DayComponent]
xs
            rest [] = Integer -> Int -> Maybe Month
fromYearMonthValid Integer
y Int
1
        rest cs

mfoldl :: (Monad m) => (a -> b -> m a) -> m a -> [b] -> m a
mfoldl :: forall (m :: * -> *) a b.
Monad m =>
(a -> b -> m a) -> m a -> [b] -> m a
mfoldl a -> b -> m a
f = let
    mf :: m a -> b -> m a
mf m a
ma b
b = do
        a <- m a
ma
        f a b
    in (m a -> b -> m a) -> m a -> [b] -> m a
forall b a. (b -> a -> b) -> b -> [a] -> b
forall (t :: * -> *) b a.
Foldable t =>
(b -> a -> b) -> b -> t a -> b
foldl m a -> b -> m a
mf

instance ParseTime TimeOfDay where
    substituteTimeSpecifier :: Proxy TimeOfDay -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy TimeOfDay
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy TimeOfDay
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy TimeOfDay
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe TimeOfDay
buildTime TimeLocale
l = let
        f :: TimeOfDay -> (Char, [Char]) -> Maybe TimeOfDay
f t :: TimeOfDay
t@(TimeOfDay Int
h Int
m Pico
s) (Char
c, [Char]
x) = let
            ra :: (Read a) => Maybe a
            ra :: forall a. Read a => Maybe a
ra = [Char] -> Maybe a
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
x
            getAmPm :: Maybe TimeOfDay
getAmPm = let
                upx :: [Char]
upx = (Char -> Char) -> [Char] -> [Char]
forall a b. (a -> b) -> [a] -> [b]
map Char -> Char
toUpper [Char]
x
                ([Char]
amStr, [Char]
pmStr) = TimeLocale -> ([Char], [Char])
amPm TimeLocale
l
                in if [Char]
upx [Char] -> [Char] -> Bool
forall a. Eq a => a -> a -> Bool
== [Char]
amStr
                    then TimeOfDay -> Maybe TimeOfDay
forall a. a -> Maybe a
Just (TimeOfDay -> Maybe TimeOfDay) -> TimeOfDay -> Maybe TimeOfDay
forall a b. (a -> b) -> a -> b
$ Int -> Int -> Pico -> TimeOfDay
TimeOfDay (Int
h Int -> Int -> Int
forall a. Integral a => a -> a -> a
`mod` Int
12) Int
m Pico
s
                    else
                        if [Char]
upx [Char] -> [Char] -> Bool
forall a. Eq a => a -> a -> Bool
== [Char]
pmStr
                            then
                                TimeOfDay -> Maybe TimeOfDay
forall a. a -> Maybe a
Just (TimeOfDay -> Maybe TimeOfDay) -> TimeOfDay -> Maybe TimeOfDay
forall a b. (a -> b) -> a -> b
$
                                    Int -> Int -> Pico -> TimeOfDay
TimeOfDay
                                        ( if Int
h Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
< Int
12
                                            then Int
h Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
12
                                            else Int
h
                                        )
                                        Int
m
                                        Pico
s
                            else Maybe TimeOfDay
forall a. Maybe a
Nothing
            in case Char
c of
                Char
'P' -> Maybe TimeOfDay
getAmPm
                Char
'p' -> Maybe TimeOfDay
getAmPm
                Char
'H' -> do
                    raw <- Maybe Int
forall a. Read a => Maybe a
ra
                    a <- clipValid 0 23 raw
                    return $ TimeOfDay a m s
                Char
'I' -> do
                    raw <- Maybe Int
forall a. Read a => Maybe a
ra
                    a <- clipValid 1 12 raw
                    return $ TimeOfDay a m s
                Char
'k' -> do
                    raw <- Maybe Int
forall a. Read a => Maybe a
ra
                    a <- clipValid 0 23 raw
                    return $ TimeOfDay a m s
                Char
'l' -> do
                    raw <- Maybe Int
forall a. Read a => Maybe a
ra
                    a <- clipValid 1 12 raw
                    return $ TimeOfDay a m s
                Char
'M' -> do
                    raw <- Maybe Int
forall a. Read a => Maybe a
ra
                    a <- clipValid 0 59 raw
                    return $ TimeOfDay h a s
                Char
'S' -> do
                    raw <- Maybe Integer
forall a. Read a => Maybe a
ra
                    a <- clipValid 0 60 raw
                    return $ TimeOfDay h m (fromInteger a)
                Char
'q' -> do
                    ps <- ([Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe ([Char] -> Maybe Integer) -> [Char] -> Maybe Integer
forall a b. (a -> b) -> a -> b
$ Int -> [Char] -> [Char]
forall a. Int -> [a] -> [a]
take Int
12 ([Char] -> [Char]) -> [Char] -> [Char]
forall a b. (a -> b) -> a -> b
$ Int -> Char -> [Char] -> [Char]
forall a. Int -> a -> [a] -> [a]
rpad Int
12 Char
'0' [Char]
x) Maybe Integer -> Maybe Integer -> Maybe Integer
forall a. Maybe a -> Maybe a -> Maybe a
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> Integer -> Maybe Integer
forall a. a -> Maybe a
forall (m :: * -> *) a. Monad m => a -> m a
return Integer
0
                    return $ TimeOfDay h m (mkPico (floor s) ps)
                Char
'Q' ->
                    if [Char] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [Char]
x
                        then TimeOfDay -> Maybe TimeOfDay
forall a. a -> Maybe a
Just TimeOfDay
t
                        else do
                            ps <- ([Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe ([Char] -> Maybe Integer) -> [Char] -> Maybe Integer
forall a b. (a -> b) -> a -> b
$ Int -> [Char] -> [Char]
forall a. Int -> [a] -> [a]
take Int
12 ([Char] -> [Char]) -> [Char] -> [Char]
forall a b. (a -> b) -> a -> b
$ Int -> Char -> [Char] -> [Char]
forall a. Int -> a -> [a] -> [a]
rpad Int
12 Char
'0' [Char]
x) Maybe Integer -> Maybe Integer -> Maybe Integer
forall a. Maybe a -> Maybe a -> Maybe a
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> Integer -> Maybe Integer
forall a. a -> Maybe a
forall (m :: * -> *) a. Monad m => a -> m a
return Integer
0
                            return $ TimeOfDay h m (mkPico (floor s) ps)
                Char
_ -> TimeOfDay -> Maybe TimeOfDay
forall a. a -> Maybe a
Just TimeOfDay
t
        in (TimeOfDay -> (Char, [Char]) -> Maybe TimeOfDay)
-> Maybe TimeOfDay -> [(Char, [Char])] -> Maybe TimeOfDay
forall (m :: * -> *) a b.
Monad m =>
(a -> b -> m a) -> m a -> [b] -> m a
mfoldl TimeOfDay -> (Char, [Char]) -> Maybe TimeOfDay
f (TimeOfDay -> Maybe TimeOfDay
forall a. a -> Maybe a
Just TimeOfDay
midnight)

rpad :: Int -> a -> [a] -> [a]
rpad :: forall a. Int -> a -> [a] -> [a]
rpad Int
n a
c [a]
xs = [a]
xs [a] -> [a] -> [a]
forall a. [a] -> [a] -> [a]
++ Int -> a -> [a]
forall a. Int -> a -> [a]
replicate (Int
n Int -> Int -> Int
forall a. Num a => a -> a -> a
- [a] -> Int
forall a. [a] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
length [a]
xs) a
c

mkPico :: Integer -> Integer -> Pico
mkPico :: Integer -> Integer -> Pico
mkPico Integer
i Integer
f = Integer -> Pico
forall a. Num a => Integer -> a
fromInteger Integer
i Pico -> Pico -> Pico
forall a. Num a => a -> a -> a
+ Rational -> Pico
forall a. Fractional a => Rational -> a
fromRational (Integer
f Integer -> Integer -> Rational
forall a. Integral a => a -> a -> Ratio a
% Integer
1000000000000)

instance ParseTime LocalTime where
    substituteTimeSpecifier :: Proxy LocalTime -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy LocalTime
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy LocalTime
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy LocalTime
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe LocalTime
buildTime TimeLocale
l [(Char, [Char])]
xs = Day -> TimeOfDay -> LocalTime
LocalTime (Day -> TimeOfDay -> LocalTime)
-> Maybe Day -> Maybe (TimeOfDay -> LocalTime)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (TimeLocale -> [(Char, [Char])] -> Maybe Day
forall t. ParseTime t => TimeLocale -> [(Char, [Char])] -> Maybe t
buildTime TimeLocale
l [(Char, [Char])]
xs) Maybe (TimeOfDay -> LocalTime)
-> Maybe TimeOfDay -> Maybe LocalTime
forall a b. Maybe (a -> b) -> Maybe a -> Maybe b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (TimeLocale -> [(Char, [Char])] -> Maybe TimeOfDay
forall t. ParseTime t => TimeLocale -> [(Char, [Char])] -> Maybe t
buildTime TimeLocale
l [(Char, [Char])]
xs)

enumDiff :: (Enum a) => a -> a -> Int
enumDiff :: forall a. Enum a => a -> a -> Int
enumDiff a
a a
b = (a -> Int
forall a. Enum a => a -> Int
fromEnum a
a) Int -> Int -> Int
forall a. Num a => a -> a -> a
- (a -> Int
forall a. Enum a => a -> Int
fromEnum a
b)

getMilZoneHours :: Char -> Maybe Int
getMilZoneHours :: Char -> Maybe Int
getMilZoneHours Char
c
    | Char
c Char -> Char -> Bool
forall a. Ord a => a -> a -> Bool
< Char
'A' = Maybe Int
forall a. Maybe a
Nothing
getMilZoneHours Char
c
    | Char
c Char -> Char -> Bool
forall a. Ord a => a -> a -> Bool
<= Char
'I' = Int -> Maybe Int
forall a. a -> Maybe a
Just (Int -> Maybe Int) -> Int -> Maybe Int
forall a b. (a -> b) -> a -> b
$ Int
1 Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Char -> Char -> Int
forall a. Enum a => a -> a -> Int
enumDiff Char
c Char
'A'
getMilZoneHours Char
'J' = Maybe Int
forall a. Maybe a
Nothing
getMilZoneHours Char
c
    | Char
c Char -> Char -> Bool
forall a. Ord a => a -> a -> Bool
<= Char
'M' = Int -> Maybe Int
forall a. a -> Maybe a
Just (Int -> Maybe Int) -> Int -> Maybe Int
forall a b. (a -> b) -> a -> b
$ Int
10 Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Char -> Char -> Int
forall a. Enum a => a -> a -> Int
enumDiff Char
c Char
'K'
getMilZoneHours Char
c
    | Char
c Char -> Char -> Bool
forall a. Ord a => a -> a -> Bool
<= Char
'Y' = Int -> Maybe Int
forall a. a -> Maybe a
Just (Int -> Maybe Int) -> Int -> Maybe Int
forall a b. (a -> b) -> a -> b
$ (Char -> Char -> Int
forall a. Enum a => a -> a -> Int
enumDiff Char
'N' Char
c) Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1
getMilZoneHours Char
'Z' = Int -> Maybe Int
forall a. a -> Maybe a
Just Int
0
getMilZoneHours Char
_ = Maybe Int
forall a. Maybe a
Nothing

getMilZone :: Char -> Maybe TimeZone
getMilZone :: Char -> Maybe TimeZone
getMilZone Char
c = let
    yc :: Char
yc = Char -> Char
toUpper Char
c
    in do
        hours <- Char -> Maybe Int
getMilZoneHours Char
yc
        return $ TimeZone (hours * 60) False [yc]

getKnownTimeZone :: TimeLocale -> String -> Maybe TimeZone
getKnownTimeZone :: TimeLocale -> [Char] -> Maybe TimeZone
getKnownTimeZone TimeLocale
locale [Char]
x = (TimeZone -> Bool) -> [TimeZone] -> Maybe TimeZone
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Maybe a
find (\TimeZone
tz -> (Char -> Char) -> [Char] -> [Char]
forall a b. (a -> b) -> [a] -> [b]
map Char -> Char
toUpper [Char]
x [Char] -> [Char] -> Bool
forall a. Eq a => a -> a -> Bool
== TimeZone -> [Char]
timeZoneName TimeZone
tz) (TimeLocale -> [TimeZone]
knownTimeZones TimeLocale
locale)

instance ParseTime TimeZone where
    substituteTimeSpecifier :: Proxy TimeZone -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy TimeZone
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy TimeZone
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy TimeZone
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe TimeZone
buildTime TimeLocale
l = let
        f :: Char -> String -> TimeZone -> Maybe TimeZone
        f :: Char -> [Char] -> TimeZone -> Maybe TimeZone
f Char
'z' [Char]
str (TimeZone Int
_ Bool
dst [Char]
name)
            | Just Int
offset <- [Char] -> Maybe Int
readTzOffset [Char]
str = TimeZone -> Maybe TimeZone
forall a. a -> Maybe a
Just (TimeZone -> Maybe TimeZone) -> TimeZone -> Maybe TimeZone
forall a b. (a -> b) -> a -> b
$ Int -> Bool -> [Char] -> TimeZone
TimeZone Int
offset Bool
dst [Char]
name
        f Char
'z' [Char]
_ TimeZone
_ = Maybe TimeZone
forall a. Maybe a
Nothing
        f Char
'Z' [Char]
str TimeZone
_
            | Just Int
offset <- [Char] -> Maybe Int
readTzOffset [Char]
str = TimeZone -> Maybe TimeZone
forall a. a -> Maybe a
Just (TimeZone -> Maybe TimeZone) -> TimeZone -> Maybe TimeZone
forall a b. (a -> b) -> a -> b
$ Int -> Bool -> [Char] -> TimeZone
TimeZone Int
offset Bool
False [Char]
""
        f Char
'Z' [Char]
str TimeZone
_
            | Just TimeZone
zone <- TimeLocale -> [Char] -> Maybe TimeZone
getKnownTimeZone TimeLocale
l [Char]
str = TimeZone -> Maybe TimeZone
forall a. a -> Maybe a
Just TimeZone
zone
        f Char
'Z' [Char]
"UTC" TimeZone
_ = TimeZone -> Maybe TimeZone
forall a. a -> Maybe a
Just TimeZone
utc
        f Char
'Z' [Char
c] TimeZone
_
            | Just TimeZone
zone <- Char -> Maybe TimeZone
getMilZone Char
c = TimeZone -> Maybe TimeZone
forall a. a -> Maybe a
Just TimeZone
zone
        f Char
'Z' [Char]
_ TimeZone
_ = Maybe TimeZone
forall a. Maybe a
Nothing
        f Char
_ [Char]
_ TimeZone
tz = TimeZone -> Maybe TimeZone
forall a. a -> Maybe a
Just TimeZone
tz
        in (Maybe TimeZone -> (Char, [Char]) -> Maybe TimeZone)
-> Maybe TimeZone -> [(Char, [Char])] -> Maybe TimeZone
forall b a. (b -> a -> b) -> b -> [a] -> b
forall (t :: * -> *) b a.
Foldable t =>
(b -> a -> b) -> b -> t a -> b
foldl (\Maybe TimeZone
mt (Char
c, [Char]
s) -> Maybe TimeZone
mt Maybe TimeZone -> (TimeZone -> Maybe TimeZone) -> Maybe TimeZone
forall a b. Maybe a -> (a -> Maybe b) -> Maybe b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= Char -> [Char] -> TimeZone -> Maybe TimeZone
f Char
c [Char]
s) (TimeZone -> Maybe TimeZone
forall a. a -> Maybe a
Just (TimeZone -> Maybe TimeZone) -> TimeZone -> Maybe TimeZone
forall a b. (a -> b) -> a -> b
$ Int -> TimeZone
minutesToTimeZone Int
0)

readTzOffset :: String -> Maybe Int
readTzOffset :: [Char] -> Maybe Int
readTzOffset [Char]
str = let
    getSign :: Char -> Maybe a
getSign Char
'+' = a -> Maybe a
forall a. a -> Maybe a
Just a
1
    getSign Char
'-' = a -> Maybe a
forall a. a -> Maybe a
Just (-a
1)
    getSign Char
_ = Maybe a
forall a. Maybe a
Nothing
    calc :: Char -> Char -> Char -> Char -> Char -> Maybe b
calc Char
s Char
h1 Char
h2 Char
m1 Char
m2 = do
        sign <- Char -> Maybe b
forall {a}. Num a => Char -> Maybe a
getSign Char
s
        h <- readMaybe [h1, h2]
        m <- readMaybe [m1, m2]
        return $ sign * (60 * h + m)
    in case [Char]
str of
        (Char
s : Char
h1 : Char
h2 : Char
':' : Char
m1 : Char
m2 : []) -> Char -> Char -> Char -> Char -> Char -> Maybe Int
forall {b}.
(Num b, Read b) =>
Char -> Char -> Char -> Char -> Char -> Maybe b
calc Char
s Char
h1 Char
h2 Char
m1 Char
m2
        (Char
s : Char
h1 : Char
h2 : Char
m1 : Char
m2 : []) -> Char -> Char -> Char -> Char -> Char -> Maybe Int
forall {b}.
(Num b, Read b) =>
Char -> Char -> Char -> Char -> Char -> Maybe b
calc Char
s Char
h1 Char
h2 Char
m1 Char
m2
        [Char]
_ -> Maybe Int
forall a. Maybe a
Nothing

instance ParseTime ZonedTime where
    substituteTimeSpecifier :: Proxy ZonedTime -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy ZonedTime
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy ZonedTime
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy ZonedTime
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe ZonedTime
buildTime TimeLocale
l [(Char, [Char])]
xs = let
        f :: ZonedTime -> (Char, [Char]) -> Maybe ZonedTime
f (ZonedTime (LocalTime Day
_ TimeOfDay
tod) TimeZone
z) (Char
's', [Char]
x) = do
            a <- [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
x
            let
                s = Integer -> POSIXTime
forall a. Num a => Integer -> a
fromInteger Integer
a
                (_, ps) = properFraction (todSec tod) :: (Integer, Pico)
                s' = POSIXTime
s POSIXTime -> POSIXTime -> POSIXTime
forall a. Num a => a -> a -> a
+ Rational -> POSIXTime
forall a. Fractional a => Rational -> a
fromRational (Pico -> Rational
forall a. Real a => a -> Rational
toRational Pico
ps)
            return $ utcToZonedTime z (posixSecondsToUTCTime s')
        f ZonedTime
t (Char, [Char])
_ = ZonedTime -> Maybe ZonedTime
forall a. a -> Maybe a
Just ZonedTime
t
        in (ZonedTime -> (Char, [Char]) -> Maybe ZonedTime)
-> Maybe ZonedTime -> [(Char, [Char])] -> Maybe ZonedTime
forall (m :: * -> *) a b.
Monad m =>
(a -> b -> m a) -> m a -> [b] -> m a
mfoldl ZonedTime -> (Char, [Char]) -> Maybe ZonedTime
f (LocalTime -> TimeZone -> ZonedTime
ZonedTime (LocalTime -> TimeZone -> ZonedTime)
-> Maybe LocalTime -> Maybe (TimeZone -> ZonedTime)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (TimeLocale -> [(Char, [Char])] -> Maybe LocalTime
forall t. ParseTime t => TimeLocale -> [(Char, [Char])] -> Maybe t
buildTime TimeLocale
l [(Char, [Char])]
xs) Maybe (TimeZone -> ZonedTime) -> Maybe TimeZone -> Maybe ZonedTime
forall a b. Maybe (a -> b) -> Maybe a -> Maybe b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (TimeLocale -> [(Char, [Char])] -> Maybe TimeZone
forall t. ParseTime t => TimeLocale -> [(Char, [Char])] -> Maybe t
buildTime TimeLocale
l [(Char, [Char])]
xs)) [(Char, [Char])]
xs

instance ParseTime UTCTime where
    substituteTimeSpecifier :: Proxy UTCTime -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy UTCTime
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy UTCTime
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy UTCTime
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe UTCTime
buildTime TimeLocale
l [(Char, [Char])]
xs = ZonedTime -> UTCTime
zonedTimeToUTC (ZonedTime -> UTCTime) -> Maybe ZonedTime -> Maybe UTCTime
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> TimeLocale -> [(Char, [Char])] -> Maybe ZonedTime
forall t. ParseTime t => TimeLocale -> [(Char, [Char])] -> Maybe t
buildTime TimeLocale
l [(Char, [Char])]
xs

instance ParseTime UniversalTime where
    substituteTimeSpecifier :: Proxy UniversalTime -> TimeLocale -> Char -> Maybe [Char]
substituteTimeSpecifier Proxy UniversalTime
_ = TimeLocale -> Char -> Maybe [Char]
timeSubstituteTimeSpecifier
    parseTimeSpecifier :: Proxy UniversalTime
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy UniversalTime
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
timeParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe UniversalTime
buildTime TimeLocale
l [(Char, [Char])]
xs = Rational -> LocalTime -> UniversalTime
localTimeToUT1 Rational
0 (LocalTime -> UniversalTime)
-> Maybe LocalTime -> Maybe UniversalTime
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> TimeLocale -> [(Char, [Char])] -> Maybe LocalTime
forall t. ParseTime t => TimeLocale -> [(Char, [Char])] -> Maybe t
buildTime TimeLocale
l [(Char, [Char])]
xs

buildTimeMonths :: [(Char, String)] -> Maybe Integer
buildTimeMonths :: [(Char, [Char])] -> Maybe Integer
buildTimeMonths [(Char, [Char])]
xs = do
    tt <-
        [(Char, [Char])]
-> ((Char, [Char]) -> Maybe Integer) -> Maybe [Integer]
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
t a -> (a -> f b) -> f (t b)
for [(Char, [Char])]
xs (((Char, [Char]) -> Maybe Integer) -> Maybe [Integer])
-> ((Char, [Char]) -> Maybe Integer) -> Maybe [Integer]
forall a b. (a -> b) -> a -> b
$ \(Char
c, [Char]
s) ->
            case Char
c of
                Char
'y' -> (Integer -> Integer) -> Maybe Integer -> Maybe Integer
forall a b. (a -> b) -> Maybe a -> Maybe b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
(*) Integer
12) (Maybe Integer -> Maybe Integer) -> Maybe Integer -> Maybe Integer
forall a b. (a -> b) -> a -> b
$ [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
                Char
'b' -> [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
                Char
'B' -> [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
                Char
_ -> Integer -> Maybe Integer
forall a. a -> Maybe a
forall (m :: * -> *) a. Monad m => a -> m a
return Integer
0
    return $ sum tt

buildTimeDays :: [(Char, String)] -> Maybe Integer
buildTimeDays :: [(Char, [Char])] -> Maybe Integer
buildTimeDays [(Char, [Char])]
xs = do
    tt <-
        [(Char, [Char])]
-> ((Char, [Char]) -> Maybe Integer) -> Maybe [Integer]
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
t a -> (a -> f b) -> f (t b)
for [(Char, [Char])]
xs (((Char, [Char]) -> Maybe Integer) -> Maybe [Integer])
-> ((Char, [Char]) -> Maybe Integer) -> Maybe [Integer]
forall a b. (a -> b) -> a -> b
$ \(Char
c, [Char]
s) ->
            case Char
c of
                Char
'w' -> (Integer -> Integer) -> Maybe Integer -> Maybe Integer
forall a b. (a -> b) -> Maybe a -> Maybe b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
(*) Integer
7) (Maybe Integer -> Maybe Integer) -> Maybe Integer -> Maybe Integer
forall a b. (a -> b) -> a -> b
$ [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
                Char
'd' -> [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
                Char
'D' -> [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
                Char
_ -> Integer -> Maybe Integer
forall a. a -> Maybe a
forall (m :: * -> *) a. Monad m => a -> m a
return Integer
0
    return $ sum tt

buildTimeSeconds :: [(Char, String)] -> Maybe Pico
buildTimeSeconds :: [(Char, [Char])] -> Maybe Pico
buildTimeSeconds [(Char, [Char])]
xs = do
    tt <- [(Char, [Char])] -> ((Char, [Char]) -> Maybe Pico) -> Maybe [Pico]
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
t a -> (a -> f b) -> f (t b)
for [(Char, [Char])]
xs (((Char, [Char]) -> Maybe Pico) -> Maybe [Pico])
-> ((Char, [Char]) -> Maybe Pico) -> Maybe [Pico]
forall a b. (a -> b) -> a -> b
$ \(Char
c, [Char]
s) -> let
        readInt :: Integer -> Maybe Pico
        readInt :: Integer -> Maybe Pico
readInt Integer
t = do
            i <- [Char] -> Maybe Integer
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
            return $ fromInteger $ i * t
        in case Char
c of
            Char
'h' -> Integer -> Maybe Pico
readInt Integer
3600
            Char
'H' -> Integer -> Maybe Pico
readInt Integer
3600
            Char
'm' -> Integer -> Maybe Pico
readInt Integer
60
            Char
'M' -> Integer -> Maybe Pico
readInt Integer
60
            Char
's' -> [Char] -> Maybe Pico
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
            Char
'S' -> [Char] -> Maybe Pico
forall a. Read a => [Char] -> Maybe a
readMaybe [Char]
s
            Char
_ -> Pico -> Maybe Pico
forall a. a -> Maybe a
forall (m :: * -> *) a. Monad m => a -> m a
return Pico
0
    return $ sum tt

instance ParseTime NominalDiffTime where
    parseTimeSpecifier :: Proxy POSIXTime
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy POSIXTime
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
durationParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe POSIXTime
buildTime TimeLocale
_ [(Char, [Char])]
xs = do
        dd <- [(Char, [Char])] -> Maybe Integer
buildTimeDays [(Char, [Char])]
xs
        tt <- buildTimeSeconds xs
        return $ (fromInteger dd * 86400) + realToFrac tt

instance ParseTime DiffTime where
    parseTimeSpecifier :: Proxy DiffTime
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy DiffTime
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
durationParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe DiffTime
buildTime TimeLocale
_ [(Char, [Char])]
xs = do
        dd <- [(Char, [Char])] -> Maybe Integer
buildTimeDays [(Char, [Char])]
xs
        tt <- buildTimeSeconds xs
        return $ (fromInteger dd * 86400) + realToFrac tt

instance ParseTime CalendarDiffDays where
    parseTimeSpecifier :: Proxy CalendarDiffDays
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy CalendarDiffDays
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
durationParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe CalendarDiffDays
buildTime TimeLocale
_ [(Char, [Char])]
xs = do
        mm <- [(Char, [Char])] -> Maybe Integer
buildTimeMonths [(Char, [Char])]
xs
        dd <- buildTimeDays xs
        return $ CalendarDiffDays mm dd

instance ParseTime CalendarDiffTime where
    parseTimeSpecifier :: Proxy CalendarDiffTime
-> TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
parseTimeSpecifier Proxy CalendarDiffTime
_ = TimeLocale -> Maybe ParseNumericPadding -> Char -> ReadP [Char]
durationParseTimeSpecifier
    buildTime :: TimeLocale -> [(Char, [Char])] -> Maybe CalendarDiffTime
buildTime TimeLocale
locale [(Char, [Char])]
xs = do
        mm <- [(Char, [Char])] -> Maybe Integer
buildTimeMonths [(Char, [Char])]
xs
        tt <- buildTime locale xs
        return $ CalendarDiffTime mm tt