Merge pull request #1791 from MITx/fix/brian/foldit-grading
when grading, check for always-regrade at the section level too
This commit is contained in:
@@ -13,7 +13,6 @@ from xblock.core import Scope
|
||||
from .module_render import get_module, get_module_for_descriptor
|
||||
from xmodule import graders
|
||||
from xmodule.capa_module import CapaModule
|
||||
from xmodule.course_module import CourseDescriptor
|
||||
from xmodule.graders import Score
|
||||
from .models import StudentModule
|
||||
|
||||
@@ -43,7 +42,6 @@ def yield_dynamic_descriptor_descendents(descriptor, module_creator):
|
||||
else:
|
||||
return descriptor.get_children()
|
||||
|
||||
|
||||
stack = [descriptor]
|
||||
|
||||
while len(stack) > 0:
|
||||
@@ -66,7 +64,7 @@ def yield_problems(request, course, student):
|
||||
).values_list('module_state_key', flat=True))
|
||||
|
||||
sections_to_list = []
|
||||
for section_format, sections in grading_context['graded_sections'].iteritems():
|
||||
for _, sections in grading_context['graded_sections'].iteritems():
|
||||
for section in sections:
|
||||
|
||||
section_descriptor = section['section_descriptor']
|
||||
@@ -123,7 +121,7 @@ def answer_distributions(request, course):
|
||||
|
||||
def grade(student, request, course, model_data_cache=None, keep_raw_scores=False):
|
||||
"""
|
||||
This grades a student as quickly as possible. It retuns the
|
||||
This grades a student as quickly as possible. It returns the
|
||||
output from the course grader, augmented with the final letter
|
||||
grade. The keys in the output are:
|
||||
|
||||
@@ -158,6 +156,12 @@ def grade(student, request, course, model_data_cache=None, keep_raw_scores=False
|
||||
should_grade_section = False
|
||||
# If we haven't seen a single problem in the section, we don't have to grade it at all! We can assume 0%
|
||||
for moduledescriptor in section['xmoduledescriptors']:
|
||||
# some problems have state that is updated independently of interaction
|
||||
# with the LMS, so they need to always be scored. (E.g. foldit.)
|
||||
if moduledescriptor.always_recalculate_grades:
|
||||
should_grade_section = True
|
||||
break
|
||||
|
||||
# Create a fake key to pull out a StudentModule object from the ModelDataCache
|
||||
|
||||
key = LmsKeyValueStore.Key(
|
||||
@@ -174,7 +178,8 @@ def grade(student, request, course, model_data_cache=None, keep_raw_scores=False
|
||||
scores = []
|
||||
|
||||
def create_module(descriptor):
|
||||
# TODO: We need the request to pass into here. If we could forgo that, our arguments
|
||||
'''creates an XModule instance given a descriptor'''
|
||||
# TODO: We need the request to pass into here. If we could forego that, our arguments
|
||||
# would be simpler
|
||||
return get_module_for_descriptor(student, request, descriptor, model_data_cache, course.id)
|
||||
|
||||
@@ -197,18 +202,18 @@ def grade(student, request, course, model_data_cache=None, keep_raw_scores=False
|
||||
|
||||
scores.append(Score(correct, total, graded, module_descriptor.display_name_with_default))
|
||||
|
||||
section_total, graded_total = graders.aggregate_scores(scores, section_name)
|
||||
_, graded_total = graders.aggregate_scores(scores, section_name)
|
||||
if keep_raw_scores:
|
||||
raw_scores += scores
|
||||
else:
|
||||
section_total = Score(0.0, 1.0, False, section_name)
|
||||
graded_total = Score(0.0, 1.0, True, section_name)
|
||||
|
||||
#Add the graded total to totaled_scores
|
||||
if graded_total.possible > 0:
|
||||
format_scores.append(graded_total)
|
||||
else:
|
||||
log.exception("Unable to grade a section with a total possible score of zero. " + str(section_descriptor.location))
|
||||
log.exception("Unable to grade a section with a total possible score of zero. " +
|
||||
str(section_descriptor.location))
|
||||
|
||||
totaled_scores[section_format] = format_scores
|
||||
|
||||
@@ -274,12 +279,9 @@ def progress_summary(student, request, course, model_data_cache):
|
||||
|
||||
"""
|
||||
|
||||
|
||||
# TODO: We need the request to pass into here. If we could forgo that, our arguments
|
||||
# TODO: We need the request to pass into here. If we could forego that, our arguments
|
||||
# would be simpler
|
||||
course_module = get_module(student, request,
|
||||
course.location, model_data_cache,
|
||||
course.id, depth=None)
|
||||
course_module = get_module(student, request, course.location, model_data_cache, course.id, depth=None)
|
||||
if not course_module:
|
||||
# This student must not have access to the course.
|
||||
return None
|
||||
@@ -310,20 +312,19 @@ def progress_summary(student, request, course, model_data_cache):
|
||||
if correct is None and total is None:
|
||||
continue
|
||||
|
||||
scores.append(Score(correct, total, graded,
|
||||
module_descriptor.display_name_with_default))
|
||||
scores.append(Score(correct, total, graded, module_descriptor.display_name_with_default))
|
||||
|
||||
scores.reverse()
|
||||
section_total, graded_total = graders.aggregate_scores(
|
||||
section_total, _ = graders.aggregate_scores(
|
||||
scores, section_module.display_name_with_default)
|
||||
|
||||
format = section_module.lms.format if section_module.lms.format is not None else ''
|
||||
module_format = section_module.lms.format if section_module.lms.format is not None else ''
|
||||
sections.append({
|
||||
'display_name': section_module.display_name_with_default,
|
||||
'url_name': section_module.url_name,
|
||||
'scores': scores,
|
||||
'section_total': section_total,
|
||||
'format': format,
|
||||
'format': module_format,
|
||||
'due': section_module.lms.due,
|
||||
'graded': graded,
|
||||
})
|
||||
@@ -353,11 +354,13 @@ def get_score(course_id, user, problem_descriptor, module_creator, model_data_ca
|
||||
if not user.is_authenticated():
|
||||
return (None, None)
|
||||
|
||||
# some problems have state that is updated independently of interaction
|
||||
# with the LMS, so they need to always be scored. (E.g. foldit.)
|
||||
if problem_descriptor.always_recalculate_grades:
|
||||
problem = module_creator(problem_descriptor)
|
||||
d = problem.get_score()
|
||||
if d is not None:
|
||||
return (d['score'], d['total'])
|
||||
score = problem.get_score()
|
||||
if score is not None:
|
||||
return (score['score'], score['total'])
|
||||
else:
|
||||
return (None, None)
|
||||
|
||||
@@ -394,7 +397,7 @@ def get_score(course_id, user, problem_descriptor, module_creator, model_data_ca
|
||||
if total is None:
|
||||
return (None, None)
|
||||
|
||||
#Now we re-weight the problem, if specified
|
||||
# Now we re-weight the problem, if specified
|
||||
weight = problem_descriptor.weight
|
||||
if weight is not None:
|
||||
if total == 0:
|
||||
|
||||
Reference in New Issue
Block a user