Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve error for missing (Translate)CustomTagBlock template #35829

Open
kdmccormick opened this issue Nov 12, 2024 · 4 comments
Open

Improve error for missing (Translate)CustomTagBlock template #35829

kdmccormick opened this issue Nov 12, 2024 · 4 comments
Labels
good first issue A good task for a newcomer to start with help wanted Ready to be picked up by anyone in the community

Comments

@kdmccormick
Copy link
Member

kdmccormick commented Nov 12, 2024

Currently, when an instance of a CustomTagBlock (or of its wrapper block, TranslateCustomTagBlock) does not have a matching template in the OLX at course/custom_tags/TAGNAME, a very opaque and confusing error message is displayed in Studio and in LMS/CMS logs.

We could make this situation better for course author and developers by explaining which template file is missing. It would be good if the Studio error was displayed in such a way that the block could still be edited or deleted.

(In addition to this, we would like to add an instance of this block to the test course)


(ORIGINAL ERROR REPORT)

We are trying to figure out the last time that CustomTagBlock and TranslateCustomTagBlock worked in LMS and in Studio. (UPDATE: They actually work in master. See my comment below).

@farhan first noticed this as an existing issue while trying to convert customtag's Sass to CSS. The errors he saw on CustomTagBlock are:

2024-11-06 22:09:43 Traceback (most recent call last):
2024-11-06 22:09:43   File "/openedx/edx-platform/cms/djangoapps/contentstore/views/preview.py", line 351, in get_preview_fragment
2024-11-06 22:09:43     fragment = block.render(preview_view, context)
2024-11-06 22:09:43                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/venv/lib/python3.11/site-packages/xblock/core.py", line 818, in render
2024-11-06 22:09:43     return self.runtime.render(self, view, context)
2024-11-06 22:09:43            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/edx-platform/xmodule/x_module.py", line 994, in render
2024-11-06 22:09:43     return super().render(block, view_name, context=context)
2024-11-06 22:09:43            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/venv/lib/python3.11/site-packages/xblock/runtime.py", line 823, in render
2024-11-06 22:09:43     frag = view_fn(context)
2024-11-06 22:09:43            ^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/edx-platform/xmodule/vertical_block.py", line 224, in author_view
2024-11-06 22:09:43     self.render_children(context, fragment, can_reorder=True, can_add=True)
2024-11-06 22:09:43   File "/openedx/edx-platform/xmodule/studio_editable.py", line 30, in render_children
2024-11-06 22:09:43     rendered_child = child.render(StudioEditableBlock.get_preview_view_name(child), context)
2024-11-06 22:09:43                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/venv/lib/python3.11/site-packages/xblock/core.py", line 818, in render
2024-11-06 22:09:43     return self.runtime.render(self, view, context)
2024-11-06 22:09:43            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/edx-platform/xmodule/x_module.py", line 994, in render
2024-11-06 22:09:43     return super().render(block, view_name, context=context)
2024-11-06 22:09:43            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/venv/lib/python3.11/site-packages/xblock/runtime.py", line 823, in render
2024-11-06 22:09:43     frag = view_fn(context)
2024-11-06 22:09:43            ^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/edx-platform/xmodule/template_block.py", line 114, in student_view
2024-11-06 22:09:43     fragment.add_content(self.rendered_html)
2024-11-06 22:09:43                          ^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/edx-platform/xmodule/template_block.py", line 107, in rendered_html
2024-11-06 22:09:43     return self.render_template(self.runtime, self.data)
2024-11-06 22:09:43            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/edx-platform/xmodule/template_block.py", line 81, in render_template
2024-11-06 22:09:43     xmltree = etree.fromstring(xml_data)
2024-11-06 22:09:43               ^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "/openedx/edx-platform/openedx/core/lib/safe_lxml/xmlparser.py", line 128, in fromstring
2024-11-06 22:09:43     rootelement = _etree.fromstring(text, parser, base_url=base_url)
2024-11-06 22:09:43                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
2024-11-06 22:09:43   File "src/lxml/etree.pyx", line 3264, in lxml.etree.fromstring
2024-11-06 22:09:43   File "src/lxml/parser.pxi", line 1916, in lxml.etree._parseMemoryDocument
2024-11-06 22:09:43   File "src/lxml/parser.pxi", line 1796, in lxml.etree._parseDoc
2024-11-06 22:09:43   File "src/lxml/parser.pxi", line 1085, in lxml.etree._BaseParser._parseUnicodeDoc
2024-11-06 22:09:43   File "src/lxml/parser.pxi", line 618, in lxml.etree._ParserContext._handleParseResultDoc
2024-11-06 22:09:43   File "src/lxml/parser.pxi", line 728, in lxml.etree._handleParseResult
2024-11-06 22:09:43   File "src/lxml/parser.pxi", line 657, in lxml.etree._raiseParseError
2024-11-06 22:09:43   File "<string>", line 1
2024-11-06 22:09:43 lxml.etree.XMLSyntaxError: Document is empty, line 1, column 1
2024-11-06 22:09:43 [06/Nov/2024 17:09:43] "GET /xblock/block-v1:edx+3+3+type@vertical+block@44306a226476427cb4ad0d9057fc3795/container_preview?_=1730912983221 HTTP/1.1" 200 631

@kdmccormick sees these NoSuchViewError for TranslateCustomTagBlock, both in LMS (these logs) and CMS (not shown):

lms-1  | 2024-11-12 16:31:52,646 ERROR 22 [django.request] [user None] [ip None] log.py:241 - Internal Server Error: /xblock/block-v1:OpenedX+TestX+TestCourse+type@vertical+block@241c59c55fc24def97bf5ec8a22ed5a4
lms-1  | Traceback (most recent call last):
lms-1  |   File "/openedx/venv/lib/python3.11/site-packages/django/core/handlers/exception.py", line 55, in inner
lms-1  |     response = get_response(request)
lms-1  |                ^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/venv/lib/python3.11/site-packages/django/core/handlers/base.py", line 197, in _get_response
lms-1  |     response = wrapped_callback(request, *callback_args, **callback_kwargs)
lms-1  |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/venv/lib/python3.11/site-packages/django/views/decorators/http.py", line 43, in inner
lms-1  |     return func(request, *args, **kwargs)
lms-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/edx-platform/common/djangoapps/util/views.py", line 63, in inner
lms-1  |     response = view_func(request, *args, **kwargs)
lms-1  |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/venv/lib/python3.11/site-packages/django/views/decorators/clickjacking.py", line 58, in wrapper_view
lms-1  |     resp = view_func(*args, **kwargs)
lms-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/venv/lib/python3.11/site-packages/django/utils/decorators.py", line 134, in _wrapper_view
lms-1  |     response = view_func(request, *args, **kwargs)
lms-1  |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/edx-platform/lms/djangoapps/courseware/views/views.py", line 1708, in render_xblock
lms-1  |     fragment = block.render(requested_view, context=student_view_context)
lms-1  |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/mnt/xblock/xblock/core.py", line 818, in render
lms-1  |     return self.runtime.render(self, view, context)
lms-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/edx-platform/xmodule/x_module.py", line 994, in render
lms-1  |     return super().render(block, view_name, context=context)
lms-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/mnt/xblock/xblock/runtime.py", line 823, in render
lms-1  |     frag = view_fn(context)
lms-1  |            ^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/edx-platform/xmodule/vertical_block.py", line 204, in student_view
lms-1  |     return self._student_or_public_view(context, STUDENT_VIEW)
lms-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/edx-platform/xmodule/vertical_block.py", line 131, in _student_or_public_view
lms-1  |     rendered_child = child.render(view, child_block_context)
lms-1  |                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/mnt/xblock/xblock/core.py", line 818, in render
lms-1  |     return self.runtime.render(self, view, context)
lms-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/openedx/edx-platform/xmodule/x_module.py", line 994, in render
lms-1  |     return super().render(block, view_name, context=context)
lms-1  |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lms-1  |   File "/mnt/xblock/xblock/runtime.py", line 820, in render
lms-1  |     raise NoSuchViewError(block, view_name)
lms-1  | xblock.exceptions.NoSuchViewError

In Studio, this looks like:
image

When was the last time this block worked?

Potentially relevant PRs:

@kdmccormick
Copy link
Member Author

Update: I was able to demonstrate that the blocks do work on master and in Redwood. It just takes manual OLX editing in order to set up each custom_tag impl that you want to use.

Essentially, a <customtag impl="foo" ...> block tells the platform to look at the file course/custom_tags/foo and render the template with args .... If foo is missing, then Studio raises an unhelpful error (which is what @farhan and I saw before).

The TranslateCustomTagBlock is just a thin wrapper that turns <book ...>, <videodev ...>, etc. into <customtag impl="book" ...> etc.

This is all spelled out in docstrings but it would be good to:

  • improve the error message
  • add sample OLX to the Open edX Test Course

Sample OLX: customtags.tar.gz

Here it is in Redwood Studio:

image

And Redwood LMS:

image

@kdmccormick kdmccormick changed the title CustomTagBlock and TranslateCustomTagBlock are broken? Improve errors when (Translate)CustomTagBlock template is missing Nov 12, 2024
@kdmccormick kdmccormick changed the title Improve errors when (Translate)CustomTagBlock template is missing Improve error for missing (Translate)CustomTagBlock template Nov 12, 2024
@kdmccormick kdmccormick added help wanted Ready to be picked up by anyone in the community good first issue A good task for a newcomer to start with labels Nov 12, 2024
@marcotuts
Copy link
Contributor

What is the value / potential use for this block I am still not fully sure I follow the value of this tag / block. (Anybody know of its use previously? )

@kdmccormick
Copy link
Member Author

kdmccormick commented Nov 13, 2024

@marcotuts It theoretically provides some convenience and semantic value for course authors working with HTML. An author can say in one place (the template): "given inputs X Y and Z, this is the HTML to display a Blarg component ", and then they can reuse that Blarg template throughout the course with any X/Y/Z inputs they want. If they ever want Blarg to render differently, they only have to change the template, not all the usages.

I would not propose this as a new Core feature today, but we should keep it working as part of our longstanding goal of Do Not Break OLX Content.

The context to this bug report is actually that we are extracting a bunch of XBlocks into plugins, including this one. Once extracted, it'll be extremely low-cost to maintain.

@marcotuts
Copy link
Contributor

Aha interesting! Tiny MCE actually has this templates idea built into itself as a plugin tool

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
good first issue A good task for a newcomer to start with help wanted Ready to be picked up by anyone in the community
Projects
None yet
Development

No branches or pull requests

2 participants