From b49d93574368fab2ad9157ecea3d48234541f670 Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 12:58:24 -0800 Subject: [PATCH 1/9] api changes needed for sqllab to explore improvements --- superset/datasets/api.py | 32 ++++++++++++++------------- superset/datasets/commands/update.py | 33 +++++++++++++++++++--------- superset/datasets/dao.py | 15 +++++++++++-- 3 files changed, 53 insertions(+), 27 deletions(-) diff --git a/superset/datasets/api.py b/superset/datasets/api.py index e5ddae5d01f88..a2f10f92c038a 100644 --- a/superset/datasets/api.py +++ b/superset/datasets/api.py @@ -27,9 +27,8 @@ from flask_babel import ngettext from marshmallow import ValidationError -from superset import event_logger, is_feature_enabled +from superset import is_feature_enabled from superset.commands.exceptions import CommandInvalidError -from superset.commands.importers.v1.utils import remove_root from superset.connectors.sqla.models import SqlaTable from superset.constants import RouteMethod from superset.databases.filters import DatabaseFilter @@ -41,7 +40,6 @@ DatasetCreateFailedError, DatasetDeleteFailedError, DatasetForbiddenError, - DatasetImportError, DatasetInvalidError, DatasetNotFoundError, DatasetRefreshFailedError, @@ -183,7 +181,6 @@ class DatasetRestApi(BaseSupersetModelRestApi): @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def post(self) -> Response: """Creates a new Dataset --- @@ -240,7 +237,6 @@ def post(self) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def put(self, pk: int) -> Response: """Changes a Dataset --- @@ -252,6 +248,10 @@ def put(self, pk: int) -> Response: schema: type: integer name: pk + - in: path + schema: + type: bool + name: override_column requestBody: description: Dataset schema required: true @@ -284,6 +284,11 @@ def put(self, pk: int) -> Response: 500: $ref: '#/components/responses/500' """ + override_column = ( + request.args["override_column"] + if request.args.get("override_column") + else False + ) if not request.is_json: return self.response_400(message="Request is not JSON") try: @@ -292,7 +297,9 @@ def put(self, pk: int) -> Response: except ValidationError as error: return self.response_400(message=error.messages) try: - changed_model = UpdateDatasetCommand(g.user, pk, item).run() + changed_model = UpdateDatasetCommand( + g.user, pk, item, override_column + ).run() response = self.response(200, id=changed_model.id, result=item) except DatasetNotFoundError: response = self.response_404() @@ -311,7 +318,6 @@ def put(self, pk: int) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def delete(self, pk: int) -> Response: """Deletes a Dataset --- @@ -362,7 +368,6 @@ def delete(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_export_ids_schema) - @event_logger.log_this_with_context(log_to_statsd=False) def export(self, **kwargs: Any) -> Response: """Export datasets --- @@ -438,7 +443,6 @@ def export(self, **kwargs: Any) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def refresh(self, pk: int) -> Response: """Refresh a Dataset --- @@ -488,7 +492,6 @@ def refresh(self, pk: int) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def related_objects(self, pk: int) -> Response: """Get charts and dashboards count associated to a dataset --- @@ -547,7 +550,6 @@ def related_objects(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_delete_ids_schema) - @event_logger.log_this_with_context(log_to_statsd=False) def bulk_delete(self, **kwargs: Any) -> Response: """Delete bulk Datasets --- @@ -607,7 +609,7 @@ def bulk_delete(self, **kwargs: Any) -> Response: @safe @statsd_metrics def import_(self) -> Response: - """Import dataset(s) with associated databases + """Import dataset (s) with associated databases --- post: requestBody: @@ -635,12 +637,12 @@ def import_(self) -> Response: 500: $ref: '#/components/responses/500' """ - upload = request.files.get("formData") + upload = request.files.get("file") if not upload: return self.response_400() with ZipFile(upload) as bundle: contents = { - remove_root(file_name): bundle.read(file_name).decode() + file_name: bundle.read(file_name).decode() for file_name in bundle.namelist() } @@ -651,6 +653,6 @@ def import_(self) -> Response: except CommandInvalidError as exc: logger.warning("Import dataset failed") return self.response_422(message=exc.normalized_messages()) - except DatasetImportError as exc: + except Exception as exc: # pylint: disable=broad-except logger.exception("Import dataset failed") return self.response_500(message=str(exc)) diff --git a/superset/datasets/commands/update.py b/superset/datasets/commands/update.py index dfc3986c09f22..809720ed6ab39 100644 --- a/superset/datasets/commands/update.py +++ b/superset/datasets/commands/update.py @@ -16,7 +16,7 @@ # under the License. import logging from collections import Counter -from typing import Any, Dict, List, Optional +from typing import Any, Dict, List, Optional, Union from flask_appbuilder.models.sqla import Model from flask_appbuilder.security.sqla.models import User @@ -48,17 +48,28 @@ class UpdateDatasetCommand(BaseCommand): - def __init__(self, user: User, model_id: int, data: Dict[str, Any]): + def __init__( + self, + user: User, + model_id: int, + data: Dict[str, Any], + override_columns: Union[bool, Any, None] = False, + ): self._actor = user self._model_id = model_id self._properties = data.copy() self._model: Optional[SqlaTable] = None + self.override_columns = override_columns def run(self) -> Model: self.validate() if self._model: try: - dataset = DatasetDAO.update(self._model, self._properties) + dataset = DatasetDAO.update( + self._model, + self._properties, + override_columns=self.override_columns, + ) return dataset except DAOUpdateFailedError as ex: logger.exception(ex.exception) @@ -123,14 +134,16 @@ def _validate_columns( ] if not DatasetDAO.validate_columns_exist(self._model_id, columns_ids): exceptions.append(DatasetColumnNotFoundValidationError()) + # validate new column names uniqueness - columns_names: List[str] = [ - column["column_name"] for column in columns if "id" not in column - ] - if not DatasetDAO.validate_columns_uniqueness( - self._model_id, columns_names - ): - exceptions.append(DatasetColumnsExistsValidationError()) + if not self.override_columns: + columns_names: List[str] = [ + column["column_name"] for column in columns if "id" not in column + ] + if not DatasetDAO.validate_columns_uniqueness( + self._model_id, columns_names + ): + exceptions.append(DatasetColumnsExistsValidationError()) def _validate_metrics( self, metrics: List[Dict[str, Any]], exceptions: List[ValidationError] diff --git a/superset/datasets/dao.py b/superset/datasets/dao.py index 3b905f450cd0f..22526e92079bf 100644 --- a/superset/datasets/dao.py +++ b/superset/datasets/dao.py @@ -15,7 +15,7 @@ # specific language governing permissions and limitations # under the License. import logging -from typing import Any, Dict, List, Optional +from typing import Any, Dict, List, Optional, Union from flask import current_app from sqlalchemy.exc import SQLAlchemyError @@ -144,7 +144,11 @@ def validate_metrics_uniqueness(dataset_id: int, metrics_names: List[str]) -> bo @classmethod def update( - cls, model: SqlaTable, properties: Dict[str, Any], commit: bool = True + cls, + model: SqlaTable, + properties: Dict[str, Any], + commit: bool = True, + override_columns: Union[bool, Any, None] = False, ) -> Optional[SqlaTable]: """ Updates a Dataset model on the metadata DB @@ -175,6 +179,13 @@ def update( new_metrics.append(metric_obj) properties["metrics"] = new_metrics + if override_columns: + # remove columns initially for full refresh + original_properties = properties["columns"] + properties["columns"] = [] + super().update(model, properties, commit=commit) + properties["columns"] = original_properties + return super().update(model, properties, commit=commit) @classmethod From 354eb123640ad9dea78a36d3a10cc2c47e94ce95 Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 13:06:13 -0800 Subject: [PATCH 2/9] fix discrepancies --- superset/datasets/api.py | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/superset/datasets/api.py b/superset/datasets/api.py index a2f10f92c038a..c2db5b8b088af 100644 --- a/superset/datasets/api.py +++ b/superset/datasets/api.py @@ -27,8 +27,9 @@ from flask_babel import ngettext from marshmallow import ValidationError -from superset import is_feature_enabled +from superset import event_logger, is_feature_enabled from superset.commands.exceptions import CommandInvalidError +from superset.commands.importers.v1.utils import remove_root from superset.connectors.sqla.models import SqlaTable from superset.constants import RouteMethod from superset.databases.filters import DatabaseFilter @@ -40,6 +41,7 @@ DatasetCreateFailedError, DatasetDeleteFailedError, DatasetForbiddenError, + DatasetImportError, DatasetInvalidError, DatasetNotFoundError, DatasetRefreshFailedError, @@ -181,6 +183,7 @@ class DatasetRestApi(BaseSupersetModelRestApi): @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def post(self) -> Response: """Creates a new Dataset --- @@ -237,6 +240,7 @@ def post(self) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def put(self, pk: int) -> Response: """Changes a Dataset --- @@ -318,6 +322,7 @@ def put(self, pk: int) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def delete(self, pk: int) -> Response: """Deletes a Dataset --- @@ -368,6 +373,7 @@ def delete(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_export_ids_schema) + @event_logger.log_this_with_context(log_to_statsd=False) def export(self, **kwargs: Any) -> Response: """Export datasets --- @@ -443,6 +449,7 @@ def export(self, **kwargs: Any) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def refresh(self, pk: int) -> Response: """Refresh a Dataset --- @@ -492,6 +499,7 @@ def refresh(self, pk: int) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def related_objects(self, pk: int) -> Response: """Get charts and dashboards count associated to a dataset --- @@ -550,6 +558,7 @@ def related_objects(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_delete_ids_schema) + @event_logger.log_this_with_context(log_to_statsd=False) def bulk_delete(self, **kwargs: Any) -> Response: """Delete bulk Datasets --- @@ -608,8 +617,9 @@ def bulk_delete(self, **kwargs: Any) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def import_(self) -> Response: - """Import dataset (s) with associated databases + """Import dataset(s) with associated databases --- post: requestBody: From 178a5b605cc059ebf77d362289a3cfe01b0a18ce Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 13:08:47 -0800 Subject: [PATCH 3/9] more diff --- superset/datasets/api.py | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/superset/datasets/api.py b/superset/datasets/api.py index c2db5b8b088af..ee67c40329ded 100644 --- a/superset/datasets/api.py +++ b/superset/datasets/api.py @@ -617,7 +617,6 @@ def bulk_delete(self, **kwargs: Any) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def import_(self) -> Response: """Import dataset(s) with associated databases --- @@ -647,12 +646,12 @@ def import_(self) -> Response: 500: $ref: '#/components/responses/500' """ - upload = request.files.get("file") + upload = request.files.get("formData") if not upload: return self.response_400() with ZipFile(upload) as bundle: contents = { - file_name: bundle.read(file_name).decode() + remove_root(file_name): bundle.read(file_name).decode() for file_name in bundle.namelist() } @@ -663,6 +662,6 @@ def import_(self) -> Response: except CommandInvalidError as exc: logger.warning("Import dataset failed") return self.response_422(message=exc.normalized_messages()) - except Exception as exc: # pylint: disable=broad-except + except DatasetImportError as exc: logger.exception("Import dataset failed") return self.response_500(message=str(exc)) From 0b2d6c92caaf9f9791b69b71ba9041949b950db3 Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 13:10:55 -0800 Subject: [PATCH 4/9] changes --- superset/datasets/api.py | 28 ++++++++++------------------ 1 file changed, 10 insertions(+), 18 deletions(-) diff --git a/superset/datasets/api.py b/superset/datasets/api.py index ee67c40329ded..5a38ea5c78fd1 100644 --- a/superset/datasets/api.py +++ b/superset/datasets/api.py @@ -16,6 +16,7 @@ # under the License. import logging from datetime import datetime +from distutils.util import strtobool from io import BytesIO from typing import Any from zipfile import ZipFile @@ -27,9 +28,8 @@ from flask_babel import ngettext from marshmallow import ValidationError -from superset import event_logger, is_feature_enabled +from superset import is_feature_enabled from superset.commands.exceptions import CommandInvalidError -from superset.commands.importers.v1.utils import remove_root from superset.connectors.sqla.models import SqlaTable from superset.constants import RouteMethod from superset.databases.filters import DatabaseFilter @@ -41,7 +41,6 @@ DatasetCreateFailedError, DatasetDeleteFailedError, DatasetForbiddenError, - DatasetImportError, DatasetInvalidError, DatasetNotFoundError, DatasetRefreshFailedError, @@ -183,7 +182,6 @@ class DatasetRestApi(BaseSupersetModelRestApi): @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def post(self) -> Response: """Creates a new Dataset --- @@ -240,7 +238,6 @@ def post(self) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def put(self, pk: int) -> Response: """Changes a Dataset --- @@ -288,9 +285,9 @@ def put(self, pk: int) -> Response: 500: $ref: '#/components/responses/500' """ - override_column = ( - request.args["override_column"] - if request.args.get("override_column") + override_columns = ( + bool(strtobool(request.args["override_columns"])) + if "override_columns" in request.args else False ) if not request.is_json: @@ -302,7 +299,7 @@ def put(self, pk: int) -> Response: return self.response_400(message=error.messages) try: changed_model = UpdateDatasetCommand( - g.user, pk, item, override_column + g.user, pk, item, override_columns ).run() response = self.response(200, id=changed_model.id, result=item) except DatasetNotFoundError: @@ -322,7 +319,6 @@ def put(self, pk: int) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def delete(self, pk: int) -> Response: """Deletes a Dataset --- @@ -373,7 +369,6 @@ def delete(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_export_ids_schema) - @event_logger.log_this_with_context(log_to_statsd=False) def export(self, **kwargs: Any) -> Response: """Export datasets --- @@ -449,7 +444,6 @@ def export(self, **kwargs: Any) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def refresh(self, pk: int) -> Response: """Refresh a Dataset --- @@ -499,7 +493,6 @@ def refresh(self, pk: int) -> Response: @protect() @safe @statsd_metrics - @event_logger.log_this_with_context(log_to_statsd=False) def related_objects(self, pk: int) -> Response: """Get charts and dashboards count associated to a dataset --- @@ -558,7 +551,6 @@ def related_objects(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_delete_ids_schema) - @event_logger.log_this_with_context(log_to_statsd=False) def bulk_delete(self, **kwargs: Any) -> Response: """Delete bulk Datasets --- @@ -618,7 +610,7 @@ def bulk_delete(self, **kwargs: Any) -> Response: @safe @statsd_metrics def import_(self) -> Response: - """Import dataset(s) with associated databases + """Import dataset (s) with associated databases --- post: requestBody: @@ -646,12 +638,12 @@ def import_(self) -> Response: 500: $ref: '#/components/responses/500' """ - upload = request.files.get("formData") + upload = request.files.get("file") if not upload: return self.response_400() with ZipFile(upload) as bundle: contents = { - remove_root(file_name): bundle.read(file_name).decode() + file_name: bundle.read(file_name).decode() for file_name in bundle.namelist() } @@ -662,6 +654,6 @@ def import_(self) -> Response: except CommandInvalidError as exc: logger.warning("Import dataset failed") return self.response_422(message=exc.normalized_messages()) - except DatasetImportError as exc: + except Exception as exc: # pylint: disable=broad-except logger.exception("Import dataset failed") return self.response_500(message=str(exc)) From 36bb4814c646049a38bd356a9699d544a0ee1d81 Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 13:59:17 -0800 Subject: [PATCH 5/9] pull changes from master --- superset/datasets/api.py | 19 ++++++++++++++----- 1 file changed, 14 insertions(+), 5 deletions(-) diff --git a/superset/datasets/api.py b/superset/datasets/api.py index 5a38ea5c78fd1..7b70031f8aaf6 100644 --- a/superset/datasets/api.py +++ b/superset/datasets/api.py @@ -28,8 +28,9 @@ from flask_babel import ngettext from marshmallow import ValidationError -from superset import is_feature_enabled +from superset import event_logger, is_feature_enabled from superset.commands.exceptions import CommandInvalidError +from superset.commands.importers.v1.utils import remove_root from superset.connectors.sqla.models import SqlaTable from superset.constants import RouteMethod from superset.databases.filters import DatabaseFilter @@ -41,6 +42,7 @@ DatasetCreateFailedError, DatasetDeleteFailedError, DatasetForbiddenError, + DatasetImportError, DatasetInvalidError, DatasetNotFoundError, DatasetRefreshFailedError, @@ -182,6 +184,7 @@ class DatasetRestApi(BaseSupersetModelRestApi): @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def post(self) -> Response: """Creates a new Dataset --- @@ -238,6 +241,7 @@ def post(self) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def put(self, pk: int) -> Response: """Changes a Dataset --- @@ -319,6 +323,7 @@ def put(self, pk: int) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def delete(self, pk: int) -> Response: """Deletes a Dataset --- @@ -369,6 +374,7 @@ def delete(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_export_ids_schema) + @event_logger.log_this_with_context(log_to_statsd=False) def export(self, **kwargs: Any) -> Response: """Export datasets --- @@ -444,6 +450,7 @@ def export(self, **kwargs: Any) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def refresh(self, pk: int) -> Response: """Refresh a Dataset --- @@ -493,6 +500,7 @@ def refresh(self, pk: int) -> Response: @protect() @safe @statsd_metrics + @event_logger.log_this_with_context(log_to_statsd=False) def related_objects(self, pk: int) -> Response: """Get charts and dashboards count associated to a dataset --- @@ -551,6 +559,7 @@ def related_objects(self, pk: int) -> Response: @safe @statsd_metrics @rison(get_delete_ids_schema) + @event_logger.log_this_with_context(log_to_statsd=False) def bulk_delete(self, **kwargs: Any) -> Response: """Delete bulk Datasets --- @@ -610,7 +619,7 @@ def bulk_delete(self, **kwargs: Any) -> Response: @safe @statsd_metrics def import_(self) -> Response: - """Import dataset (s) with associated databases + """Import dataset(s) with associated databases --- post: requestBody: @@ -638,12 +647,12 @@ def import_(self) -> Response: 500: $ref: '#/components/responses/500' """ - upload = request.files.get("file") + upload = request.files.get("formData") if not upload: return self.response_400() with ZipFile(upload) as bundle: contents = { - file_name: bundle.read(file_name).decode() + remove_root(file_name): bundle.read(file_name).decode() for file_name in bundle.namelist() } @@ -654,6 +663,6 @@ def import_(self) -> Response: except CommandInvalidError as exc: logger.warning("Import dataset failed") return self.response_422(message=exc.normalized_messages()) - except Exception as exc: # pylint: disable=broad-except + except DatasetImportError as exc: logger.exception("Import dataset failed") return self.response_500(message=str(exc)) From 949ecaa880a0e44c0d8a1b3c8c4d505f756b8b44 Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 14:02:11 -0800 Subject: [PATCH 6/9] change typing --- superset/datasets/commands/update.py | 4 ++-- superset/datasets/dao.py | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/superset/datasets/commands/update.py b/superset/datasets/commands/update.py index 809720ed6ab39..216d7f8956a32 100644 --- a/superset/datasets/commands/update.py +++ b/superset/datasets/commands/update.py @@ -16,7 +16,7 @@ # under the License. import logging from collections import Counter -from typing import Any, Dict, List, Optional, Union +from typing import Any, Dict, List, Optional from flask_appbuilder.models.sqla import Model from flask_appbuilder.security.sqla.models import User @@ -53,7 +53,7 @@ def __init__( user: User, model_id: int, data: Dict[str, Any], - override_columns: Union[bool, Any, None] = False, + override_columns: bool = False, ): self._actor = user self._model_id = model_id diff --git a/superset/datasets/dao.py b/superset/datasets/dao.py index 22526e92079bf..ed865fff1219d 100644 --- a/superset/datasets/dao.py +++ b/superset/datasets/dao.py @@ -15,7 +15,7 @@ # specific language governing permissions and limitations # under the License. import logging -from typing import Any, Dict, List, Optional, Union +from typing import Any, Dict, List, Optional from flask import current_app from sqlalchemy.exc import SQLAlchemyError @@ -148,7 +148,7 @@ def update( model: SqlaTable, properties: Dict[str, Any], commit: bool = True, - override_columns: Union[bool, Any, None] = False, + override_columns: bool = False, ) -> Optional[SqlaTable]: """ Updates a Dataset model on the metadata DB From f002d47872c458ed3fd4d202166c0744d8d7dbb1 Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 15:17:27 -0800 Subject: [PATCH 7/9] add comments --- tests/datasets/api_tests.py | 38 +++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/tests/datasets/api_tests.py b/tests/datasets/api_tests.py index 37ef6a46f1fb8..bea5fadfdb866 100644 --- a/tests/datasets/api_tests.py +++ b/tests/datasets/api_tests.py @@ -547,6 +547,44 @@ def test_update_dataset_item(self): db.session.delete(dataset) db.session.commit() + def test_update_dataset_item_w_override_columns(self): + """ + Dataset API: Test update dataset with override columns + """ + # Add default dataset + dataset = self.insert_default_dataset() + self.login(username="admin") + dataset_data = { + "columns": [ + { + "column_name": "new_col", + "description": "description", + "expression": "expression", + "type": "INTEGER", + "verbose_name": "New Col", + } + ], + "description": "changed description", + } + uri = f"api/v1/dataset/{dataset.id}?override_columns=true" + rv = self.put_assert_metric(uri, dataset_data, "put") + assert rv.status_code == 200 + + columns = ( + db.session.query(TableColumn) + .filter_by(table_id=dataset.id) + .order_by("column_name") + .all() + ) + + assert columns[0].column_name == dataset_data["columns"][0]["column_name"] + assert columns[0].description == dataset_data["columns"][0]["description"] + assert columns[0].expression == dataset_data["columns"][0]["expression"] + assert columns[0].type == dataset_data["columns"][0]["type"] + + db.session.delete(dataset) + db.session.commit() + def test_update_dataset_create_column(self): """ Dataset API: Test update dataset create column From 7ddf9eaca6112b4adfc73f01d130ef0bb50704ab Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 15:24:48 -0800 Subject: [PATCH 8/9] fix this code --- superset/datasets/commands/update.py | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/superset/datasets/commands/update.py b/superset/datasets/commands/update.py index 216d7f8956a32..7b4c521db88f5 100644 --- a/superset/datasets/commands/update.py +++ b/superset/datasets/commands/update.py @@ -66,8 +66,9 @@ def run(self) -> Model: if self._model: try: dataset = DatasetDAO.update( - self._model, - self._properties, + model=self._model, + properties=self._properties, + commit=True, override_columns=self.override_columns, ) return dataset From 57ca09c708a8e6d35a76b58b8212ed70a4515fc3 Mon Sep 17 00:00:00 2001 From: hughhhh Date: Fri, 27 Nov 2020 15:36:26 -0800 Subject: [PATCH 9/9] fix --- superset/datasets/dao.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/superset/datasets/dao.py b/superset/datasets/dao.py index ed865fff1219d..284a43508068a 100644 --- a/superset/datasets/dao.py +++ b/superset/datasets/dao.py @@ -143,7 +143,7 @@ def validate_metrics_uniqueness(dataset_id: int, metrics_names: List[str]) -> bo return len(dataset_query) == 0 @classmethod - def update( + def update( # pylint: disable=W:279 cls, model: SqlaTable, properties: Dict[str, Any],