Y35QCWYW2OTZ27ZVTH2BA3XJTUCJ2WMLKU32ZCOCDY3AW7TIZXRAC
2KZPOGRBY6KBMO76F55ZKIVOLSG3O63VP3RHRZVANXYT3OLZ3OWQC
4QX5E5ACVN57KJLCWOM4JEI6JSV4XZNCWVYPOTKSOMUW3SOMCNJAC
EQXRXRZDYCM7BDAVBOXQYPG6C7IJT3OFGNIXCDAHJJBRKAXNGL7AC
ADMKQQGCGVSHHIMVQ4XFRDCG544SBJCYALSKZV45CQQBZ4ACUH2AC
NVOCQVASZWTKQJG7GPH7KHKZZR7NUG4WLV5YY4KAIRPCJRWCZPIAC
7DBNV3GV773FH5ZLQWFX4RBOS4Q3CIK2RYZNNABY3ZOETYZCXRNQC
N4NDAZYTLSI2W22KT3SYXL257DBMSH3UT2BXOYM7LH7FSZAY4RLAC
JUUMYIQEXSYRMPCQSHIRIG6TBHAR5LU46FE5WI3UHYX6KA4ESH7AC
instance FromField LogEvent where
fromField f m = let fromText "start_work" = return StartWork
fromText "stop_work" = return StopWork
fromText a = conversionError $ LogEventParseError $ "unrecognized log event type " ++ a
in fromField f m >>= fromText
-- instance FromField WorkEvent where
-- fromField f m = let fromText "start_work" = return StartWork
-- fromText "stop_work" = return StopWork
-- fromText a = conversionError $ LogEventParseError $ "unrecognized log event type " ++ a
-- in fromField f m >>= fromText
payouts dep ptime widx = let addIntervalDiff :: (Functor f, Foldable f) => NDT -> f LogInterval -> (NDT, NDT)
addIntervalDiff total ivals = (\dt -> (dt + total, dt)) $ sumLogIntervals dep ptime ivals
(totalTime, keyTimes) = M.mapAccum addIntervalDiff (fromInteger 0) $ M.map snd widx
in M.map (\kt -> toRational $ kt / totalTime) keyTimes
payouts dep ptime widx =
let addIntervalDiff :: (Functor f, Foldable f) => NDT -> f Interval -> (NDT, NDT)
addIntervalDiff total ivals = (\dt -> (dt + total, dt)) $ workCredit dep ptime ivals
(totalTime, keyTimes) = M.mapAccum addIntervalDiff (fromInteger 0) $ M.map snd widx
in M.map (\kt -> toRational $ kt / totalTime) keyTimes
sumLogIntervals :: (Functor f, Foldable f) => Depreciation -> UTCTime -> f LogInterval -> NDT
sumLogIntervals dep ptime ivals = F.foldl' (+) (fromInteger 0) $ fmap (depreciateInterval dep ptime) ivals
workCredit :: (Functor f, Foldable f) => Depreciation -> UTCTime -> f Interval -> NDT
workCredit dep ptime ivals = F.foldl' (+) (fromInteger 0) $ fmap (depreciateInterval dep ptime) ivals
depreciateInterval :: Depreciation -> UTCTime -> LogInterval -> NDT
depreciateInterval dep ptime ival = let depreciation :: Rational
depreciation = depf dep $ diffUTCTime ptime (end . workInterval $ ival)
in fromRational $ depreciation * (toRational . ilen . workInterval $ ival)
{-|
Compute the depreciated difftime for a single Interval value.
-}
depreciateInterval :: Depreciation -> UTCTime -> Interval -> NDT
depreciateInterval dep ptime ival =
let depreciation :: Rational
depreciation = depf dep $ diffUTCTime ptime (end $ ival)
in fromRational $ depreciation * (toRational . ilen $ ival)
appendLogEntry :: WorkIndex -> LogEntry -> WorkIndex
appendLogEntry workIndex entry = let acc = reduceToIntervals $ pushEntry entry workIndex
in insert (btcAddr entry) acc workIndex
type RawIndex = Map BtcAddr ([LogEntry], [LogInterval])
pushEntry :: LogEntry -> WorkIndex -> ([LogEntry], [LogInterval])
appendLogEntry :: RawIndex -> LogEntry -> RawIndex
appendLogEntry workIndex entry =
let acc = reduceToIntervals $ pushEntry entry workIndex
in insert (btcAddr entry) acc workIndex
pushEntry :: LogEntry -> RawIndex -> ([LogEntry], [LogInterval])
reduceToIntervals ((LogEntry addr end StopWork) : (LogEntry _ start StartWork) : xs, intervals) = (xs, (LogInterval addr (interval start end)) : intervals)
reduceToIntervals ((LogEntry addr (StopWork end)) : (LogEntry _ (StartWork start)) : xs, intervals) =
(xs, (LogInterval addr (interval start end)) : intervals)