@@ -66,10 +66,16 @@ const ID: RuleID = RuleID::HierarchicalGroupingSetsToUnion;
66
66
pub struct RuleHierarchicalGroupingSetsToUnion {
67
67
id : RuleID ,
68
68
matchers : Vec < Matcher > ,
69
+ cte_channel_size : usize ,
69
70
}
70
71
71
72
impl RuleHierarchicalGroupingSetsToUnion {
72
- pub fn new ( _ctx : Arc < OptimizerContext > ) -> Self {
73
+ pub fn new ( ctx : Arc < OptimizerContext > ) -> Self {
74
+ let cte_channel_size = ctx
75
+ . get_table_ctx ( )
76
+ . get_settings ( )
77
+ . get_grouping_sets_channel_size ( )
78
+ . unwrap ( ) ;
73
79
Self {
74
80
id : ID ,
75
81
matchers : vec ! [ Matcher :: MatchOp {
@@ -79,21 +85,36 @@ impl RuleHierarchicalGroupingSetsToUnion {
79
85
children: vec![ Matcher :: Leaf ] ,
80
86
} ] ,
81
87
} ] ,
88
+ cte_channel_size : cte_channel_size as usize ,
82
89
}
83
90
}
84
91
85
92
/// Analyzes grouping sets to build a true hierarchical dependency DAG
86
- fn build_hierarchy_dag ( & self , grouping_sets : & [ Vec < IndexType > ] ) -> HierarchyDAG {
93
+ fn build_hierarchy_dag (
94
+ & self ,
95
+ grouping_sets : & [ Vec < IndexType > ] ,
96
+ agg : & Aggregate ,
97
+ ) -> HierarchyDAG {
87
98
let mut levels: Vec < GroupingLevel > = grouping_sets
88
99
. iter ( )
89
100
. enumerate ( )
90
- . map ( |( idx, set) | GroupingLevel {
91
- set_index : idx,
92
- columns : set. clone ( ) ,
93
- direct_children : Vec :: new ( ) ,
94
- possible_parents : Vec :: new ( ) ,
95
- chosen_parent : None ,
96
- level : set. len ( ) ,
101
+ . map ( |( idx, set) | {
102
+ // Sort columns according to their order in group_items for consistent schema ordering
103
+ let mut sorted_columns = set. clone ( ) ;
104
+ sorted_columns. sort_by_key ( |& col_idx| {
105
+ agg. group_items
106
+ . iter ( )
107
+ . position ( |item| item. index == col_idx)
108
+ . unwrap_or ( usize:: MAX ) // Put unknown columns at the end
109
+ } ) ;
110
+ GroupingLevel {
111
+ set_index : idx,
112
+ columns : sorted_columns,
113
+ direct_children : Vec :: new ( ) ,
114
+ possible_parents : Vec :: new ( ) ,
115
+ chosen_parent : None ,
116
+ level : set. len ( ) ,
117
+ }
97
118
} )
98
119
. collect ( ) ;
99
120
@@ -406,7 +427,7 @@ impl RuleHierarchicalGroupingSetsToUnion {
406
427
cte_name : cte_name. to_string ( ) ,
407
428
cte_output_columns : None ,
408
429
ref_count : 1 ,
409
- channel_size : None ,
430
+ channel_size : Some ( self . cte_channel_size ) ,
410
431
}
411
432
. into ( ) ,
412
433
) ,
@@ -457,7 +478,7 @@ impl RuleHierarchicalGroupingSetsToUnion {
457
478
cte_name : cte_name. to_string ( ) ,
458
479
cte_output_columns : None ,
459
480
ref_count : 1 ,
460
- channel_size : None ,
481
+ channel_size : Some ( self . cte_channel_size ) ,
461
482
}
462
483
. into ( ) ,
463
484
) ,
@@ -497,7 +518,7 @@ impl RuleHierarchicalGroupingSetsToUnion {
497
518
cte_name : cte_name. to_string ( ) ,
498
519
cte_output_columns : None ,
499
520
ref_count : 1 ,
500
- channel_size : None ,
521
+ channel_size : Some ( self . cte_channel_size ) ,
501
522
}
502
523
. into ( ) ,
503
524
) ,
@@ -632,10 +653,11 @@ impl RuleHierarchicalGroupingSetsToUnion {
632
653
// Create parent CTE consumer
633
654
let parent_output_columns: Vec < IndexType > = {
634
655
let mut output_cols = Vec :: new ( ) ;
635
- // Then : aggregate function output columns
656
+ // First : aggregate function output columns
636
657
for agg_item in & agg. aggregate_functions {
637
658
output_cols. push ( agg_item. index ) ;
638
659
}
660
+ // Then: parent level columns (already sorted from build_hierarchy_dag)
639
661
for & col_idx in & parent_level. columns {
640
662
output_cols. push ( col_idx) ;
641
663
}
@@ -666,7 +688,7 @@ impl RuleHierarchicalGroupingSetsToUnion {
666
688
cte_name : cte_name. to_string ( ) ,
667
689
cte_output_columns : None ,
668
690
ref_count : 1 ,
669
- channel_size : None ,
691
+ channel_size : Some ( self . cte_channel_size ) ,
670
692
}
671
693
. into ( ) ,
672
694
) ,
@@ -850,7 +872,7 @@ impl Rule for RuleHierarchicalGroupingSetsToUnion {
850
872
}
851
873
852
874
// Build hierarchy DAG
853
- let hierarchy = self . build_hierarchy_dag ( & grouping_sets. sets ) ;
875
+ let hierarchy = self . build_hierarchy_dag ( & grouping_sets. sets , & agg ) ;
854
876
// Check if we have meaningful hierarchical structure
855
877
let hierarchical_levels = hierarchy
856
878
. levels
0 commit comments