This is an automated email from the ASF dual-hosted git repository.

eschutho pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/superset.git


The following commit(s) were added to refs/heads/master by this push:
     new 855ca2228cb fix(query_context): raise 422 not 500 on malformed Jinja 
in Query datasource access check (#44011)
855ca2228cb is described below

commit 855ca2228cb698c9ceedd7d5001b52d6080ee0f4
Author: Elizabeth Thompson <[email protected]>
AuthorDate: Thu Sep 24 15:02:26 2026 -0700

    fix(query_context): raise 422 not 500 on malformed Jinja in Query 
datasource access check (#44011)
    
    Co-authored-by: Claude Opus 4.6 <[email protected]>
---
 superset/common/query_context_processor.py         |  7 +++++-
 .../common/test_query_context_processor.py         | 28 ++++++++++++++++++++++
 2 files changed, 34 insertions(+), 1 deletion(-)

diff --git a/superset/common/query_context_processor.py 
b/superset/common/query_context_processor.py
index eed87377bae..cb4e0694358 100644
--- a/superset/common/query_context_processor.py
+++ b/superset/common/query_context_processor.py
@@ -26,6 +26,7 @@ import pandas as pd
 import pyarrow as pa
 from flask import current_app
 from flask_babel import gettext as _
+from jinja2.exceptions import TemplateError
 from pandas.api.types import infer_dtype
 
 from superset.common.chart_data import ChartDataResultFormat
@@ -45,6 +46,7 @@ from superset.daos.chart import ChartDAO
 from superset.exceptions import (
     QueryObjectValidationError,
     SupersetException,
+    SupersetTemplateException,
 )
 from superset.explorables.base import Explorable
 from superset.extensions import cache_manager, security_manager
@@ -937,7 +939,10 @@ class QueryContextProcessor:
         # come first to avoid rendering caller-supplied input for a resource 
the
         # caller is not allowed to access.
         if self._qc_datasource.type == DatasourceType.QUERY:
-            security_manager.raise_for_access(query=self._qc_datasource)
+            try:
+                security_manager.raise_for_access(query=self._qc_datasource)
+            except TemplateError as ex:
+                raise SupersetTemplateException(str(ex)) from ex
         else:
             
security_manager.raise_for_access(query_context=self._query_context)
 
diff --git a/tests/unit_tests/common/test_query_context_processor.py 
b/tests/unit_tests/common/test_query_context_processor.py
index 117741bb372..b35c51cfe73 100644
--- a/tests/unit_tests/common/test_query_context_processor.py
+++ b/tests/unit_tests/common/test_query_context_processor.py
@@ -2220,6 +2220,34 @@ def 
test_raise_for_access_evaluates_access_before_validate():
     query.validate.assert_not_called()
 
 
+def test_raise_for_access_wraps_template_error_for_query_datasource():
+    """
+    When the datasource is a SQL Lab Query and raise_for_access() Jinja-renders
+    malformed SQL, the raw jinja2 TemplateError must be wrapped in
+    SupersetTemplateException (422) instead of leaking as an unhandled 500.
+    """
+    from jinja2.exceptions import TemplateSyntaxError
+
+    from superset.exceptions import SupersetTemplateException
+    from superset.utils.core import DatasourceType
+
+    query = MagicMock()
+    query_context = MagicMock()
+    query_context.queries = [query]
+    query_context.datasource.type = DatasourceType.QUERY
+
+    processor = QueryContextProcessor(query_context)
+
+    with patch(
+        
"superset.common.query_context_processor.security_manager.raise_for_access",
+        side_effect=TemplateSyntaxError("unexpected end of template", 
lineno=1),
+    ):
+        with pytest.raises(SupersetTemplateException):
+            processor.raise_for_access()
+
+    query.validate.assert_not_called()
+
+
 def test_grouping_sets_fallback_handles_adhoc_and_physical_columns() -> None:
     """
     The fallback used on engines without native GROUPING SETS support must

Reply via email to