52 lines
2.0 KiB
Haskell
52 lines
2.0 KiB
Haskell
-- SPDX-FileCopyrightText: 2022 Sarah Vaupel <vaupel.sarah@campus.lmu.de>
|
|
--
|
|
-- SPDX-License-Identifier: AGPL-3.0-or-later
|
|
|
|
module Handler.Utils.Corrections where
|
|
|
|
import Import
|
|
|
|
|
|
-- CorrectionInfo has seeming redundancies, but these are useful for aggregation
|
|
-- INVARIANT: isJust ciTot `implies` ciCorrected > 0
|
|
data CorrectionInfo = CorrectionInfo
|
|
{ ciSubmittors, ciSubmissions, ciAssigned, ciCorrected :: Integer
|
|
, ciCorrector :: Maybe UserId
|
|
, ciTot, ciMin, ciMax :: Maybe NominalDiffTime
|
|
}
|
|
|
|
instance Semigroup CorrectionInfo where
|
|
corrA <> corrB =
|
|
assert (isJust (ciTot corrA) `implies` (ciCorrected corrA > 0)) $
|
|
assert (isJust (ciTot corrB) `implies` (ciCorrected corrB > 0))
|
|
CorrectionInfo
|
|
{ ciSubmittors = ciSubmittors `mergeWith` (+)
|
|
, ciSubmissions = ciSubmissions `mergeWith` (+)
|
|
, ciAssigned = ciAssigned `mergeWith` (+)
|
|
, ciCorrected = ciCorrected `mergeWith` (+)
|
|
, ciCorrector = ciCorrector `mergeWith` keepEqual
|
|
, ciTot = ciTot `mergeWith` ignoreNothing (+)
|
|
, ciMin = ciMin `mergeWith` ignoreNothing min
|
|
, ciMax = ciMax `mergeWith` ignoreNothing max
|
|
}
|
|
where
|
|
mergeWith :: (CorrectionInfo -> a) -> (a -> a -> c) -> c
|
|
mergeWith prj f = on f prj corrA corrB
|
|
|
|
keepEqual (Just x) (Just y) | x==y = Just x
|
|
keepEqual Nothing other = other
|
|
keepEqual other Nothing = other
|
|
keepEqual _ _ = Nothing
|
|
|
|
instance Monoid CorrectionInfo where
|
|
mappend = (<>)
|
|
mempty = CorrectionInfo { ciSubmittors = 0
|
|
, ciSubmissions = 0
|
|
, ciAssigned = 0
|
|
, ciCorrected = 0
|
|
, ciCorrector = Nothing
|
|
, ciMin = Nothing
|
|
, ciTot = Nothing
|
|
, ciMax = Nothing
|
|
}
|