diff --git a/openassessment/xblock/test/test_submission.py b/openassessment/xblock/test/test_submission.py index f42401f0ff..453cbe8363 100644 --- a/openassessment/xblock/test/test_submission.py +++ b/openassessment/xblock/test/test_submission.py @@ -15,6 +15,8 @@ from django.core.exceptions import ObjectDoesNotExist from django.test.utils import override_settings from freezegun import freeze_time +from openedx_filters import PipelineStep +from openedx_filters.learning.filters import ORASubmissionViewRenderStarted from xblock.exceptions import NoSuchServiceError from submissions import api as sub_api @@ -29,7 +31,7 @@ from openassessment.xblock.apis.submissions import submissions_actions from openassessment.xblock.utils.data_conversion import create_submission_dict, prepare_submission_for_serialization from openassessment.xblock.openassessmentblock import OpenAssessmentBlock -from openassessment.xblock.ui_mixins.legacy.views.submission import get_team_submission_context +from openassessment.xblock.ui_mixins.legacy.views.submission import get_team_submission_context, render_submission from openassessment.xblock.workflow_mixin import WorkflowMixin from openassessment.xblock.test.test_team import MockTeamsService, MOCK_TEAM_ID @@ -79,6 +81,22 @@ def setup_mock_team(xblock): return setup_mock_team(xblock) +class TestRenderInvalidTemplate(PipelineStep): + """ + Utility class used when getting steps for pipeline. + """ + + def run_filter(self, context, template_name): # pylint: disable=arguments-differ + """ + Pipeline step that stops the course about render process. + """ + raise ORASubmissionViewRenderStarted.RenderInvalidTemplate( + "Invalid template.", + context={"context": "current_context"}, + template_name="current/path/template.html", + ) + + @ddt.ddt class SubmissionTest(SubmissionXBlockHandlerTestCase, SubmissionTestMixin): """ Test Submissions Api for Open Assessments. """ @@ -822,6 +840,68 @@ def test_team_open_unanswered(self, xblock): } ) + @patch('openassessment.xblock.ui_mixins.legacy.views.submission.get_submission_path') + @patch.object(OpenAssessmentBlock, "render_assessment") + @patch.object(ORASubmissionViewRenderStarted, "run_filter") + @scenario('data/submission_open.xml', user_id="Red Five") + def test_render_submission_no_run_filter( + self, + xblock, + mock_run_filter: Mock, + mock_render_assessment: Mock, + mock_get_submission_path: Mock + ): + """ + Test for `render_submission` when the `run_filter` method is not called. + """ + mock_get_submission_path.return_value = "another/path/template.html" + + render_submission(xblock.config_data, xblock.submission_data) + + mock_run_filter.assert_not_called() + mock_render_assessment.assert_called_once() + + @patch.object(OpenAssessmentBlock, "render_assessment") + @patch.object(ORASubmissionViewRenderStarted, "run_filter") + @scenario('data/submission_open.xml', user_id="Red Five") + def test_render_submission_run_filter( + self, xblock, mock_run_filter: Mock, mock_render_assessment: Mock + ): + """ + Test for `render_submission` when the `run_filter` method is called. + """ + expected_context = {"context": "new_context"} + expected_path = "new/path/template.html" + mock_run_filter.return_value = (expected_context, expected_path) + + render_submission(xblock.config_data, xblock.submission_data) + + mock_run_filter.assert_called_once() + mock_render_assessment.assert_called_once_with(expected_path, expected_context) + + @override_settings( + OPEN_EDX_FILTERS_CONFIG={ + "org.openedx.learning.ora.submission_view.render.started.v1": { + "fail_silently": False, + "pipeline": [ + "openassessment.xblock.test.test_submission.TestRenderInvalidTemplate" + ] + } + } + ) + @patch.object(OpenAssessmentBlock, "render_assessment") + @scenario('data/submission_open.xml', user_id="Red Five") + def test_render_submission_run_filter_exception(self, xblock, mock_render_assessment: Mock): + """ + Test for `render_submission` when the `run_filter` method raises an exception. + """ + expected_context = {"context": "current_context"} + expected_path = "current/path/template.html" + + render_submission(xblock.config_data, xblock.submission_data) + + mock_render_assessment.assert_called_once_with(expected_path, expected_context) + @patch('submissions.team_api.get_teammates_with_submissions_from_other_teams') @scenario('data/submission_open.xml', user_id="Red Five") def test_get_team_submission_context( diff --git a/openassessment/xblock/ui_mixins/legacy/views/submission.py b/openassessment/xblock/ui_mixins/legacy/views/submission.py index 8119502f64..4a16841f95 100644 --- a/openassessment/xblock/ui_mixins/legacy/views/submission.py +++ b/openassessment/xblock/ui_mixins/legacy/views/submission.py @@ -4,6 +4,7 @@ import logging from django.core.exceptions import ObjectDoesNotExist +from openedx_filters.learning.filters import ORASubmissionViewRenderStarted from xblock.exceptions import NoSuchServiceError from openassessment.xblock.utils.data_conversion import ( @@ -37,6 +38,14 @@ def render_submission(config, submission_info): context = get_submission_context(config, submission_info) path = get_submission_path(submission_info) + if path == "legacy/response/oa_response.html": + try: + # .. filter_implemented_name: ORASubmissionViewRenderStarted + # .. filter_type: org.openedx.learning.ora.submission_view.render.started.v1 + context, path = ORASubmissionViewRenderStarted.run_filter(context, path) + except ORASubmissionViewRenderStarted.RenderInvalidTemplate as exc: + context, path = exc.context, exc.template_name # pylint: disable=no-member + return config.render_assessment(path, context_dict=context) diff --git a/requirements/base.in b/requirements/base.in index 972338b182..ca87fa873b 100644 --- a/requirements/base.in +++ b/requirements/base.in @@ -9,6 +9,7 @@ edx-toggles djangorestframework Xblock edx-opaque-keys +openedx-filters django django-simple-history diff --git a/requirements/base.txt b/requirements/base.txt index e973b2207e..166890f8b4 100644 --- a/requirements/base.txt +++ b/requirements/base.txt @@ -12,11 +12,12 @@ backports-zoneinfo==0.2.1 ; python_version < "3.9" # via # -c requirements/constraints.txt # django + # djangorestframework bleach==6.1.0 # via -r requirements/base.in -boto3==1.34.72 +boto3==1.34.83 # via -r requirements/base.in -botocore==1.34.72 +botocore==1.34.83 # via # boto3 # s3transfer @@ -30,7 +31,7 @@ click==8.1.7 # via # code-annotations # edx-django-utils -code-annotations==1.7.0 +code-annotations==1.8.0 # via edx-toggles defusedxml==0.7.1 # via -r requirements/base.in @@ -47,11 +48,12 @@ django==4.2.11 # edx-submissions # edx-toggles # jsonfield + # openedx-filters django-crum==0.7.9 # via # edx-django-utils # edx-toggles -django-model-utils==4.4.0 +django-model-utils==4.5.0 # via # -r requirements/base.in # edx-submissions @@ -63,21 +65,21 @@ django-waffle==4.1.0 # via # edx-django-utils # edx-toggles -djangorestframework==3.14.0 +djangorestframework==3.15.1 # via # -r requirements/base.in # edx-submissions -edx-django-utils==5.11.0 +edx-django-utils==5.12.0 # via # -r requirements/base.in # edx-toggles -edx-i18n-tools==1.3.0 +edx-i18n-tools==1.5.0 # via -r requirements/base.in edx-opaque-keys==2.5.1 # via -r requirements/base.in -edx-submissions==3.6.0 +edx-submissions==3.7.0 # via -r requirements/base.in -edx-toggles==5.1.1 +edx-toggles==5.2.0 # via -r requirements/base.in fs==2.0.18 # via @@ -107,10 +109,11 @@ loremipsum==1.0.5 # -r requirements/base.in lxml==4.9.4 # via + # -c requirements/constraints.txt # -r requirements/base.in # edx-i18n-tools # xblock -mako==1.3.2 +mako==1.3.3 # via xblock markupsafe==2.1.5 # via @@ -119,6 +122,8 @@ markupsafe==2.1.5 # xblock newrelic==9.8.0 # via edx-django-utils +openedx-filters==1.8.0 + # via -r requirements/base.in path==13.1.0 # via # -c requirements/constraints.txt @@ -132,7 +137,7 @@ polib==1.2.0 # via edx-i18n-tools psutil==5.9.8 # via edx-django-utils -pycparser==2.21 +pycparser==2.22 # via cffi pymongo==3.13.0 # via edx-opaque-keys @@ -152,7 +157,6 @@ python-swiftclient==3.13.1 pytz==2024.1 # via # -r requirements/base.in - # djangorestframework # edx-submissions # fs # xblock @@ -183,7 +187,7 @@ stevedore==5.2.0 # edx-opaque-keys text-unidecode==1.3 # via python-slugify -typing-extensions==4.10.0 +typing-extensions==4.11.0 # via # asgiref # edx-opaque-keys @@ -195,7 +199,7 @@ voluptuous==0.14.2 # via # -c requirements/constraints.txt # -r requirements/base.in -web-fragments==2.1.0 +web-fragments==2.2.0 # via xblock webencodings==0.5.1 # via @@ -203,7 +207,7 @@ webencodings==0.5.1 # html5lib webob==1.8.7 # via xblock -xblock==2.0.0 +xblock==3.1.0 # via -r requirements/base.in # The following packages are considered to be unsafe in a requirements file: diff --git a/requirements/ci.txt b/requirements/ci.txt index ce31587de2..186554ff6c 100644 --- a/requirements/ci.txt +++ b/requirements/ci.txt @@ -30,7 +30,7 @@ distlib==0.3.8 # virtualenv docopt==0.6.2 # via coveralls -filelock==3.13.3 +filelock==3.13.4 # via # -r requirements/tox.txt # tox diff --git a/requirements/docs.txt b/requirements/docs.txt index fb3ee6bb15..27cc459218 100644 --- a/requirements/docs.txt +++ b/requirements/docs.txt @@ -89,7 +89,7 @@ sphinxcontrib-serializinghtml==1.1.5 # via sphinx tornado==6.4 # via livereload -typing-extensions==4.10.0 +typing-extensions==4.11.0 # via pydata-sphinx-theme urllib3==2.2.1 # via requests diff --git a/requirements/quality.txt b/requirements/quality.txt index 0d51dd80c5..c1283c39ab 100644 --- a/requirements/quality.txt +++ b/requirements/quality.txt @@ -30,6 +30,7 @@ backports-zoneinfo[tzdata]==0.2.1 ; python_version < "3.9" # -r requirements/test.txt # celery # django + # djangorestframework # kombu billiard==4.2.0 # via @@ -41,12 +42,12 @@ binaryornot==0.4.4 # cookiecutter bleach==6.1.0 # via -r requirements/test.txt -boto3==1.34.72 +boto3==1.34.83 # via # -r requirements/test.txt # fs-s3fs # moto -botocore==1.34.72 +botocore==1.34.83 # via # -r requirements/test.txt # boto3 @@ -102,7 +103,7 @@ click-repl==0.3.0 # via # -r requirements/test.txt # celery -code-annotations==1.7.0 +code-annotations==1.8.0 # via # -r requirements/test.txt # edx-lint @@ -148,13 +149,14 @@ django==4.2.11 # edx-submissions # edx-toggles # jsonfield + # openedx-filters # xblock-sdk django-crum==0.7.9 # via # -r requirements/test.txt # edx-django-utils # edx-toggles -django-model-utils==4.4.0 +django-model-utils==4.5.0 # via # -r requirements/test.txt # edx-submissions @@ -167,23 +169,23 @@ django-waffle==4.1.0 # -r requirements/test.txt # edx-django-utils # edx-toggles -djangorestframework==3.14.0 +djangorestframework==3.15.1 # via # -r requirements/test.txt # edx-submissions -edx-django-utils==5.11.0 +edx-django-utils==5.12.0 # via # -r requirements/test.txt # edx-toggles -edx-i18n-tools==1.3.0 +edx-i18n-tools==1.5.0 # via -r requirements/test.txt edx-lint==5.3.6 # via -r requirements/quality.in edx-opaque-keys==2.5.1 # via -r requirements/test.txt -edx-submissions==3.6.0 +edx-submissions==3.7.0 # via -r requirements/test.txt -edx-toggles==5.1.1 +edx-toggles==5.2.0 # via -r requirements/test.txt exceptiongroup==1.2.0 # via @@ -191,11 +193,11 @@ exceptiongroup==1.2.0 # pytest factory-boy==3.3.0 # via -r requirements/test.txt -faker==24.4.0 +faker==24.8.0 # via # -r requirements/test.txt # factory-boy -filelock==3.13.3 +filelock==3.13.4 # via # -r requirements/test.txt # tox @@ -243,7 +245,7 @@ jsonfield==3.1.0 # via # -r requirements/test.txt # edx-submissions -kombu==5.3.6 +kombu==5.3.7 # via # -r requirements/test.txt # celery @@ -255,11 +257,12 @@ loremipsum==1.0.5 # -r requirements/test.txt lxml==4.9.4 # via + # -c requirements/constraints.txt # -r requirements/test.txt # edx-i18n-tools # xblock # xblock-sdk -mako==1.3.2 +mako==1.3.3 # via # -r requirements/test.txt # xblock @@ -292,6 +295,8 @@ newrelic==9.8.0 # via # -r requirements/test.txt # edx-django-utils +openedx-filters==1.8.0 + # via -r requirements/test.txt packaging==24.0 # via # -r requirements/test.txt @@ -335,7 +340,7 @@ psutil==5.9.8 # edx-django-utils pycodestyle==2.11.1 # via -r requirements/quality.in -pycparser==2.21 +pycparser==2.22 # via # -r requirements/test.txt # cffi @@ -404,7 +409,6 @@ python-swiftclient==3.13.1 pytz==2024.1 # via # -r requirements/test.txt - # djangorestframework # edx-submissions # fs # xblock @@ -484,7 +488,7 @@ types-python-dateutil==2.9.0.20240316 # via # -r requirements/test.txt # arrow -typing-extensions==4.10.0 +typing-extensions==4.11.0 # via # -r requirements/test.txt # asgiref @@ -523,7 +527,7 @@ wcwidth==0.2.13 # via # -r requirements/test.txt # prompt-toolkit -web-fragments==2.1.0 +web-fragments==2.2.0 # via # -r requirements/test.txt # xblock @@ -538,21 +542,15 @@ webob==1.8.7 # -r requirements/test.txt # xblock # xblock-sdk -werkzeug==3.0.1 +werkzeug==3.0.2 # via # -r requirements/test.txt # moto -wrapt==1.11.2 +xblock==3.1.0 # via - # -c requirements/constraints.txt - # -r requirements/test.txt - # aws-xray-sdk -xblock==2.0.0 - # via - # -c requirements/constraints.txt # -r requirements/test.txt # xblock-sdk -xblock-sdk==0.9.0 +xblock-sdk==0.10.0 # via -r requirements/test.txt xmltodict==0.13.0 # via diff --git a/requirements/test-acceptance.txt b/requirements/test-acceptance.txt index 719e13509d..3aecc7b9cb 100644 --- a/requirements/test-acceptance.txt +++ b/requirements/test-acceptance.txt @@ -26,6 +26,7 @@ backports-zoneinfo[tzdata]==0.2.1 ; python_version < "3.9" # -r requirements/test.txt # celery # django + # djangorestframework # kombu billiard==4.2.0 # via @@ -37,12 +38,12 @@ binaryornot==0.4.4 # cookiecutter bleach==6.1.0 # via -r requirements/test.txt -boto3==1.34.72 +boto3==1.34.83 # via # -r requirements/test.txt # fs-s3fs # moto -botocore==1.34.72 +botocore==1.34.83 # via # -r requirements/test.txt # boto3 @@ -94,7 +95,7 @@ click-repl==0.3.0 # via # -r requirements/test.txt # celery -code-annotations==1.7.0 +code-annotations==1.8.0 # via # -r requirements/test.txt # edx-toggles @@ -138,13 +139,14 @@ django==4.2.11 # edx-submissions # edx-toggles # jsonfield + # openedx-filters # xblock-sdk django-crum==0.7.9 # via # -r requirements/test.txt # edx-django-utils # edx-toggles -django-model-utils==4.4.0 +django-model-utils==4.5.0 # via # -r requirements/test.txt # edx-submissions @@ -157,21 +159,21 @@ django-waffle==4.1.0 # -r requirements/test.txt # edx-django-utils # edx-toggles -djangorestframework==3.14.0 +djangorestframework==3.15.1 # via # -r requirements/test.txt # edx-submissions -edx-django-utils==5.11.0 +edx-django-utils==5.12.0 # via # -r requirements/test.txt # edx-toggles -edx-i18n-tools==1.3.0 +edx-i18n-tools==1.5.0 # via -r requirements/test.txt edx-opaque-keys==2.5.1 # via -r requirements/test.txt -edx-submissions==3.6.0 +edx-submissions==3.7.0 # via -r requirements/test.txt -edx-toggles==5.1.1 +edx-toggles==5.2.0 # via -r requirements/test.txt exceptiongroup==1.2.0 # via @@ -179,11 +181,11 @@ exceptiongroup==1.2.0 # pytest factory-boy==3.3.0 # via -r requirements/test.txt -faker==24.4.0 +faker==24.8.0 # via # -r requirements/test.txt # factory-boy -filelock==3.13.3 +filelock==3.13.4 # via # -r requirements/test.txt # tox @@ -229,7 +231,7 @@ jsonfield==3.1.0 # via # -r requirements/test.txt # edx-submissions -kombu==5.3.6 +kombu==5.3.7 # via # -r requirements/test.txt # celery @@ -241,11 +243,12 @@ loremipsum==1.0.5 # -r requirements/test.txt lxml==4.9.4 # via + # -c requirements/constraints.txt # -r requirements/test.txt # edx-i18n-tools # xblock # xblock-sdk -mako==1.3.2 +mako==1.3.3 # via # -r requirements/test.txt # xblock @@ -276,6 +279,8 @@ newrelic==9.8.0 # via # -r requirements/test.txt # edx-django-utils +openedx-filters==1.8.0 + # via -r requirements/test.txt packaging==24.0 # via # -r requirements/test.txt @@ -316,7 +321,7 @@ psutil==5.9.8 # via # -r requirements/test.txt # edx-django-utils -pycparser==2.21 +pycparser==2.22 # via # -r requirements/test.txt # cffi @@ -374,7 +379,6 @@ python-swiftclient==3.13.1 pytz==2024.1 # via # -r requirements/test.txt - # djangorestframework # edx-submissions # fs # xblock @@ -450,7 +454,7 @@ types-python-dateutil==2.9.0.20240316 # via # -r requirements/test.txt # arrow -typing-extensions==4.10.0 +typing-extensions==4.11.0 # via # -r requirements/test.txt # asgiref @@ -487,7 +491,7 @@ wcwidth==0.2.13 # via # -r requirements/test.txt # prompt-toolkit -web-fragments==2.1.0 +web-fragments==2.2.0 # via # -r requirements/test.txt # xblock @@ -502,21 +506,15 @@ webob==1.8.7 # -r requirements/test.txt # xblock # xblock-sdk -werkzeug==3.0.1 +werkzeug==3.0.2 # via # -r requirements/test.txt # moto -wrapt==1.11.2 +xblock==3.1.0 # via - # -c requirements/constraints.txt - # -r requirements/test.txt - # aws-xray-sdk -xblock==2.0.0 - # via - # -c requirements/constraints.txt # -r requirements/test.txt # xblock-sdk -xblock-sdk==0.9.0 +xblock-sdk==0.10.0 # via -r requirements/test.txt xmltodict==0.13.0 # via diff --git a/requirements/test.txt b/requirements/test.txt index 76d02d271e..6799e25413 100644 --- a/requirements/test.txt +++ b/requirements/test.txt @@ -22,6 +22,7 @@ backports-zoneinfo[tzdata]==0.2.1 ; python_version < "3.9" # -r requirements/base.txt # celery # django + # djangorestframework # kombu billiard==4.2.0 # via celery @@ -29,12 +30,12 @@ binaryornot==0.4.4 # via cookiecutter bleach==6.1.0 # via -r requirements/base.txt -boto3==1.34.72 +boto3==1.34.83 # via # -r requirements/base.txt # fs-s3fs # moto -botocore==1.34.72 +botocore==1.34.83 # via # -r requirements/base.txt # boto3 @@ -77,7 +78,7 @@ click-plugins==1.1.1 # via celery click-repl==0.3.0 # via celery -code-annotations==1.7.0 +code-annotations==1.8.0 # via # -r requirements/base.txt # edx-toggles @@ -111,13 +112,14 @@ distlib==0.3.8 # edx-submissions # edx-toggles # jsonfield + # openedx-filters # xblock-sdk django-crum==0.7.9 # via # -r requirements/base.txt # edx-django-utils # edx-toggles -django-model-utils==4.4.0 +django-model-utils==4.5.0 # via # -r requirements/base.txt # edx-submissions @@ -133,25 +135,25 @@ django-waffle==4.1.0 # via # -r requirements/base.txt # edx-submissions -edx-django-utils==5.11.0 +edx-django-utils==5.12.0 # via # -r requirements/base.txt # edx-toggles -edx-i18n-tools==1.3.0 +edx-i18n-tools==1.5.0 # via -r requirements/base.txt edx-opaque-keys==2.5.1 # via -r requirements/base.txt -edx-submissions==3.6.0 +edx-submissions==3.7.0 # via -r requirements/base.txt -edx-toggles==5.1.1 +edx-toggles==5.2.0 # via -r requirements/base.txt exceptiongroup==1.2.0 # via pytest factory-boy==3.3.0 # via -r requirements/test.in -faker==24.4.0 +faker==24.8.0 # via factory-boy -filelock==3.13.3 +filelock==3.13.4 # via # tox # virtualenv @@ -193,7 +195,7 @@ jsonfield==3.1.0 # via # -r requirements/base.txt # edx-submissions -kombu==5.3.6 +kombu==5.3.7 # via celery lazy==1.6 # via -r requirements/base.txt @@ -203,11 +205,12 @@ loremipsum==1.0.5 # -r requirements/base.txt lxml==4.9.4 # via + # -c requirements/constraints.txt # -r requirements/base.txt # edx-i18n-tools # xblock # xblock-sdk -mako==1.3.2 +mako==1.3.3 # via # -r requirements/base.txt # xblock @@ -234,6 +237,8 @@ newrelic==9.8.0 # via # -r requirements/base.txt # edx-django-utils +openedx-filters==1.8.0 + # via -r requirements/base.txt packaging==24.0 # via # pyproject-api @@ -269,7 +274,7 @@ psutil==5.9.8 # via # -r requirements/base.txt # edx-django-utils -pycparser==2.21 +pycparser==2.22 # via # -r requirements/base.txt # cffi @@ -318,7 +323,6 @@ python-swiftclient==3.13.1 pytz==2024.1 # via # -r requirements/base.txt - # djangorestframework # edx-submissions # fs # xblock @@ -387,7 +391,7 @@ tox==4.14.2 # via -r requirements/test.in types-python-dateutil==2.9.0.20240316 # via arrow -typing-extensions==4.10.0 +typing-extensions==4.11.0 # via # -r requirements/base.txt # asgiref @@ -418,7 +422,7 @@ voluptuous==0.14.2 # -r requirements/base.txt wcwidth==0.2.13 # via prompt-toolkit -web-fragments==2.1.0 +web-fragments==2.2.0 # via # -r requirements/base.txt # xblock @@ -433,18 +437,13 @@ webob==1.8.7 # -r requirements/base.txt # xblock # xblock-sdk -werkzeug==3.0.1 +werkzeug==3.0.2 # via moto -wrapt==1.11.2 +xblock==3.1.0 # via - # -c requirements/constraints.txt - # aws-xray-sdk -xblock==2.0.0 - # via - # -c requirements/constraints.txt # -r requirements/base.txt # xblock-sdk -xblock-sdk==0.9.0 +xblock-sdk==0.10.0 # via -r requirements/test.in xmltodict==0.13.0 # via moto diff --git a/requirements/tox.txt b/requirements/tox.txt index cc5293d666..246985fb98 100644 --- a/requirements/tox.txt +++ b/requirements/tox.txt @@ -12,7 +12,7 @@ colorama==0.4.6 # via tox distlib==0.3.8 # via virtualenv -filelock==3.13.3 +filelock==3.13.4 # via # tox # virtualenv