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

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


The following commit(s) were added to refs/heads/master by this push:
     new c945160b9e3 [fix](query-cache) include variant subcolumn path in query 
cache digest (#61709)
c945160b9e3 is described below

commit c945160b9e39ef45e22560923bc3cb1f66ea0726
Author: 924060929 <[email protected]>
AuthorDate: Wed Mar 25 16:56:04 2026 +0800

    [fix](query-cache) include variant subcolumn path in query cache digest 
(#61709)
    
    Different variant subcolumn queries (e.g. data['int_1'] vs
    data['int_nested']) were generating the same cache digest because
    normalizeSelectColumns() only used the base column name. This caused
    query cache to return wrong results when different subcolumns of the
    same variant column were queried.
    
    Fix: include the variant subcolumn path in the normalized select column
    name so that different subcolumns produce different cache digests.
---
 .../org/apache/doris/planner/OlapScanNode.java     | 11 +++++++++-
 .../doris/planner/QueryCacheNormalizerTest.java    | 25 +++++++++++++++++++++-
 2 files changed, 34 insertions(+), 2 deletions(-)

diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/planner/OlapScanNode.java 
b/fe/fe-core/src/main/java/org/apache/doris/planner/OlapScanNode.java
index d651bf79010..9f0b1a1e56b 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/planner/OlapScanNode.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/planner/OlapScanNode.java
@@ -1249,7 +1249,16 @@ public class OlapScanNode extends ScanNode {
                 .flatMap(tupleId -> 
normalizer.getDescriptorTable().getTupleDesc(tupleId).getSlots().stream())
                 .collect(Collectors.toList());
         List<Pair<SlotId, String>> selectColumns = slots.stream()
-                .map(slot -> Pair.of(slot.getId(), slot.getColumn().getName()))
+                .map(slot -> {
+                    // For variant subcolumns, use the materialized column 
name (e.g. "data.int_1")
+                    // to distinguish different subcolumns of the same variant 
column in cache digest.
+                    List<String> subColPath = slot.getSubColLables();
+                    String colName = slot.getColumn().getName();
+                    if (subColPath != null && !subColPath.isEmpty()) {
+                        colName = colName + "." + String.join(".", subColPath);
+                    }
+                    return Pair.of(slot.getId(), colName);
+                })
                 .collect(Collectors.toList());
         for (Column partitionColumn : 
olapTable.getPartitionInfo().getPartitionColumns()) {
             boolean selectPartitionColumn = false;
diff --git 
a/fe/fe-core/src/test/java/org/apache/doris/planner/QueryCacheNormalizerTest.java
 
b/fe/fe-core/src/test/java/org/apache/doris/planner/QueryCacheNormalizerTest.java
index 5648484f49d..5e618797188 100644
--- 
a/fe/fe-core/src/test/java/org/apache/doris/planner/QueryCacheNormalizerTest.java
+++ 
b/fe/fe-core/src/test/java/org/apache/doris/planner/QueryCacheNormalizerTest.java
@@ -110,7 +110,14 @@ public class QueryCacheNormalizerTest extends 
TestWithFeService {
                 + "distributed by hash(k1) buckets 3\n"
                 + "properties('replication_num' = '1')";
 
-        createTables(nonPart, part1, part2, multiLeveParts);
+        String variantTable = "create table db1.variant_tbl("
+                + "  k1 int,\n"
+                + "  data variant)\n"
+                + "DUPLICATE KEY(k1)\n"
+                + "distributed by hash(k1) buckets 3\n"
+                + "properties('replication_num' = '1')";
+
+        createTables(nonPart, part1, part2, multiLeveParts, variantTable);
 
         
connectContext.getSessionVariable().setDisableNereidsRules("PRUNE_EMPTY_PARTITION");
         connectContext.getSessionVariable().setEnableQueryCache(true);
@@ -358,6 +365,22 @@ public class QueryCacheNormalizerTest extends 
TestWithFeService {
         Assertions.assertEquals(fourPhaseAggPlans, threePhaseAggPlans);
     }
 
+    @Test
+    public void testVariantSubColumnDigest() throws Exception {
+        // Different variant subcolumns should produce different digests
+        String digest1 = getDigest(
+                "select cast(data['int_1'] as int), count(*) from 
db1.variant_tbl group by cast(data['int_1'] as int)");
+        String digest2 = getDigest(
+                "select cast(data['int_nested'] as int), count(*) from 
db1.variant_tbl group by cast(data['int_nested'] as int)");
+        Assertions.assertNotEquals(digest1, digest2,
+                "Queries on different variant subcolumns must have different 
cache digests");
+
+        // Same variant subcolumn with different aliases should produce same 
digest
+        String digest3 = getDigest(
+                "select cast(data['int_1'] as int) as a, count(*) as cnt from 
db1.variant_tbl group by cast(data['int_1'] as int)");
+        Assertions.assertEquals(digest1, digest3);
+    }
+
     private String getDigest(String sql) throws Exception {
         return Hex.encodeHexString(getQueryCacheParam(sql).digest);
     }


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to