chore: merge master
This commit is contained in:
commit
db790bf626
@ -4,6 +4,7 @@ RGCourseParticipants: Kursteilnehmer:innen
|
||||
RGCourseLecturers: Kursverwalter:innen
|
||||
RGCourseCorrectors: Korrektor:innen
|
||||
RGCourseTutors: Tutor:innen
|
||||
RGCourseParticipantsInTutorial: Kursteilnehmer:innen, die in mindestens einem Tutorium angemeldet sind
|
||||
RGCourseUnacceptedApplicants: Nicht akzeptierte Bewerber:innen
|
||||
RecipientToggleAll: Alle/Keine
|
||||
CommCourseTestSubject customSubject@Text !ident-ok: [TEST] #{customSubject}
|
||||
|
||||
@ -4,6 +4,7 @@ RGCourseParticipants: Course participants
|
||||
RGCourseLecturers: Course administrators
|
||||
RGCourseCorrectors: Course correctors
|
||||
RGCourseTutors: Course tutors
|
||||
RGCourseParticipantsInTutorial: Course participants who are registered for at least one tutorial
|
||||
RGCourseUnacceptedApplicants: Applicants not accepted
|
||||
RecipientToggleAll: All/None
|
||||
CommCourseTestSubject customSubject: [TEST] #{customSubject}
|
||||
|
||||
@ -17,7 +17,7 @@ User json -- Each Uni2work user has a corresponding row in this table; create
|
||||
lastAuthentication UTCTime Maybe -- last login date
|
||||
created UTCTime default=now()
|
||||
lastLdapSynchronisation UTCTime Maybe
|
||||
ldapPrimaryKey Text Maybe
|
||||
ldapPrimaryKey UserEduPersonPrincipalName Maybe
|
||||
tokensIssuedAfter UTCTime Maybe -- do not accept bearer tokens issued before this time (accept all tokens if null)
|
||||
matrikelnummer UserMatriculation Maybe -- optional immatriculation-string; usually a number, but not always (e.g. lecturers, pupils, guests,...)
|
||||
firstName Text -- For export in tables, pre-split firstName from displayName
|
||||
|
||||
@ -7,8 +7,6 @@ import Import
|
||||
import Handler.Utils
|
||||
import Handler.Utils.Communication
|
||||
|
||||
import qualified Data.Map as Map
|
||||
|
||||
import qualified Database.Esqueleto.Legacy as E
|
||||
|
||||
|
||||
@ -17,8 +15,8 @@ getCCommR = postCCommR
|
||||
postCCommR tid ssh csh = do
|
||||
(cid, tuts, exams, sheets) <- runDB $ do
|
||||
cid <- getKeyBy404 $ TermSchoolCourseShort tid ssh csh
|
||||
tuts' <- selectKeysList [TutorialCourse ==. cid] []
|
||||
tuts <- forM tuts' $ \tutid -> do
|
||||
tuts'' <- selectKeysList [TutorialCourse ==. cid] []
|
||||
tuts' <- forM tuts'' $ \tutid -> do
|
||||
cID <- encrypt tutid
|
||||
return ( RGTutorialParticipants cID
|
||||
, E.from $ \(user `E.InnerJoin` participant) -> do
|
||||
@ -26,6 +24,18 @@ postCCommR tid ssh csh = do
|
||||
E.where_ $ participant E.^. TutorialParticipantTutorial E.==. E.val tutid
|
||||
return user
|
||||
)
|
||||
let
|
||||
tuts | length tuts' < 2 = tuts'
|
||||
| otherwise = ( RGCourseParticipantsInTutorial
|
||||
, E.from $ \(user `E.InnerJoin` participant) -> do
|
||||
E.on $ user E.^. UserId E.==. participant E.^. CourseParticipantUser
|
||||
E.where_ $ participant E.^. CourseParticipantCourse E.==. E.val cid
|
||||
E.&&. participant E.^. CourseParticipantState E.==. E.val CourseParticipantActive
|
||||
E.&&. (E.exists . E.from $ \tutParticipant -> E.where_ $
|
||||
tutParticipant E.^. TutorialParticipantUser E.==. user E.^. UserId
|
||||
)
|
||||
return user
|
||||
) : tuts'
|
||||
|
||||
exams' <- selectKeysList [ExamCourse ==. cid] []
|
||||
exams <- forM exams' $ \examid -> do
|
||||
@ -55,7 +65,7 @@ postCCommR tid ssh csh = do
|
||||
, crUltDest = SomeRoute $ CourseR tid ssh csh CCommR
|
||||
, crJobs = crJobsCourseCommunication cid
|
||||
, crTestJobs = crTestJobsCourseCommunication cid
|
||||
, crRecipients = Map.fromList $
|
||||
, crRecipients =
|
||||
[ ( RGCourseParticipants
|
||||
, E.from $ \(user `E.InnerJoin` participant) -> do
|
||||
E.on $ user E.^. UserId E.==. participant E.^. CourseParticipantUser
|
||||
@ -69,14 +79,6 @@ postCCommR tid ssh csh = do
|
||||
E.where_ $ lecturer E.^. LecturerCourse E.==. E.val cid
|
||||
return user
|
||||
)
|
||||
, ( RGCourseCorrectors
|
||||
, E.from $ \user -> do
|
||||
E.where_ $ E.exists $ E.from $ \(sheet `E.InnerJoin` corrector) -> do
|
||||
E.on $ sheet E.^. SheetId E.==. corrector E.^. SheetCorrectorSheet
|
||||
E.where_ $ sheet E.^. SheetCourse E.==. E.val cid
|
||||
E.&&. user E.^. UserId E.==. corrector E.^. SheetCorrectorUser
|
||||
return user
|
||||
)
|
||||
, ( RGCourseTutors
|
||||
, E.from $ \user -> do
|
||||
E.where_ $ E.exists $ E.from $ \(tutorial `E.InnerJoin` tutor) -> do
|
||||
@ -85,7 +87,16 @@ postCCommR tid ssh csh = do
|
||||
E.&&. user E.^. UserId E.==. tutor E.^. TutorUser
|
||||
return user
|
||||
)
|
||||
, ( RGCourseUnacceptedApplicants
|
||||
, ( RGCourseCorrectors
|
||||
, E.from $ \user -> do
|
||||
E.where_ $ E.exists $ E.from $ \(sheet `E.InnerJoin` corrector) -> do
|
||||
E.on $ sheet E.^. SheetId E.==. corrector E.^. SheetCorrectorSheet
|
||||
E.where_ $ sheet E.^. SheetCourse E.==. E.val cid
|
||||
E.&&. user E.^. UserId E.==. corrector E.^. SheetCorrectorUser
|
||||
return user
|
||||
)
|
||||
] ++ tuts ++ exams ++ sheets ++
|
||||
[ ( RGCourseUnacceptedApplicants
|
||||
, E.from $ \user -> do
|
||||
E.where_ . E.exists . E.from $ \courseApplication ->
|
||||
E.where_ $ courseApplication E.^. CourseApplicationCourse E.==. E.val cid
|
||||
@ -96,7 +107,7 @@ postCCommR tid ssh csh = do
|
||||
E.&&. courseParticipant E.^. CourseParticipantState E.==. E.val CourseParticipantActive
|
||||
return user
|
||||
)
|
||||
] ++ tuts ++ exams ++ sheets
|
||||
]
|
||||
, crRecipientAuth = Just $ \uid -> do
|
||||
cID <- encrypt uid
|
||||
evalAccessDB (CourseR tid ssh csh $ CUserR cID) False
|
||||
|
||||
@ -255,10 +255,10 @@ makeCourseTable colChoices psValidator' = do
|
||||
E.||. (E.maybe (E.val mempty) (E.castString . esqueletoMarkupOutput) (course E.^. CourseDescription) `E.ilike` (E.%) E.++. E.val needle E.++. (E.%))
|
||||
, singletonMap "search-shorthand" . FilterColumn $ \(view queryCourse -> course) criterion -> case getLast (criterion :: Last Text) of
|
||||
Nothing -> E.val True :: E.SqlExpr (E.Value Bool)
|
||||
Just needle -> (E.castString (course E.^. CourseShorthand) `E.ilike` (E.%) E.++. E.val needle E.++. (E.%))
|
||||
Just needle -> E.castString (course E.^. CourseShorthand) `E.ilike` (E.%) E.++. E.val needle E.++. (E.%)
|
||||
, singletonMap "search-title" . FilterColumn $ \(view queryCourse -> course) criterion -> case getLast (criterion :: Last Text) of
|
||||
Nothing -> E.val True :: E.SqlExpr (E.Value Bool)
|
||||
Just needle -> (E.castString (course E.^. CourseName) `E.ilike` (E.%) E.++. E.val needle E.++. (E.%))
|
||||
Just needle -> E.castString (course E.^. CourseName) `E.ilike` (E.%) E.++. E.val needle E.++. (E.%)
|
||||
, singletonMap "allocation" . FilterColumn $ \row (criteria :: Set AllocationSearch) -> if
|
||||
| Set.null criteria -> E.true
|
||||
| otherwise -> flip E.any criteria $ \case
|
||||
|
||||
@ -176,6 +176,7 @@ data UserTableCsv = UserTableCsv
|
||||
, csvUserName :: UserDisplayName
|
||||
, csvUserSex :: Maybe Sex
|
||||
, csvUserMatriculation :: Maybe UserMatriculation
|
||||
, csvUserEPPN :: Maybe UserEduPersonPrincipalName
|
||||
, csvUserEmail :: UserEmail
|
||||
, csvUserStudyFeatures :: UserTableStudyFeatures
|
||||
, csvUserSubmissionGroup :: Maybe SubmissionGroupName
|
||||
@ -194,6 +195,7 @@ instance Csv.ToNamedRecord UserTableCsv where
|
||||
, "name" Csv..= csvUserName
|
||||
, "sex" Csv..= csvUserSex
|
||||
, "matriculation" Csv..= csvUserMatriculation
|
||||
, "eduPersonPrincipalName" Csv..= csvUserEPPN
|
||||
, "email" Csv..= csvUserEmail
|
||||
, "study-features" Csv..= csvUserStudyFeatures
|
||||
, "submission-group" Csv..= csvUserSubmissionGroup
|
||||
@ -239,7 +241,7 @@ userTableCsvHeader :: Bool -> [Entity Tutorial] -> [Entity Sheet] -> UserCsvExpo
|
||||
userTableCsvHeader showSex tuts sheets UserCsvExportData{..} = Csv.header $
|
||||
[ "surname", "first-name", "name" ] ++
|
||||
[ "sex" | showSex ] ++
|
||||
[ "matriculation", "email", "study-features"] ++
|
||||
[ "matriculation", "eduPersonPrincipalName", "email", "study-features"] ++
|
||||
[ "tutorial" | hasEmptyRegGroup ] ++
|
||||
map (encodeUtf8 . CI.foldedCase) regGroups ++
|
||||
[ "exams", "registration" ] ++
|
||||
@ -255,6 +257,7 @@ data UserTableJson = UserTableJson
|
||||
, jsonUserName :: UserDisplayName
|
||||
, jsonUserSex :: Maybe (Maybe Sex)
|
||||
, jsonUserMatriculation :: Maybe UserMatriculation
|
||||
, jsonUserEPPN :: Maybe UserEduPersonPrincipalName
|
||||
, jsonUserEmail :: UserEmail
|
||||
, jsonUserStudyFeatures :: UserTableStudyFeatures
|
||||
, jsonUserSubmissionGroup :: Maybe SubmissionGroupName
|
||||
@ -291,6 +294,7 @@ instance ToJSON UserTableJson where
|
||||
, pure $ "name" JSON..= jsonUserName
|
||||
, ("sex" JSON..=) <$> jsonUserSex
|
||||
, ("matriculation" JSON..=) <$> jsonUserMatriculation
|
||||
, ("eduPersonPrincipalName" JSON..=) <$> jsonUserEPPN
|
||||
, pure $ "email" JSON..= jsonUserEmail
|
||||
, ("study-features" JSON..=) <$> assertM' (views _Wrapped $ not . onull) jsonUserStudyFeatures
|
||||
, ("submission-group" JSON..=) <$> jsonUserSubmissionGroup
|
||||
@ -523,6 +527,7 @@ makeCourseUserTable cid acts restrict colChoices psValidator csvColumns = do
|
||||
<*> view (hasUser . _userDisplayName)
|
||||
<*> view (hasUser . _userSex)
|
||||
<*> view (hasUser . _userMatrikelnummer)
|
||||
<*> view (hasUser . _userLdapPrimaryKey)
|
||||
<*> view (hasUser . _userEmail)
|
||||
<*> view _userStudyFeatures
|
||||
<*> preview (_userSubmissionGroup . _entityVal . _submissionGroupName)
|
||||
@ -550,12 +555,13 @@ makeCourseUserTable cid acts restrict colChoices psValidator csvColumns = do
|
||||
repUserJson = C.foldMapM $ \(E.Value uid, res) -> Map.singleton <$> encrypt uid <*> mkUserTableJson res
|
||||
where
|
||||
mkUserTableJson res' = flip runReaderT res' $ UserTableJson
|
||||
<$> view (hasUser . _userSurname)
|
||||
<*> view (hasUser . _userFirstName)
|
||||
<*> view (hasUser . _userDisplayName)
|
||||
<$> view (hasUser . _userSurname)
|
||||
<*> view (hasUser . _userFirstName)
|
||||
<*> view (hasUser . _userDisplayName)
|
||||
<*> views (hasUser . _userSex) (guardOn showSex)
|
||||
<*> view (hasUser . _userMatrikelnummer)
|
||||
<*> view (hasUser . _userEmail)
|
||||
<*> view (hasUser . _userMatrikelnummer)
|
||||
<*> view (hasUser . _userLdapPrimaryKey)
|
||||
<*> view (hasUser . _userEmail)
|
||||
<*> view _userStudyFeatures
|
||||
<*> preview (_userSubmissionGroup . _entityVal . _submissionGroupName)
|
||||
<*> view _userTableRegistration
|
||||
|
||||
@ -183,6 +183,7 @@ data ExamUserTableCsv = ExamUserTableCsv
|
||||
, csvEUserFirstName :: Maybe Text
|
||||
, csvEUserName :: Maybe Text
|
||||
, csvEUserMatriculation :: Maybe Text
|
||||
, csvEUserEPPN :: Maybe UserEduPersonPrincipalName
|
||||
, csvEUserStudyFeatures :: UserTableStudyFeatures
|
||||
, csvEUserOccurrence :: Maybe (CI Text)
|
||||
, csvEUserExercisePoints :: Maybe (Maybe Points)
|
||||
@ -203,6 +204,7 @@ instance ToNamedRecord ExamUserTableCsv where
|
||||
, "first-name" Csv..= csvEUserFirstName
|
||||
, "name" Csv..= csvEUserName
|
||||
, "matriculation" Csv..= csvEUserMatriculation
|
||||
, "eduPersonPrincipalName" Csv..= csvEUserEPPN
|
||||
, "study-features" Csv..= csvEUserStudyFeatures
|
||||
, "occurrence" Csv..= csvEUserOccurrence
|
||||
] ++ catMaybes
|
||||
@ -228,6 +230,7 @@ instance FromNamedRecord ExamUserTableCsv where
|
||||
<*> csv .:?? "first-name"
|
||||
<*> csv .:?? "name"
|
||||
<*> csv .:?? "matriculation"
|
||||
<*> csv .:?? "eduPersonPrincipalName"
|
||||
<*> pure mempty
|
||||
<*> csv .:?? "occurrence"
|
||||
<*> fmap Just (csv .:?? "exercise-points")
|
||||
@ -270,7 +273,7 @@ examUserTableCsvHeader :: ( MonoFoldable mono
|
||||
=> SheetGradeSummary -> Bool -> mono -> Csv.Header
|
||||
examUserTableCsvHeader allBoni doBonus pNames = Csv.header $
|
||||
[ "surname", "first-name", "name"
|
||||
, "matriculation"
|
||||
, "matriculation", "eduPersonPrincipalName"
|
||||
, "study-features"
|
||||
, "course-note"
|
||||
, "occurrence"
|
||||
@ -608,6 +611,7 @@ postEUsersR tid ssh csh examn = do
|
||||
<*> view (resultUser . _entityVal . _userFirstName . to Just)
|
||||
<*> view (resultUser . _entityVal . _userDisplayName . to Just)
|
||||
<*> view (resultUser . _entityVal . _userMatrikelnummer)
|
||||
<*> view (resultUser . _entityVal . _userLdapPrimaryKey)
|
||||
<*> view resultStudyFeatures
|
||||
<*> preview (resultExamOccurrence . _entityVal . _examOccurrenceName)
|
||||
<*> fmap (bool (const Nothing) Just showPoints) (preview $ resultUser . _entityKey . to (examBonusAchieved ?? bonus) . _achievedPoints . _Wrapped)
|
||||
@ -933,6 +937,7 @@ postEUsersR tid ssh csh examn = do
|
||||
guessUser' ExamUserTableCsv{..} = do
|
||||
let criteria = PredDNF . maybe Set.empty Set.singleton . fromNullable . Set.fromList . fmap PLVariable $ catMaybes
|
||||
[ GuessUserMatrikelnummer <$> csvEUserMatriculation
|
||||
, GuessUserEduPersonPrincipalName <$> csvEUserEPPN
|
||||
, GuessUserDisplayName <$> csvEUserName
|
||||
, GuessUserSurname <$> csvEUserSurname
|
||||
, GuessUserFirstName <$> csvEUserFirstName
|
||||
|
||||
@ -10,8 +10,6 @@ import Handler.Utils.Communication
|
||||
import qualified Database.Esqueleto.Legacy as E
|
||||
import qualified Database.Esqueleto.Utils as E
|
||||
|
||||
import qualified Data.Map as Map
|
||||
|
||||
|
||||
getTCommR, postTCommR :: TermId -> SchoolId -> CourseShorthand -> TutorialName -> Handler Html
|
||||
getTCommR = postTCommR
|
||||
@ -36,21 +34,13 @@ postTCommR tid ssh csh tutn = do
|
||||
, crUltDest = SomeRoute $ CTutorialR tid ssh csh tutn TCommR
|
||||
, crJobs = crJobsCourseCommunication cid
|
||||
, crTestJobs = crTestJobsCourseCommunication cid
|
||||
, crRecipients = Map.fromList $
|
||||
, crRecipients =
|
||||
[ ( RGCourseLecturers
|
||||
, E.from $ \(user `E.InnerJoin` lecturer) -> do
|
||||
E.on $ user E.^. UserId E.==. lecturer E.^. LecturerUser
|
||||
E.where_ $ lecturer E.^. LecturerCourse E.==. E.val cid
|
||||
return user
|
||||
)
|
||||
, ( RGCourseCorrectors
|
||||
, E.from $ \user -> do
|
||||
E.where_ $ E.exists $ E.from $ \(sheet `E.InnerJoin` corrector) -> do
|
||||
E.on $ sheet E.^. SheetId E.==. corrector E.^. SheetCorrectorSheet
|
||||
E.where_ $ sheet E.^. SheetCourse E.==. E.val cid
|
||||
E.&&. corrector E.^. SheetCorrectorUser E.==. user E.^. UserId
|
||||
return user
|
||||
)
|
||||
, ( RGCourseTutors
|
||||
, E.from $ \user -> do
|
||||
E.where_ $ E.exists $ E.from $ \(tutorial `E.InnerJoin` tutor) -> do
|
||||
@ -59,6 +49,14 @@ postTCommR tid ssh csh tutn = do
|
||||
E.&&. tutor E.^. TutorUser E.==. user E.^. UserId
|
||||
return user
|
||||
)
|
||||
, ( RGCourseCorrectors
|
||||
, E.from $ \user -> do
|
||||
E.where_ $ E.exists $ E.from $ \(sheet `E.InnerJoin` corrector) -> do
|
||||
E.on $ sheet E.^. SheetId E.==. corrector E.^. SheetCorrectorSheet
|
||||
E.where_ $ sheet E.^. SheetCourse E.==. E.val cid
|
||||
E.&&. corrector E.^. SheetCorrectorUser E.==. user E.^. UserId
|
||||
return user
|
||||
)
|
||||
] ++ usertuts
|
||||
, crRecipientAuth = Just $ \uid -> do
|
||||
isTutorialUser <- E.selectExists . E.from $ \tutorialUser ->
|
||||
|
||||
@ -22,7 +22,7 @@ import qualified Data.Set as Set
|
||||
import qualified Data.Conduit.Combinators as C
|
||||
|
||||
|
||||
data RecipientGroup = RGCourseParticipants | RGCourseLecturers | RGCourseCorrectors | RGCourseTutors | RGCourseUnacceptedApplicants
|
||||
data RecipientGroup = RGCourseParticipants | RGCourseLecturers | RGCourseCorrectors | RGCourseTutors | RGCourseParticipantsInTutorial | RGCourseUnacceptedApplicants
|
||||
| RGTutorialParticipants CryptoUUIDTutorial
|
||||
| RGExamRegistered CryptoUUIDExam
|
||||
| RGSheetSubmittor CryptoUUIDSheet
|
||||
@ -69,7 +69,7 @@ instance Button UniWorX CommunicationButton where
|
||||
|
||||
|
||||
data CommunicationRoute = CommunicationRoute
|
||||
{ crRecipients :: Map RecipientGroup (E.SqlQuery (E.SqlExpr (Entity User)))
|
||||
{ crRecipients :: [(RecipientGroup, E.SqlQuery (E.SqlExpr (Entity User)))]
|
||||
, crRecipientAuth :: Maybe (UserId -> DB AuthResult) -- ^ Only resolve userids given as GET-Parameter if they fulfil this criterion
|
||||
, crJobs, crTestJobs :: Communication -> ConduitT () Job (YesodDB UniWorX) ()
|
||||
, crHeading :: SomeMessage UniWorX
|
||||
@ -111,7 +111,8 @@ commR CommunicationRoute{..} = do
|
||||
mbCurrentRoute <- getCurrentRoute
|
||||
|
||||
(suggestedRecipients, chosenRecipients) <- runDB $ do
|
||||
suggested <- for crRecipients $ \user -> E.select user
|
||||
suggestedUsers <- for crRecipients $ \(_,user) -> E.select user
|
||||
let suggested = zip (view _1 <$> crRecipients) suggestedUsers
|
||||
|
||||
let
|
||||
decrypt' :: CryptoUUIDUser -> DB (Maybe (Entity User))
|
||||
@ -127,21 +128,21 @@ commR CommunicationRoute{..} = do
|
||||
let
|
||||
lookupUser :: UserId -> User
|
||||
lookupUser lId
|
||||
= entityVal . unsafeHead . filter ((== lId) . entityKey) $ concat (Map.elems suggestedRecipients) ++ chosenRecipients
|
||||
= entityVal . unsafeHead . filter ((== lId) . entityKey) $ concat (view _2 <$> suggestedRecipients) ++ chosenRecipients
|
||||
|
||||
let chosenRecipients' = Map.fromList $
|
||||
[ ( (BoundedPosition $ RecipientGroup g, pos)
|
||||
, (Right recp, recp `elem` map entityKey chosenRecipients)
|
||||
)
|
||||
| (g, recps) <- Map.toList suggestedRecipients
|
||||
| (g, recps) <- suggestedRecipients
|
||||
, (pos, recp) <- zip [0..] $ map entityKey recps
|
||||
] ++
|
||||
[ ( (BoundedPosition RecipientCustom, pos)
|
||||
, (Right recp, True)
|
||||
)
|
||||
| (pos, recp) <- zip [0..] . Set.toList $ Set.fromList (map entityKey chosenRecipients) \\ Set.fromList (concatMap (map entityKey) $ Map.elems suggestedRecipients)
|
||||
| (pos, recp) <- zip [0..] . Set.toList $ Set.fromList (map entityKey chosenRecipients) \\ Set.fromList (concatMap (map entityKey) $ view _2 <$> suggestedRecipients)
|
||||
]
|
||||
activeCategories = map RecipientGroup (Map.keys suggestedRecipients) `snoc` RecipientCustom
|
||||
activeCategories = map RecipientGroup (view _1 <$> suggestedRecipients) `snoc` RecipientCustom
|
||||
|
||||
let recipientAForm :: AForm Handler (Set (Either UserEmail UserId))
|
||||
recipientAForm = postProcess <$> massInputA MassInput{..} (fslI MsgCommRecipients & setTooltip MsgCommRecipientsTip) True (Just chosenRecipients')
|
||||
|
||||
@ -45,10 +45,16 @@ computeUserAuthenticationDigest = hashlazy . JSON.encode
|
||||
|
||||
|
||||
data GuessUserInfo
|
||||
= GuessUserMatrikelnummer { guessUserMatrikelnummer :: UserMatriculation }
|
||||
| GuessUserDisplayName { guessUserDisplayName :: UserDisplayName }
|
||||
| GuessUserSurname { guessUserSurname :: UserSurname }
|
||||
| GuessUserFirstName { guessUserFirstName :: UserFirstName }
|
||||
= GuessUserMatrikelnummer
|
||||
{ guessUserMatrikelnummer :: UserMatriculation }
|
||||
| GuessUserEduPersonPrincipalName
|
||||
{ guessUserEduPersonPrincipalName :: UserEduPersonPrincipalName }
|
||||
| GuessUserDisplayName
|
||||
{ guessUserDisplayName :: UserDisplayName }
|
||||
| GuessUserSurname
|
||||
{ guessUserSurname :: UserSurname }
|
||||
| GuessUserFirstName
|
||||
{ guessUserFirstName :: UserFirstName }
|
||||
deriving (Eq, Ord, Read, Show, Generic, Typeable)
|
||||
instance Binary GuessUserInfo
|
||||
|
||||
@ -93,10 +99,11 @@ guessUser (((Set.toList . toNullable) <$>) . Set.toList . dnfTerms -> criteria)
|
||||
containsAsSet x y = E.and . map (\y' -> x `E.hasInfix` E.val y') $ asWords y
|
||||
|
||||
toSql user pl = bool id E.not_ (is _PLNegated pl) $ case pl ^. _plVar of
|
||||
GuessUserMatrikelnummer userMatriculation' -> user E.^. UserMatrikelnummer E.==. E.val (Just userMatriculation')
|
||||
GuessUserDisplayName userDisplayName' -> user E.^. UserDisplayName `containsAsSet` userDisplayName'
|
||||
GuessUserSurname userSurname' -> user E.^. UserSurname `containsAsSet` userSurname'
|
||||
GuessUserFirstName userFirstName' -> user E.^. UserFirstName `containsAsSet` userFirstName'
|
||||
GuessUserMatrikelnummer userMatriculation' -> user E.^. UserMatrikelnummer E.==. E.val (Just userMatriculation')
|
||||
GuessUserEduPersonPrincipalName userEPPN' -> user E.^. UserLdapPrimaryKey E.==. E.val (Just userEPPN')
|
||||
GuessUserDisplayName userDisplayName' -> user E.^. UserDisplayName `containsAsSet` userDisplayName'
|
||||
GuessUserSurname userSurname' -> user E.^. UserSurname `containsAsSet` userSurname'
|
||||
GuessUserFirstName userFirstName' -> user E.^. UserFirstName `containsAsSet` userFirstName'
|
||||
|
||||
go didLdap = do
|
||||
let retrieveUsers = E.select . E.from $ \user -> do
|
||||
|
||||
@ -13,49 +13,53 @@ import Import.NoModel
|
||||
import qualified Yesod.Auth.Util.PasswordStore as PWStore
|
||||
|
||||
|
||||
type Count = Sum Integer
|
||||
type Points = Centi
|
||||
type Count = Sum Integer
|
||||
type Points = Centi
|
||||
|
||||
type Email = Text
|
||||
type Email = Text
|
||||
|
||||
type UserTitle = Text
|
||||
type UserFirstName = Text
|
||||
type UserSurname = Text
|
||||
type UserDisplayName = Text
|
||||
type UserMatriculation = Text
|
||||
type UserTitle = Text
|
||||
type UserFirstName = Text
|
||||
type UserSurname = Text
|
||||
type UserDisplayName = Text
|
||||
type UserIdent = CI Text
|
||||
type UserMatriculation = Text
|
||||
type UserEmail = CI Email
|
||||
|
||||
type StudyDegreeName = Text
|
||||
type StudyDegreeShorthand = Text
|
||||
type StudyDegreeKey = Int
|
||||
type StudyTermsName = Text
|
||||
type StudyTermsShorthand = Text
|
||||
type StudyTermsKey = Int
|
||||
type StudySubTermsKey = Int
|
||||
type StudyDegreeName = Text
|
||||
type StudyDegreeShorthand = Text
|
||||
type StudyDegreeKey = Int
|
||||
type StudyTermsName = Text
|
||||
type StudyTermsShorthand = Text
|
||||
type StudyTermsKey = Int
|
||||
type StudySubTermsKey = Int
|
||||
|
||||
type SchoolName = CI Text
|
||||
type SchoolShorthand = CI Text
|
||||
type CourseName = CI Text
|
||||
type CourseShorthand = CI Text
|
||||
type SheetName = CI Text
|
||||
type MaterialName = CI Text
|
||||
type UserEmail = CI Email
|
||||
type UserIdent = CI Text
|
||||
type TutorialName = CI Text
|
||||
type ExamName = CI Text
|
||||
type ExamPartName = CI Text
|
||||
type ExamOccurrenceName = CI Text
|
||||
type AllocationName = CI Text
|
||||
type AllocationShorthand = CI Text
|
||||
type SchoolName = CI Text
|
||||
type SchoolShorthand = CI Text
|
||||
|
||||
type SubmissionGroupName = CI Text
|
||||
type CourseName = CI Text
|
||||
type CourseShorthand = CI Text
|
||||
type MaterialName = CI Text
|
||||
type TutorialName = CI Text
|
||||
type SheetName = CI Text
|
||||
type SubmissionGroupName = CI Text
|
||||
|
||||
type PWHashAlgorithm = ByteString -> PWStore.Salt -> Int -> ByteString
|
||||
type InstanceId = UUID
|
||||
type ClusterId = UUID
|
||||
type TokenId = UUID
|
||||
type TermCandidateIncidence = UUID
|
||||
type ExamName = CI Text
|
||||
type ExamPartName = CI Text
|
||||
type ExamOccurrenceName = CI Text
|
||||
|
||||
type SessionFileReference = Digest SHA3_256
|
||||
type AllocationName = CI Text
|
||||
type AllocationShorthand = CI Text
|
||||
|
||||
type PWHashAlgorithm = ByteString -> PWStore.Salt -> Int -> ByteString
|
||||
|
||||
type InstanceId = UUID
|
||||
type ClusterId = UUID
|
||||
type TokenId = UUID
|
||||
|
||||
type TermCandidateIncidence = UUID
|
||||
|
||||
type SessionFileReference = Digest SHA3_256
|
||||
|
||||
type WorkflowDefinitionName = CI Text
|
||||
type WorkflowInstanceName = CI Text
|
||||
|
||||
@ -4,6 +4,9 @@ import Import.NoModel
|
||||
import Model.Types.TH.PathPiece
|
||||
|
||||
|
||||
type UserEduPersonPrincipalName = Text
|
||||
|
||||
|
||||
data SystemFunction
|
||||
= SystemExamOffice
|
||||
| SystemFaculty
|
||||
|
||||
@ -16,14 +16,16 @@ $if not (null activeCategories)
|
||||
_{MsgRGCourseCorrectors}
|
||||
$of RecipientGroup RGCourseTutors
|
||||
_{MsgRGCourseTutors}
|
||||
$of RecipientGroup RGCourseParticipantsInTutorial
|
||||
_{MsgRGCourseParticipantsInTutorial}
|
||||
$of RecipientGroup (RGTutorialParticipants tutid)
|
||||
^{rgTutorialParticipantsCaption tutid}
|
||||
$of RecipientGroup RGCourseUnacceptedApplicants
|
||||
_{MsgRGCourseUnacceptedApplicants}
|
||||
$of RecipientGroup (RGExamRegistered eid)
|
||||
^{rgExamRegisteredCaption eid}
|
||||
$of RecipientGroup (RGSheetSubmittor sid)
|
||||
^{rgSheetSubmittorCaption sid}
|
||||
$of RecipientGroup RGCourseUnacceptedApplicants
|
||||
_{MsgRGCourseUnacceptedApplicants}
|
||||
|
||||
$if hasContent category
|
||||
<fieldset .recipient-category__fieldset uw-interactive-fieldset .interactive-fieldset__target data-conditional-input=#{checkedIdent category}>
|
||||
|
||||
Reference in New Issue
Block a user