This is an automated email from the ASF dual-hosted git repository.
betodealmeida 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 68c145adc36 feat(semantic layers): add metadata on additive metrics
(#40279)
68c145adc36 is described below
commit 68c145adc3610283a2c695c0a2f0b5cb10ee0118
Author: Beto Dealmeida <[email protected]>
AuthorDate: Wed May 20 18:29:28 2026 -0400
feat(semantic layers): add metadata on additive metrics (#40279)
---
.../src/superset_core/semantic_layers/types.py | 21 ++++++++
tests/unit_tests/semantic_layers/types_test.py | 58 ++++++++++++++++++++++
2 files changed, 79 insertions(+)
diff --git a/superset-core/src/superset_core/semantic_layers/types.py
b/superset-core/src/superset_core/semantic_layers/types.py
index 1239c1303be..3bfa9e8c315 100644
--- a/superset-core/src/superset_core/semantic_layers/types.py
+++ b/superset-core/src/superset_core/semantic_layers/types.py
@@ -92,6 +92,26 @@ class Dimension:
grain: Grain | None = None
+class AggregationType(str, enum.Enum):
+ """
+ Aggregation function applied by a metric.
+
+ Additivity (across an arbitrary set of grouping dimensions):
+ * ``SUM``, ``COUNT``: fully additive — sub-group sums roll up via ``sum``.
+ * ``MIN``, ``MAX``: roll up via ``min`` / ``max`` of sub-group values.
+ * ``AVG``, ``COUNT_DISTINCT``, ``OTHER``: not safely roll-uppable from
+ sub-aggregates without auxiliary data.
+ """
+
+ SUM = "SUM"
+ COUNT = "COUNT"
+ MIN = "MIN"
+ MAX = "MAX"
+ AVG = "AVG"
+ COUNT_DISTINCT = "COUNT_DISTINCT"
+ OTHER = "OTHER"
+
+
@dataclass(frozen=True)
class Metric:
id: str
@@ -100,6 +120,7 @@ class Metric:
definition: str
description: str | None = None
+ aggregation: AggregationType | None = None
@dataclass(frozen=True)
diff --git a/tests/unit_tests/semantic_layers/types_test.py
b/tests/unit_tests/semantic_layers/types_test.py
new file mode 100644
index 00000000000..0b1e8813f71
--- /dev/null
+++ b/tests/unit_tests/semantic_layers/types_test.py
@@ -0,0 +1,58 @@
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+
+from __future__ import annotations
+
+import pyarrow as pa
+from superset_core.semantic_layers.types import AggregationType, Metric
+
+
+def test_metric_aggregation_defaults_to_none() -> None:
+ metric = Metric(
+ id="x",
+ name="x",
+ type=pa.float64(),
+ definition="sum(x)",
+ )
+ assert metric.aggregation is None
+
+
+def test_metric_accepts_aggregation_type() -> None:
+ metric = Metric(
+ id="x",
+ name="x",
+ type=pa.float64(),
+ definition="sum(x)",
+ aggregation=AggregationType.SUM,
+ )
+ assert metric.aggregation is AggregationType.SUM
+
+
+def test_aggregation_type_is_string_enum() -> None:
+ # Behaves as a string for equality and serialization, so it can be sent
+ # over JSON without an explicit converter.
+ assert AggregationType.SUM == "SUM"
+ assert AggregationType.COUNT_DISTINCT.value == "COUNT_DISTINCT"
+ assert {a.value for a in AggregationType} == {
+ "SUM",
+ "COUNT",
+ "MIN",
+ "MAX",
+ "AVG",
+ "COUNT_DISTINCT",
+ "OTHER",
+ }