This is an automated email from the ASF dual-hosted git repository. beto pushed a commit to branch prevent-column-modifications in repository https://gitbox.apache.org/repos/asf/superset.git
commit 6e2f6871e907188b645065d65608227ae03872ac Author: Beto Dealmeida <[email protected]> AuthorDate: Tue Jul 9 16:22:45 2024 -0400 fix: prevent guest users from changing columns --- superset/security/manager.py | 53 ++++++++++++++++++++++++-------------------- 1 file changed, 29 insertions(+), 24 deletions(-) diff --git a/superset/security/manager.py b/superset/security/manager.py index d03da75079..b99856f96d 100644 --- a/superset/security/manager.py +++ b/superset/security/manager.py @@ -145,7 +145,7 @@ RoleModelView.edit_columns = ["name", "permissions", "user"] RoleModelView.related_views = [] -def freeze_metric(metric: Metric) -> str: +def freeze_value(metric: Metric) -> str: """ Used to compare metric sets. """ @@ -170,32 +170,37 @@ def query_context_modified(query_context: "QueryContext") -> bool: if form_data.get("slice_id") != stored_chart.id: return True - # compare form_data - requested_metrics = { - freeze_metric(metric) for metric in form_data.get("metrics") or [] - } - stored_metrics = { - freeze_metric(metric) - for metric in stored_chart.params_dict.get("metrics") or [] - } - if not requested_metrics.issubset(stored_metrics): - return True + stored_query_context = ( + json.loads(cast(str, stored_chart.query_context)) + if stored_chart.query_context + else None + ) - # compare queries in query_context - queries_metrics = { - freeze_metric(metric) - for query in query_context.queries - for metric in query.metrics or [] - } + # compare columns and metrics in form_data with stored values + for key in ["metrics", "columns"]: + requested_values = {freeze_value(value) for value in form_data.get(key) or []} + stored_values = { + freeze_value(value) for value in stored_chart.params_dict.get(key) or [] + } + if not requested_values.issubset(stored_values): + return True - if stored_chart.query_context: - stored_query_context = json.loads(cast(str, stored_chart.query_context)) - for query in stored_query_context.get("queries") or []: - stored_metrics.update( - {freeze_metric(metric) for metric in query.get("metrics") or []} - ) + # compare queries in query_context + queries_values = { + freeze_value(value) + for query in query_context.queries + for value in query.get(key) or [] + } + if stored_query_context: + for query in stored_query_context.get("queries") or []: + stored_values.update( + {freeze_value(value) for value in query.get(key) or []} + ) + + if not queries_values.issubset(stored_values): + return True - return not queries_metrics.issubset(stored_metrics) + return False class SupersetSecurityManager( # pylint: disable=too-many-public-methods
