Created
February 9, 2016 16:29
-
-
Save jhamrick/506c0161af1393ae32cf to your computer and use it in GitHub Desktop.
An example of how to programmatically generate a feedback notebook for nbgrader
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import os | |
import pandas as pd | |
from nbgrader.api import Gradebook | |
from nbformat import write as write_nb | |
from nbformat.v4 import new_notebook, new_markdown_cell | |
def gradebook(): | |
if os.environ.get('NBGRADER_DB_URL', ''): | |
gb = Gradebook(os.environ['NBGRADER_DB_URL']) | |
else: | |
gb = Gradebook('sqlite:///gradebook.db') | |
return gb | |
def load_timestamp(assignment, student): | |
timestamps = pd.read_csv("grades/timestamps.csv")\ | |
.groupby('assignment')\ | |
.get_group(assignment)\ | |
.set_index('student').T | |
return timestamps[student] | |
def _make_feedback_section(nb, submission, ts): | |
total_score = submission.score | |
total_max_score = submission.max_score | |
src = "## Score: {:.2f} / {:.2f}\n\n".format(max(0.0, total_score - ts['late_penalty']), total_max_score) | |
if ts['late_penalty'] > 0: | |
src += '* Raw score: {:.2f} / {:.2f}\n'.format(total_score, total_max_score) | |
src += '* Late penalty: {:.2f}\n'.format(ts['late_penalty']) | |
src += "\nClick on the notebooks below to see comments and scores for each part of the problem.\n\n" | |
for notebook in submission.notebooks: | |
src += "* [{}](html/{}.html)\n".format(notebook.notebook.name, notebook.notebook.name) | |
src += " * Score: {:.2f} / {:.2f}\n".format(notebook.score, notebook.max_score) | |
has_comments = any([x.comment for x in notebook.comments]) | |
if has_comments: | |
src += " * Note: some parts of this problem have comments/feedback from the grader\n" | |
nb.cells.append(new_markdown_cell(src)) | |
def make_feedback_notebook(assignment_id, student_id): | |
# load gradebook | |
gb = gradebook() | |
# create index notebook | |
index = new_notebook() | |
index.cells.append(new_markdown_cell(source='# Grades for {}'.format(assignment_id))) | |
ts = load_timestamp(assignment_id, student_id) | |
src = '* Time submitted: {}\n'.format(ts['timestamp']) | |
src += '* Late days used: {:.0f}\n'.format(ts['late_days']) | |
index.cells.append(new_markdown_cell(src)) | |
# report information about the normal problems | |
submission = gb.find_submission(assignment_id, student_id) | |
_make_feedback_section(index, submission, ts) | |
# set kernel to python 3 | |
index.metadata["kernelspec"] = { | |
"display_name": "Python 3", | |
"name": "python3" | |
} | |
with open(os.path.join("feedback", assignment_id, student_id, "Grades.ipynb"), "w") as fh: | |
write_nb(index, fh) | |
return index |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment