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

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


The following commit(s) were added to refs/heads/master by this push:
     new 0472c11  fix: Add deprecated fields to QueryObject schema (#9579)
0472c11 is described below

commit 0472c11157450de50cd97e36e4459bb2c9c4e5e4
Author: Ville Brofeldt <33317356+ville...@users.noreply.github.com>
AuthorDate: Sat Apr 18 20:28:57 2020 +0300

    fix: Add deprecated fields to QueryObject schema (#9579)
    
    * fix: Add deprecated fields to QueryObject schema
    
    * linting
---
 superset/charts/schemas.py          | 34 ++++++++++++++++++++++++++++++++++
 superset/common/query_object.py     | 26 +++++++++++++++++++++++++-
 superset/connectors/druid/models.py |  4 ++--
 tests/charts/api_tests.py           | 15 ++++++++++++---
 4 files changed, 73 insertions(+), 6 deletions(-)

diff --git a/superset/charts/schemas.py b/superset/charts/schemas.py
index 0a7035c..49d0480 100644
--- a/superset/charts/schemas.py
+++ b/superset/charts/schemas.py
@@ -393,6 +393,19 @@ class ChartDataExtrasSchema(Schema):
         enum=["today", "now"],
         required=False,
     )
+    where = fields.String(
+        description="WHERE clause to be added to queries using AND operator.",
+        required=False,
+    )
+    having = fields.String(
+        description="HAVING clause to be added to aggregate queries using "
+        "AND operator.",
+        required=False,
+    )
+    having_druid = fields.String(
+        description="HAVING filters to be added to legacy Druid datasource 
queries.",
+        required=False,
+    )
 
 
 class ChartDataQueryObjectSchema(Schema):
@@ -484,6 +497,27 @@ class ChartDataQueryObjectSchema(Schema):
         required=False,
         example=[["my_col_1", False], ["my_col_2", True]],
     )
+    where = fields.String(
+        description="WHERE clause to be added to queries using AND operator."
+        "This field is deprecated, and should be passed to `extras`.",
+        required=False,
+        deprecated=True,
+    )
+    having = fields.String(
+        description="HAVING clause to be added to aggregate queries using "
+        "AND operator. This field is deprecated, and should be passed "
+        "to `extras`.",
+        required=False,
+        deprecated=True,
+    )
+    having_filters = fields.List(
+        fields.Dict(),
+        description="HAVING filters to be added to legacy Druid datasource 
queries. "
+        "This field is deprecated, and should be passed to `extras` "
+        "as `filters_druid`.",
+        required=False,
+        deprecated=True,
+    )
 
 
 class ChartDataDatasourceSchema(Schema):
diff --git a/superset/common/query_object.py b/superset/common/query_object.py
index 31a6241..0a83ef7 100644
--- a/superset/common/query_object.py
+++ b/superset/common/query_object.py
@@ -18,7 +18,7 @@
 import hashlib
 import logging
 from datetime import datetime, timedelta
-from typing import Any, Dict, List, Optional, Union
+from typing import Any, Dict, List, NamedTuple, Optional, Union
 
 import simplejson as json
 from flask_babel import gettext as _
@@ -35,6 +35,18 @@ logger = logging.getLogger(__name__)
 #  https://github.com/python/mypy/issues/5288
 
 
+class DeprecatedExtrasField(NamedTuple):
+    name: str
+    extras_name: str
+
+
+DEPRECATED_EXTRAS_FIELDS = (
+    DeprecatedExtrasField(name="where", extras_name="where"),
+    DeprecatedExtrasField(name="having", extras_name="having"),
+    DeprecatedExtrasField(name="having_filters", extras_name="having_druid"),
+)
+
+
 class QueryObject:
     """
     The query object's schema matches the interfaces of DB connectors like sqla
@@ -75,6 +87,7 @@ class QueryObject:
         columns: Optional[List[str]] = None,
         orderby: Optional[List[List]] = None,
         post_processing: Optional[List[Dict[str, Any]]] = None,
+        **kwargs: Any,
     ):
         extras = extras or {}
         is_sip_38 = is_feature_enabled("SIP_38_VIZ_REARCHITECTURE")
@@ -124,6 +137,17 @@ class QueryObject:
 
         self.orderby = orderby or []
 
+        # move deprecated fields to extras
+        for field in DEPRECATED_EXTRAS_FIELDS:
+            if field.name in kwargs:
+                logger.warning(
+                    f"The field `{field.name} is deprecated, and should be "
+                    f"passed to `extras` via the `{field.extras_name}` 
property"
+                )
+                value = kwargs[field.name]
+                if value:
+                    self.extras[field.extras_name] = value
+
     def to_dict(self) -> Dict[str, Any]:
         query_object_dict = {
             "granularity": self.granularity,
diff --git a/superset/connectors/druid/models.py 
b/superset/connectors/druid/models.py
index 20dd732..8d4aeb1 100644
--- a/superset/connectors/druid/models.py
+++ b/superset/connectors/druid/models.py
@@ -24,7 +24,7 @@ from copy import deepcopy
 from datetime import datetime, timedelta
 from distutils.version import LooseVersion
 from multiprocessing.pool import ThreadPool
-from typing import cast, Dict, Iterable, List, Optional, Set, Tuple, Union
+from typing import Any, cast, Dict, Iterable, List, Optional, Set, Tuple, Union
 
 import pandas as pd
 import sqlalchemy as sa
@@ -1639,7 +1639,7 @@ class DruidDatasource(Model, BaseDatasource):
 
         return cond
 
-    def get_having_filters(self, raw_filters: List[Dict]) -> "Having":
+    def get_having_filters(self, raw_filters: List[Dict[str, Any]]) -> 
"Having":
         filters = None
         reversed_op_map = {
             FilterOperationType.NOT_EQUALS.value: 
FilterOperationType.EQUALS.value,
diff --git a/tests/charts/api_tests.py b/tests/charts/api_tests.py
index 1f64bae..6a78f30 100644
--- a/tests/charts/api_tests.py
+++ b/tests/charts/api_tests.py
@@ -76,11 +76,21 @@ class ChartApiTests(SupersetTestCase, 
ApiOwnersTestCaseMixin):
             "datasource": {"id": slc.datasource_id, "type": 
slc.datasource_type},
             "queries": [
                 {
+                    "extras": {"where": ""},
                     "granularity": "ds",
                     "groupby": ["name"],
+                    "is_timeseries": False,
                     "metrics": [{"label": "sum__num"}],
-                    "filters": [],
+                    "order_desc": True,
+                    "orderby": [],
                     "row_limit": 100,
+                    "time_range": "100 years ago : now",
+                    "timeseries_limit": 0,
+                    "timeseries_limit_metric": None,
+                    "filters": [{"col": "gender", "op": "==", "val": "boy"}],
+                    "having": "",
+                    "having_filters": [],
+                    "where": "",
                 }
             ],
         }
@@ -660,8 +670,7 @@ class ChartApiTests(SupersetTestCase, 
ApiOwnersTestCaseMixin):
         self.assertEqual(data["result"][0]["rowcount"], 100)
 
     def test_invalid_chart_data(self):
-        """
-            Query API: Test chart data query
+        """Query API: Test chart data query with invalid schema
         """
         self.login(username="admin")
         query_context = self._get_query_context()

Reply via email to