backend/src/main/java/ch/fhnw/speech_collection_app/features/base/user_group/UserGroupService.java
public CheckWrapper checkNext(long groupId) {
        checkAllowed(groupId);
        var loggedInUserId = customUserDetailsService.getLoggedInUserId();
        Long achievementId = achievementsService.getDayCheckAchievement(new Timestamp(new Date().getTime()));
        var userAchievements = achievementsService.getUserAchievement(loggedInUserId, achievementId);
        var res = dslContext.select(DATA_TUPLE.asterisk())
                .from(DATA_TUPLE.join(DATA_ELEMENT).onKey(DATA_TUPLE.DATA_ELEMENT_ID_1)
                        .join(TEXT).onKey(TEXT.DATA_ELEMENT_ID))
                .where(DSL.abs(DATA_TUPLE.WRONG.plus(DATA_TUPLE.CORRECT)).lessThan(speechCollectionAppConfig.getMinNumChecks())
                        .and(DATA_ELEMENT.USER_GROUP_ID.eq(groupId))
                        //.and(DATA_TUPLE.FINISHED.isFalse())
                        // user should only check once
                        .and(DATA_TUPLE.ID.notIn(dslContext.select(CHECKED_DATA_TUPLE.DATA_TUPLE_ID)
                                .from(CHECKED_DATA_TUPLE)
                                .where(CHECKED_DATA_TUPLE.USER_ID.eq(loggedInUserId)))))
                // user should not check self-generated data
                .except(dslContext.select(DATA_TUPLE.asterisk())
                        .from(DATA_TUPLE.join(DATA_ELEMENT).on(DATA_TUPLE.DATA_ELEMENT_ID_2.eq(DATA_ELEMENT.ID)))
                        .where(DATA_ELEMENT.USER_ID.eq(loggedInUserId)))
                .limit(speechCollectionAppConfig.getNumRandomSelect()).fetchInto(DataTuple.class);
        var dataTuple = res.isEmpty() ? null : res.get(ThreadLocalRandom.current().nextInt(res.size()));
        return new CheckWrapper(dataTuple, achievementsService.getAchievementWrapper(userAchievements));
    }
/**
     * returns the next occurrence to check based on the groupId and available data.<br>
     * occurrences are labeled until it is clear that they clearly wrong|correct.<br>
     */
returns the next occurrence to check based on the groupId and available data.
occurrences are labeled until it is clear that they clearly wrong|correct.
returns the next occurrence to check based on the groupId and available data . occurrences are labeled until it is clear that they clearly wrong|correct .
public CheckWrapper checkNext(long groupId) {
        checkAllowed(groupId);
        var loggedInUserId = customUserDetailsService.getLoggedInUserId();
        Long achievementId = achievementsService.getDayCheckAchievement(new Timestamp(new Date().getTime()));
        var userAchievements = achievementsService.getUserAchievement(loggedInUserId, achievementId);
        var res = dslContext.select(DATA_TUPLE.asterisk())
                .from(DATA_TUPLE.join(DATA_ELEMENT).onKey(DATA_TUPLE.DATA_ELEMENT_ID_1)
                        .join(TEXT).onKey(TEXT.DATA_ELEMENT_ID))
                .where(DSL.abs(DATA_TUPLE.WRONG.plus(DATA_TUPLE.CORRECT)).lessThan(speechCollectionAppConfig.getMinNumChecks())
                        .and(DATA_ELEMENT.USER_GROUP_ID.eq(groupId))
                        .and(DATA_TUPLE.ID.notIn(dslContext.select(CHECKED_DATA_TUPLE.DATA_TUPLE_ID)
                                .from(CHECKED_DATA_TUPLE)
                                .where(CHECKED_DATA_TUPLE.USER_ID.eq(loggedInUserId)))))
                .except(dslContext.select(DATA_TUPLE.asterisk())
                        .from(DATA_TUPLE.join(DATA_ELEMENT).on(DATA_TUPLE.DATA_ELEMENT_ID_2.eq(DATA_ELEMENT.ID)))
                        .where(DATA_ELEMENT.USER_ID.eq(loggedInUserId)))
                .limit(speechCollectionAppConfig.getNumRandomSelect()).fetchInto(DataTuple.class);
        var dataTuple = res.isEmpty() ? null : res.get(ThreadLocalRandom.current().nextInt(res.size()));
        return new CheckWrapper(dataTuple, achievementsService.getAchievementWrapper(userAchievements));
    }
public CheckWrapper checkNext ( long groupId ) { checkAllowed ( groupId ) ; var loggedInUserId = customUserDetailsService . getLoggedInUserId ( ) ; Long achievementId = achievementsService . getDayCheckAchievement ( new Timestamp ( new Date ( ) . getTime ( ) ) ) ; var userAchievements = achievementsService . getUserAchievement ( loggedInUserId , achievementId ) ; var res = dslContext . select ( DATA_TUPLE . asterisk ( ) ) . from ( DATA_TUPLE . join ( DATA_ELEMENT ) . onKey ( DATA_TUPLE . DATA_ELEMENT_ID_1 ) . join ( TEXT ) . onKey ( TEXT . DATA_ELEMENT_ID ) ) . where ( DSL . abs ( DATA_TUPLE . WRONG . plus ( DATA_TUPLE . CORRECT ) ) . lessThan ( speechCollectionAppConfig . getMinNumChecks ( ) ) . and ( DATA_ELEMENT . USER_GROUP_ID . eq ( groupId ) ) . and ( DATA_TUPLE . ID . notIn ( dslContext . select ( CHECKED_DATA_TUPLE . DATA_TUPLE_ID ) . from ( CHECKED_DATA_TUPLE ) . where ( CHECKED_DATA_TUPLE . USER_ID . eq ( loggedInUserId ) ) ) ) ) . except ( dslContext . select ( DATA_TUPLE . asterisk ( ) ) . from ( DATA_TUPLE . join ( DATA_ELEMENT ) . on ( DATA_TUPLE . DATA_ELEMENT_ID_2 . eq ( DATA_ELEMENT . ID ) ) ) . where ( DATA_ELEMENT . USER_ID . eq ( loggedInUserId ) ) ) . limit ( speechCollectionAppConfig . getNumRandomSelect ( ) ) . fetchInto ( DataTuple . class ) ; var dataTuple = res . isEmpty ( ) ? null : res . get ( ThreadLocalRandom . current ( ) . nextInt ( res . size ( ) ) ) ; return new CheckWrapper ( dataTuple , achievementsService . getAchievementWrapper ( userAchievements ) ) ; }
returns the next occurrence to check based on the groupId and available data.<br>
 occurrences are labeled until it is clear that they clearly wrong|correct.<br>
returns the next occurrence to check based on the groupId and available data . <br > occurrences are labeled until it is clear that they clearly wrong|correct . <br >
//.and(DATA_TUPLE.FINISHED.isFalse()) // user should only check once // user should not check self-generated data