Epoch in Haskell
A common requirement in programs is getting the number of seconds, milliseconds, or nanoseconds since the Unix epoch. Here’s how to do it in Haskell.
import Data.Time.Clock.POSIX (getPOSIXTime, POSIXTime)
import Data.Time.Clock (UTCTime, getCurrentTime)
import Data.Time.Format (formatTime, defaultTimeLocale)
main :: IO ()
main = do
now <- getCurrentTime
putStrLn $ formatTime defaultTimeLocale "%Y-%m-%d %H:%M:%S%Q %z" now
posixTime <- getPOSIXTime
let seconds = floor posixTime :: Integer
let milliseconds = floor (posixTime * 1000) :: Integer
let nanoseconds = floor (posixTime * 1000000000) :: Integer
print seconds
print milliseconds
print nanoseconds
let utcFromSeconds = posixSecondsToUTCTime $ fromIntegral seconds
let utcFromNanoseconds = posixSecondsToUTCTime $ fromIntegral nanoseconds / 1000000000
putStrLn $ formatTime defaultTimeLocale "%Y-%m-%d %H:%M:%S %z" utcFromSeconds
putStrLn $ formatTime defaultTimeLocale "%Y-%m-%d %H:%M:%S%Q %z" utcFromNanoseconds
posixSecondsToUTCTime :: POSIXTime -> UTCTime
posixSecondsToUTCTime = idIn Haskell, we use the Data.Time library to work with time-related functions. The getPOSIXTime function returns the current time as the number of seconds since the Unix epoch.
We use getCurrentTime to get the current time, and formatTime to format it as a string.
To get the elapsed time since the Unix epoch in seconds, milliseconds, or nanoseconds, we multiply the POSIX time by the appropriate factor and convert it to an integer.
You can also convert integer seconds or nanoseconds since the epoch into the corresponding UTCTime. In this example, we use posixSecondsToUTCTime to perform this conversion.
Here’s an example of what the output might look like:
$ runhaskell epoch.hs
2023-05-15 10:30:45.123456 +0000
1684146645
1684146645123
1684146645123456000
2023-05-15 10:30:45 +0000
2023-05-15 10:30:45.123456 +0000Next, we’ll look at another time-related task: time parsing and formatting.