From ade99469eae873632f1df20b9bbdeef16300a4ab Mon Sep 17 00:00:00 2001 From: Artur Gaspar Date: Mon, 14 Oct 2024 13:13:52 -0300 Subject: [PATCH] feat: allow viewing attachments in studio --- ai_eval/shortanswer.py | 19 +++++++++++++++++++ ai_eval/static/js/src/shortanswer_edit.js | 15 ++++++++++++++- 2 files changed, 33 insertions(+), 1 deletion(-) diff --git a/ai_eval/shortanswer.py b/ai_eval/shortanswer.py index 2080824..c60e95a 100644 --- a/ai_eval/shortanswer.py +++ b/ai_eval/shortanswer.py @@ -6,6 +6,7 @@ from django.utils.translation import gettext_noop as _ from web_fragments.fragment import Fragment +from webob import Response from xblock.core import XBlock from xblock.exceptions import JsonHandlerError from xblock.fields import Dict, Integer, String, Scope @@ -185,6 +186,24 @@ def submit_studio_edits(self, data, suffix=''): data["values"]["attachments"][key] = self.attachments[key] return super().submit_studio_edits.__wrapped__(self, data, suffix) + @XBlock.handler + def view_attachment(self, request, suffix=''): + # TODO: restrict to studio + key = request.GET['key'] + try: + data = self.attachments[key] + except KeyError: + # TODO: 404 + raise + return Response( + body=data.encode(), + headerlist=[ + ("Content-Type", "application/octet-stream"), + # TODO: escape and encode filename + ("Content-Disposition", f'attachment; filename="{key}"'), + ] + ) + @staticmethod def workbench_scenarios(): """A canned scenario for display in the workbench.""" diff --git a/ai_eval/static/js/src/shortanswer_edit.js b/ai_eval/static/js/src/shortanswer_edit.js index d6e8ebd..47261aa 100644 --- a/ai_eval/static/js/src/shortanswer_edit.js +++ b/ai_eval/static/js/src/shortanswer_edit.js @@ -4,6 +4,8 @@ function ShortAnswerAIEvalXBlock(runtime, element) { StudioEditableXBlockMixin(runtime, element); + var viewAttachmentUrl = runtime.handlerUrl(element, "view_attachment"); + var $input = $('#xb-field-edit-attachments'); var buildFileInput = function() { @@ -13,7 +15,18 @@ function ShortAnswerAIEvalXBlock(runtime, element) { var files = JSON.parse($input.val() || "{}"); for (var filename of Object.keys(files)) { var $fileItem = $('
  • '); - $fileItem.append(filename); + var $fileLink; + if (files[filename] === null) { + /* File that already exists. */ + $fileLink = $(''); + $fileLink.attr("target", "_blank"); + var fileLinkQuery = new URLSearchParams({key: filename}).toString(); + $fileLink.attr('href', `${viewAttachmentUrl}?${fileLinkQuery}`); + } else { + $fileLink = $(''); + } + $fileLink.append(filename); + $fileItem.append($fileLink); var $deleteButton = $('