Beispiel #1
0
def main():
    setup_logging()

    args, parser = parse_args()

    if "none" == args.which:
        parser.print_help()
    elif "ungraded" == args.which:
        submissions_status = submissions_statistics(
            args.course_id,
            is_verbose=args.verbose,
            download_folder=args.download_folder,
        )
        print("Total ungraded: {}".format(
            submissions_status["total_ungraded"]))
    elif args.which == "list_students":
        pprint(get_students(args.course_id))
    elif "feedbacks" == args.which:
        export_feedbacks(args.course_id, Path(args.download_folder))
    elif "export" == args.which:
        export_all(args.course_id, Path(args.download_folder))
    elif "student_report" == args.which:
        student_statuses = status_report(args.course_id)
        headers = ("Student", "Submissions", "Last Submission")
        print(tabulate(student_statuses, headers, tablefmt="pretty"))
Beispiel #2
0
def status_report(course_id):
    """
    Generates a short report of the students for a specific course.
    Returns a list of StudentStatus tuples.
    """
    assignments = get_assignments(course_id)
    users_map = get_students(course_id)

    submissions_by_user = Counter()
    last_submission_by_user = defaultdict(
        lambda: SubmissionTuple(name="Nothing", timestamp=0))

    for assignment in assignments:
        for submission in assignment.submissions:
            user_name = users_map[submission.user_id]
            submissions_by_user[user_name] += 1

            if (last_submission_by_user[user_name].timestamp <
                    submission.timestamp):
                last_submission_by_user[user_name] = SubmissionTuple(
                    name=assignment.name, timestamp=submission.timestamp)

    student_statuses = []
    for user, submission_count in submissions_by_user.items():
        student_statuses.append(
            StudentStatus(user, submission_count,
                          last_submission_by_user[user].name))

    student_statuses = sorted(
        student_statuses,
        key=lambda student_status: student_status.total_submissions,
    )

    return student_statuses
Beispiel #3
0
def export_submissions(course_id, download_folder):
    """
    Downloads all submissions from a given course
    """
    assignments = get_assignments(course_id)
    users_map = get_students(course_id)
    for assignment in assignments:
        for submission in assignment.submissions:
            download_submission(
                assignment.name,
                users_map[submission.user_id],
                submission,
                download_folder,
            )
Beispiel #4
0
    def lock_submissions(self, course_id, students_names=None):
        """
        Locking submissions for this specific assignment.
        """
        if students_names is None:
            students_ids = list(get_students(course_id).keys())
        else:
            students_ids = get_students_ids_by_name(course_id, students_names)

        if not students_ids:
            logger.warning("No student was found! Aborting...")
        else:
            mod_assign_lock_submissions(self.uid, students_ids)

            logger.info(
                "Locked submissions for assignment '%s' for %s",
                self.name,
                students_names
                if students_names is not None else "all students.",
            )
Beispiel #5
0
def submissions_statistics(course_id, is_verbose=False, download_folder=None):
    """
    Returns a dictionary describing the status of ungraded exercises in the course.
    The dictionary looks like this:
        ```
        {
            'total_submissions': 10,
            'total_ungraded': 5,
            'total_resubmissions': 2,
            'exercises': {
                'assign1': {
                    'submissions': 2,
                    'ungraded': 2,
                    'resubmissions': 0}
                },
                ...
            }
        }
        ```

    If download_folder is set, downloads the ungraded exercises
    """
    logger.info("Showing ungraded submissions for course %s", course_id)
    total_submissions = 0
    total_ungraded = 0
    total_resubmissions = 0
    assignments_statistics = {}

    assignments = get_assignments(course_id)
    users_map = get_students(course_id)

    for assignment in assignments:
        current_assignment_submissions_amount = len(assignment.submissions)
        current_assignment_ungraded = assignment.ungraded()
        current_assignment_ungraded_amount = len(current_assignment_ungraded)

        current_assignment_resubmissions_amount = 0
        ungraded_ignored = []

        for submission in current_assignment_ungraded:
            if submission.resubmitted:
                current_assignment_resubmissions_amount += 1

            if submission.user_id in STUDENTS_TO_IGNORE.keys():
                ungraded_ignored.append(STUDENTS_TO_IGNORE[submission.user_id])

            if download_folder is not None:
                download_submission(
                    assignment.name,
                    users_map[submission.user_id],
                    submission,
                    download_folder,
                )

        total_submissions += current_assignment_submissions_amount
        total_ungraded += current_assignment_ungraded_amount
        total_resubmissions += current_assignment_resubmissions_amount

        # Print total stats about this assignment
        if is_verbose and len(ungraded_ignored) != 0:
            logger.info(
                "Ignored %s submissions for assignment '%s' (CMID %s, ID %s): %s",
                len(ungraded_ignored),
                assignment.name,
                assignment.cmid,
                assignment.uid,
                ungraded_ignored,
            )

        amount_ungraded_not_ignored = current_assignment_ungraded_amount - len(
            ungraded_ignored)
        if amount_ungraded_not_ignored != 0:
            logger.info(
                "Total ungraded for assignment [%s] (CMID %s, ID %s): %s/%s",
                assignment.name,
                assignment.cmid,
                assignment.uid,
                amount_ungraded_not_ignored,
                len(assignment.submissions),
            )

        assignments_statistics[assignment.name] = {
            "submissions": current_assignment_submissions_amount,
            "ungraded": amount_ungraded_not_ignored,
            "resubmissions": current_assignment_resubmissions_amount,
        }

    return {
        "total_submissions": total_submissions,
        "total_ungraded": total_ungraded,
        "total_resubmissions": total_resubmissions,
        "exercises": assignments_statistics,
    }