module Rakka.Utils ( yesOrNo , parseYesOrNo , maybeA , deleteIfEmpty , formatW3CDateTime , chomp ) where import Control.Arrow import Control.Arrow.ArrowList import Data.Time import Text.Printf yesOrNo :: Bool -> String yesOrNo True = "yes" yesOrNo False = "no" parseYesOrNo :: ArrowChoice a => a String Bool parseYesOrNo = proc str -> do case str of "yes" -> returnA -< True "no" -> returnA -< False _ -> returnA -< error ("Expected yes or no: " ++ str) maybeA :: (ArrowList a, ArrowChoice a) => a b c -> a b (Maybe c) maybeA a = listA a >>> proc xs -> case xs of [] -> returnA -< Nothing (x:_) -> returnA -< Just x deleteIfEmpty :: (ArrowList a, ArrowChoice a) => a String String deleteIfEmpty = proc str -> do case str of "" -> none -< () _ -> returnA -< str formatW3CDateTime :: ZonedTime -> String formatW3CDateTime zonedTime = formatLocalTime (zonedTimeToLocalTime zonedTime) ++ formatTimeZone (zonedTimeZone zonedTime) where formatLocalTime :: LocalTime -> String formatLocalTime localTime = let (year, month, day) = toGregorian (localDay localTime) timeOfDay = localTimeOfDay localTime (secInt, secFrac) = properFraction (todSec timeOfDay) in (printf "%04d-%02d-%02dT%02d:%02d:%02d" year month day (todHour timeOfDay) (todMin timeOfDay) (secInt :: Int)) ++ (if secFrac == 0 then "" else tail (show secFrac)) formatTimeZone :: TimeZone -> String formatTimeZone tz = case timeZoneMinutes tz of offset | offset < 0 -> '-':(showTZ $ negate offset) | offset == 0 -> "Z" | otherwise -> '+':(showTZ offset) showTZ :: Int -> String showTZ offset = let hour = offset `div` 60 minute = offset - hour * 60 in show2 hour ++ ":" ++ show2 minute show2 :: Int -> String show2 n | n < 10 = '0':(show n) | otherwise = show n chomp :: String -> String chomp = reverse . snd . break (/= '\n') . reverse