def get(self, course_id, question_id, user_id): course = Courses.query.get_or_404(course_id) require(READ, course) question = PostsForQuestions.query.get_or_404(question_id) # ineligible authors - eg. instructors, TAs, dropped student, current user student = UserTypesForCourse.query.filter_by( name=UserTypesForCourse.TYPE_STUDENT).first_or_404() ineligible_users = CoursesAndUsers.query.filter_by(courses_id=course_id) \ .filter(CoursesAndUsers.usertypesforcourse_id != student.id) \ .values(CoursesAndUsers.users_id) ineligible_user_ids_base = [u[0] for u in ineligible_users] ineligible_user_ids_base.append(user_id) # ineligible authors (potentially) - eg. authors for answers that the user has seen judged = Judgements.query.filter_by(users_id=current_user.id).join(AnswerPairings) \ .filter_by(questions_id=question.id).all() judged_authors1 = [ j.answerpairing.answer1.post.users_id for j in judged ] judged_authors2 = [ j.answerpairing.answer2.post.users_id for j in judged ] ineligible_user_ids = ineligible_user_ids_base + judged_authors1 + judged_authors2 eligible_answers = PostsForAnswers.query.filter_by(questions_id=question.id) \ .join(Posts).filter(Posts.users_id.notin_(ineligible_user_ids)).count() avail_pairs = eligible_answers / 2 >= 1 # min 1 pair required return {'availPairsLogic': avail_pairs}
def get(self, course_id, question_id, user_id): course = Courses.query.get_or_404(course_id) require(READ, course) question = PostsForQuestions.query.get_or_404(question_id) # ineligible authors - eg. instructors, TAs, dropped student, current user student = UserTypesForCourse.query.filter_by(name=UserTypesForCourse.TYPE_STUDENT).first_or_404() ineligible_users = CoursesAndUsers.query.filter_by(courses_id=course_id) \ .filter(CoursesAndUsers.usertypesforcourse_id != student.id) \ .values(CoursesAndUsers.users_id) ineligible_user_ids_base = [u[0] for u in ineligible_users] ineligible_user_ids_base.append(user_id) # ineligible authors (potentially) - eg. authors for answers that the user has seen judged = Judgements.query.filter_by(users_id=current_user.id).join(AnswerPairings) \ .filter_by(questions_id=question.id).all() judged_authors1 = [j.answerpairing.answer1.post.users_id for j in judged] judged_authors2 = [j.answerpairing.answer2.post.users_id for j in judged] ineligible_user_ids = ineligible_user_ids_base + judged_authors1 + judged_authors2 eligible_answers = PostsForAnswers.query.filter_by(questions_id=question.id) \ .join(Posts).filter(Posts.users_id.notin_(ineligible_user_ids)).count() avail_pairs = eligible_answers / 2 >= 1 # min 1 pair required return {'availPairsLogic': avail_pairs}
def get(self, course_id, question_id): """ Get an answer pair for judgement. """ course = Courses.query.get_or_404(course_id) question = PostsForQuestions.query.get_or_404(question_id) require(READ, question) if not question.judging_period: return {'error': 'Evaluation period is not active.'}, 403 pair_generator = AnswerPairGenerator(course.id, question, current_user.id) try: answerpairing = pair_generator.get_pair() on_answer_pair_get.send(self, event_name=on_answer_pair_get.name, user=current_user, course_id=course_id, data={ 'id': answerpairing.id, 'answer_pair': ','.join([ str(answerpairing.answers_id1), str(answerpairing.answers_id2) ]), }) return marshal( { 'id': answerpairing.id, 'answers': [answerpairing.answer1, answerpairing.answer2] }, dataformat.get_answer_pairings_new()) except InsufficientAnswersException: return { "error": "Not enough answers are available for an evaluation." }, 400 except UserHasJudgedAllAnswers: return { "error": "You have judged all the currently available answers." }, 400 except AnswerMissingScoreCalculation: return {"error": "An answer is missing a calculated score."}, 400 except MissingScoreFromAnswer: return {"error": "A score is missing from an answer."}, 400 except UnknownAnswerPairError: return { "error": "Generating scored pairs failed, this really shouldn't happen." }, 500
def get(self, course_id): course = Courses.query.get_or_404(course_id) require(READ, course) questions = PostsForQuestions.query. \ with_entities(PostsForQuestions.id). \ join(Posts).filter_by(courses_id=course.id). \ all() # ineligible authors - eg. instructors, TAs, dropped student, current user ineligible_users = CoursesAndUsers.query. \ filter_by(courses_id=course_id). \ join(UserTypesForCourse).filter(UserTypesForCourse.name.notlike(UserTypesForCourse.TYPE_STUDENT)). \ values(CoursesAndUsers.users_id) ineligible_user_ids_base = [u[0] for u in ineligible_users] ineligible_user_ids_base.append(current_user.id) # It is a little bit hard to write query to include authors for each answers in the loop below # stmt = PostsForAnswers.query.\ # with_entities(PostsForAnswers.questions_id, func.count(PostsForAnswers.id).label('answer_count')). \ # join(Posts).join(AnswerPairings).join(Judgements). \ # filter(Posts.users_id.notin_(ineligible_userIds_base)).subquery() # # questions = PostsForQuestions.query.\ # with_entities(PostsForQuestions.id, stmt.c.answer_count). \ # join(Posts).filter_by(courses_id=course.id). \ # outerjoin(stmt, PostsForQuestions.id == stmt.c.questions_id). \ # all() avail_pairs = {} for ques in questions: question_id = ques[0] # ineligible authors (potentially) - eg. authors for answers that the user has seen judged = Judgements.query.filter_by(users_id=current_user.id).join(AnswerPairings) \ .filter_by(questions_id=question_id).all() judged_authors1 = [ j.answerpairing.answer1.post.users_id for j in judged ] judged_authors2 = [ j.answerpairing.answer2.post.users_id for j in judged ] ineligible_user_ids = ineligible_user_ids_base + judged_authors1 + judged_authors2 eligible_answers = PostsForAnswers.query.filter_by(questions_id=question_id) \ .join(Posts).filter(Posts.users_id.notin_(ineligible_user_ids)).count() avail_pairs[ question_id] = eligible_answers / 2 >= 1 # min 1 pair required return {'availPairsLogic': avail_pairs}
def get(self, course_id): course = Courses.query.get_or_404(course_id) require(READ, course) questions = PostsForQuestions.query.join(Posts).filter_by(courses_id=course.id).all() judgements = {ques.id: judgement_count(ques, current_user.id) for ques in questions} on_judgement_course_count.send( self, event_name=on_judgement_course_count.name, user=current_user, course_id=course_id, data={'user_id': current_user.id, 'counts': judgements} ) return {'judgements': judgements}
def get(self, course_id, question_id, user_id): course = Courses.query.get_or_404(course_id) require(READ, course) question = PostsForQuestions.query. \ options(load_only('id', 'criteria_count', 'posts_id')). \ get_or_404(question_id) require(READ, question) count = judgement_count(question, user_id) on_judgement_question_count.send( self, event_name=on_judgement_question_count.name, user=current_user, course_id=course_id, data={'question_id': question_id, 'user_id': user_id, 'count': count} ) return {"count": count}
def get(self, course_id): course = Courses.query.get_or_404(course_id) require(READ, course) questions = PostsForQuestions.query. \ with_entities(PostsForQuestions.id). \ join(Posts).filter_by(courses_id=course.id). \ all() # ineligible authors - eg. instructors, TAs, dropped student, current user ineligible_users = CoursesAndUsers.query. \ filter_by(courses_id=course_id). \ join(UserTypesForCourse).filter(UserTypesForCourse.name.notlike(UserTypesForCourse.TYPE_STUDENT)). \ values(CoursesAndUsers.users_id) ineligible_user_ids_base = [u[0] for u in ineligible_users] ineligible_user_ids_base.append(current_user.id) # It is a little bit hard to write query to include authors for each answers in the loop below # stmt = PostsForAnswers.query.\ # with_entities(PostsForAnswers.questions_id, func.count(PostsForAnswers.id).label('answer_count')). \ # join(Posts).join(AnswerPairings).join(Judgements). \ # filter(Posts.users_id.notin_(ineligible_userIds_base)).subquery() # # questions = PostsForQuestions.query.\ # with_entities(PostsForQuestions.id, stmt.c.answer_count). \ # join(Posts).filter_by(courses_id=course.id). \ # outerjoin(stmt, PostsForQuestions.id == stmt.c.questions_id). \ # all() avail_pairs = {} for ques in questions: question_id = ques[0] # ineligible authors (potentially) - eg. authors for answers that the user has seen judged = Judgements.query.filter_by(users_id=current_user.id).join(AnswerPairings) \ .filter_by(questions_id=question_id).all() judged_authors1 = [j.answerpairing.answer1.post.users_id for j in judged] judged_authors2 = [j.answerpairing.answer2.post.users_id for j in judged] ineligible_user_ids = ineligible_user_ids_base + judged_authors1 + judged_authors2 eligible_answers = PostsForAnswers.query.filter_by(questions_id=question_id) \ .join(Posts).filter(Posts.users_id.notin_(ineligible_user_ids)).count() avail_pairs[question_id] = eligible_answers / 2 >= 1 # min 1 pair required return {'availPairsLogic': avail_pairs}
def get(self, course_id): course = Courses.query.get_or_404(course_id) require(READ, course) questions = PostsForQuestions.query.join(Posts).filter_by( courses_id=course.id).all() judgements = { ques.id: judgement_count(ques, current_user.id) for ques in questions } on_judgement_course_count.send( self, event_name=on_judgement_course_count.name, user=current_user, course_id=course_id, data={ 'user_id': current_user.id, 'counts': judgements }) return {'judgements': judgements}
def get(self, course_id, question_id, user_id): course = Courses.query.get_or_404(course_id) require(READ, course) question = PostsForQuestions.query. \ options(load_only('id', 'criteria_count', 'posts_id')). \ get_or_404(question_id) require(READ, question) count = judgement_count(question, user_id) on_judgement_question_count.send( self, event_name=on_judgement_question_count.name, user=current_user, course_id=course_id, data={ 'question_id': question_id, 'user_id': user_id, 'count': count }) return {"count": count}
def get(self, course_id, question_id): """ Get an answer pair for judgement. """ course = Courses.query.get_or_404(course_id) question = PostsForQuestions.query.get_or_404(question_id) require(READ, question) if not question.judging_period: return {'error': 'Evaluation period is not active.'}, 403 pair_generator = AnswerPairGenerator(course.id, question, current_user.id) try: answerpairing = pair_generator.get_pair() on_answer_pair_get.send( self, event_name=on_answer_pair_get.name, user=current_user, course_id=course_id, data={ 'id': answerpairing.id, 'answer_pair': ','.join([str(answerpairing.answers_id1), str(answerpairing.answers_id2)]), }) return marshal( {'id': answerpairing.id, 'answers': [answerpairing.answer1, answerpairing.answer2]}, dataformat.get_answer_pairings_new()) except InsufficientAnswersException: return {"error": "Not enough answers are available for an evaluation."}, 400 except UserHasJudgedAllAnswers: return {"error": "You have judged all the currently available answers."}, 400 except AnswerMissingScoreCalculation: return {"error": "An answer is missing a calculated score."}, 400 except MissingScoreFromAnswer: return {"error": "A score is missing from an answer."}, 400 except UnknownAnswerPairError: return {"error": "Generating scored pairs failed, this really shouldn't happen."}, 500
def post(self, course_id, question_id): """ Stores a judgement into the database. """ Courses.query.get_or_404(course_id) question = PostsForQuestions.query.get_or_404(question_id) if not question.judging_period: return {'error': 'Evaluation period is not active.'}, 403 require(READ, question) require(CREATE, Judgements) question_criteria = CriteriaAndPostsForQuestions.query. \ filter_by(question=question, active=True).all() params = new_judgement_parser.parse_args() answer_pair = AnswerPairings.query.get(params['answerpair_id']) if not answer_pair: return {"error": "Invalid Answer Pair ID"}, 404 # check if number of judgements matches number of criteria if len(question_criteria) != len(params['judgements']): return {"error": "Not all criteria were evaluated."}, 400 # check if each judgement has an questionCriteria Id and a winner id for judgement in params['judgements']: if 'question_criterion_id' not in judgement: return {"error": "Missing question_criterion_id in evaluation."}, 400 if 'answer_id_winner' not in judgement: return {"error": "Missing selected answer for one of the criteria."}, 400 # check that we're using criteria that were assigned to the course and that we didn't # get duplicate criteria in judgements known_criterion = False for question_criterion_entry in question_criteria[:]: if judgement['question_criterion_id'] == question_criterion_entry.id: known_criterion = True question_criteria.remove(question_criterion_entry) if not known_criterion: return {"error": "Unknown criterion submitted in judgement!"}, 400 # check that the winner id matches one of the answer pairs winner_id = judgement['answer_id_winner'] if winner_id != answer_pair.answer1.id and winner_id != answer_pair.answer2.id: return {"error": "Selected answer ID does not match the available pair of answers."}, 400 # check if pair has already been judged by this user if Judgements.query.filter_by(users_id=current_user.id).join(AnswerPairings). \ filter(or_( and_( AnswerPairings.answers_id1 == answer_pair.answers_id1, AnswerPairings.answers_id2 == answer_pair.answers_id2), and_( AnswerPairings.answers_id1 == answer_pair.answers_id2, AnswerPairings.answers_id2 == answer_pair.answers_id1) ) ).first(): return {"error": "You've already evaluated this pair of answers."}, 400 # now the real deal, creating the judgement judgements = Judgements.create_judgement(params, answer_pair, current_user.id) # update answer scores current_app.logger.debug("Doing scoring") Judgements.calculate_scores(question_id) on_judgement_create.send( self, event_name=on_judgement_create.name, user=current_user, course_id=course_id, data=marshal(judgements, dataformat.get_judgements())) return {'objects': marshal(judgements, dataformat.get_judgements())}
def post(self, course_id, question_id): """ Stores a judgement into the database. """ Courses.query.get_or_404(course_id) question = PostsForQuestions.query.get_or_404(question_id) if not question.judging_period: return {'error': 'Evaluation period is not active.'}, 403 require(READ, question) require(CREATE, Judgements) question_criteria = CriteriaAndPostsForQuestions.query. \ filter_by(question=question, active=True).all() params = new_judgement_parser.parse_args() answer_pair = AnswerPairings.query.get(params['answerpair_id']) if not answer_pair: return {"error": "Invalid Answer Pair ID"}, 404 # check if number of judgements matches number of criteria if len(question_criteria) != len(params['judgements']): return {"error": "Not all criteria were evaluated."}, 400 # check if each judgement has an questionCriteria Id and a winner id for judgement in params['judgements']: if 'question_criterion_id' not in judgement: return { "error": "Missing question_criterion_id in evaluation." }, 400 if 'answer_id_winner' not in judgement: return { "error": "Missing selected answer for one of the criteria." }, 400 # check that we're using criteria that were assigned to the course and that we didn't # get duplicate criteria in judgements known_criterion = False for question_criterion_entry in question_criteria[:]: if judgement[ 'question_criterion_id'] == question_criterion_entry.id: known_criterion = True question_criteria.remove(question_criterion_entry) if not known_criterion: return { "error": "Unknown criterion submitted in judgement!" }, 400 # check that the winner id matches one of the answer pairs winner_id = judgement['answer_id_winner'] if winner_id != answer_pair.answer1.id and winner_id != answer_pair.answer2.id: return { "error": "Selected answer ID does not match the available pair of answers." }, 400 # check if pair has already been judged by this user if Judgements.query.filter_by(users_id=current_user.id).join(AnswerPairings). \ filter(or_( and_( AnswerPairings.answers_id1 == answer_pair.answers_id1, AnswerPairings.answers_id2 == answer_pair.answers_id2), and_( AnswerPairings.answers_id1 == answer_pair.answers_id2, AnswerPairings.answers_id2 == answer_pair.answers_id1) ) ).first(): return { "error": "You've already evaluated this pair of answers." }, 400 # now the real deal, creating the judgement judgements = Judgements.create_judgement(params, answer_pair, current_user.id) # update answer scores current_app.logger.debug("Doing scoring") Judgements.calculate_scores(question_id) on_judgement_create.send(self, event_name=on_judgement_create.name, user=current_user, course_id=course_id, data=marshal(judgements, dataformat.get_judgements())) return {'objects': marshal(judgements, dataformat.get_judgements())}