Skip to content

Commit 118f441

Browse files
committed
Include numbas.review_allowed SCORM element, to determine if full review is allowed.
See numbas/editor#795 If review mode is not allowed yet, a student can still enter an exam, but in the "just completed" mode, so they might not see all feedback, depending on the exam's feedback settings. The attempts listing page shows when each kind of feedback is available.
1 parent e0ca58b commit 118f441

5 files changed

Lines changed: 64 additions & 16 deletions

File tree

numbas_lti/forms.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -205,6 +205,7 @@ def save(self, commit=True):
205205

206206
class CreateExamForm(ModelForm):
207207
package = forms.FileField(required=False)
208+
208209
class Meta:
209210
model = Exam
210211
fields = ['package','retrieve_url','rest_url']

numbas_lti/models.py

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -289,6 +289,34 @@ def duration(self):
289289

290290
return self._duration
291291

292+
def get_feedback_settings(self, completed, review_allowed):
293+
content = self.source()
294+
295+
def get(node, attr, default=None):
296+
return node.get(attr, node.get(attr.lower(), default))
297+
298+
feedback = get(content, 'feedback', {})
299+
300+
def resolve_feedback_setting(setting):
301+
return {
302+
'always': True,
303+
'oncompletion': completed,
304+
'inreview': review_allowed,
305+
'never': False,
306+
}[setting]
307+
308+
info = [
309+
(_('Maximum available score'), get(feedback,'showTotalMark', 'always')),
310+
(_('Whether answers are correct'), get(feedback,'showAnswerState', 'always')),
311+
(_('Awarded scores'), get(feedback,'showActualMark', 'always')),
312+
(_('Feedback messages for each question part'), get(feedback, 'showPartFeedbackMessages', 'always')),
313+
(_('Expected answers to each part'), get(feedback, 'revealExpectedAnswers', 'inreview')),
314+
(_('Advice for each question'), get(feedback, 'revealAdvice', 'inreview')),
315+
]
316+
317+
return info
318+
319+
292320
GRADING_METHODS = [
293321
('highest',_('Highest score')),
294322
('last',_('Last attempt')),

numbas_lti/templates/numbas_lti/review_not_allowed.html

Lines changed: 0 additions & 1 deletion
This file was deleted.

numbas_lti/templates/numbas_lti/show_attempts.html

Lines changed: 30 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -67,15 +67,9 @@ <h1>
6767
</td>
6868
<td>
6969
{% if attempt.completed %}
70-
{% if attempt.review_allowed %}
7170
<a title="{% blocktranslate with start_time=attempt.start_time %}Review attempt started at {{start_time}}{% endblocktranslate %}" class="button info" href="{% url_with_lti 'run_attempt' pk=attempt.pk %}">
72-
{% icon 'play' %} {% translate "Review this attempt" %}
73-
</a>
74-
{% else %}
75-
{% if attempt.resource.allow_review_from %}
76-
{% include "numbas_lti/review_not_allowed.html" with allow_review_from=attempt.resource.allow_review_from %}
77-
{% endif %}
78-
{% endif %}
71+
{% icon 'play' %} {% translate "Review this attempt" %}
72+
</a>
7973
{% else %}
8074
{% if attempt.resume_allowed %}
8175
<a title="{% blocktranslate with start_time=attempt.start_time %}Continue attempt started at {{start_time}}{% endblocktranslate %}" class="button {% if attempt.completed %}info{% else %}primary{% endif %}" href="{% url_with_lti 'run_attempt' pk=attempt.pk %}">
@@ -88,6 +82,34 @@ <h1>
8882
{% endfor %}
8983
</tbody>
9084
</table>
85+
86+
{% if resource.show_marks_when == 'review' and resource.allow_review_from %}
87+
<p class="warning">{% blocktranslate with time_iso=resource.allow_review_from|date:"c" time=resource.allow_review_from %}Full review will be available from <time datetime="{{time_iso}}">{{time}}</time>.{% endblocktranslate %}</p>
88+
{% endif %}
89+
90+
<p>{% blocktranslate %}These are the feedback settings for this activity:{% endblocktranslate %}</p>
91+
92+
<table class="settings-table">
93+
<thead>
94+
<tr>
95+
<th scope="col">{% translate "Feedback" %}</th>
96+
<th scope="col">{% translate "Available from" %}</th>
97+
</tr>
98+
</thead>
99+
<tbody>
100+
{% for label, when in exam_info %}
101+
<tr>
102+
<td scope="row">{{label}}</td>
103+
<td>
104+
{% if when == 'always' %}{% translate "The start of the attempt" %}{% endif %}
105+
{% if when == 'oncompletion' %}{% translate "Immediately after finishing" %}{% endif %}
106+
{% if when == 'inreview' %}{% translate "When full review is allowed" %}{% endif %}
107+
{% if when == 'never' %}{% translate "Never" %}{% endif %}
108+
</td>
109+
</tr>
110+
{% endfor %}
111+
</tbody>
112+
</table>
91113
</main>
92114

93115
{% include "numbas_lti/footer.html" %}

numbas_lti/views/attempt.py

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -201,8 +201,11 @@ def dispatch(self,request,*args,**kwargs):
201201
def get_context_data(self,*args,**kwargs):
202202
context = super(ShowAttemptsView,self).get_context_data(*args,**kwargs)
203203

204-
context['resource'] = self.request.resource
204+
resource = self.request.resource
205+
206+
context['resource'] = resource
205207
context['can_start_new_attempt'] = self.request.resource.can_start_new_attempt(self.request.user)
208+
context['exam_info'] = resource.exam.get_feedback_settings(completed=False,review_allowed=False)
206209

207210
return context
208211

@@ -252,12 +255,6 @@ def get_mode(self):
252255
raise PermissionDenied(gettext("You're not allowed to review this attempt."))
253256

254257
if attempt.completed():
255-
if not attempt.review_allowed():
256-
if attempt.resource.allow_review_from:
257-
template = get_template('numbas_lti/review_not_allowed.html')
258-
raise PermissionDenied(template.render({'allow_review_from': attempt.resource.allow_review_from}))
259-
else:
260-
raise PermissionDenied(_("You're not allowed to review this attempt."))
261258
return 'review'
262259
else:
263260
return 'normal'
@@ -374,6 +371,7 @@ def get_data(self):
374371
'numbas.user_role': 'instructor' if request_is_instructor(self.request) else 'student',
375372
'numbas.duration_extension.amount': duration_extension_amount,
376373
'numbas.duration_extension.units': duration_extension_units,
374+
'numbas.review_allowed': attempt.review_allowed(),
377375
}
378376

379377
now = datetime.datetime.now().timestamp()

0 commit comments

Comments
 (0)