16
16
// under the License.
17
17
18
18
use std:: collections:: HashSet ;
19
+ use std:: ops:: ControlFlow ;
19
20
use std:: sync:: Arc ;
20
21
21
22
use crate :: planner:: { ContextProvider , PlannerContext , SqlToRel } ;
@@ -28,7 +29,7 @@ use crate::utils::{
28
29
29
30
use datafusion_common:: error:: DataFusionErrorBuilder ;
30
31
use datafusion_common:: tree_node:: { TreeNode , TreeNodeRecursion } ;
31
- use datafusion_common:: { not_impl_err, plan_err, Result } ;
32
+ use datafusion_common:: { not_impl_err, plan_err, DataFusionError , Result } ;
32
33
use datafusion_common:: { RecursionUnnestOption , UnnestOptions } ;
33
34
use datafusion_expr:: expr:: { Alias , PlannedReplaceSelectItem , WildcardOptions } ;
34
35
use datafusion_expr:: expr_rewriter:: {
@@ -45,8 +46,8 @@ use datafusion_expr::{
45
46
46
47
use indexmap:: IndexMap ;
47
48
use sqlparser:: ast:: {
48
- Distinct , Expr as SQLExpr , GroupByExpr , NamedWindowExpr , OrderBy ,
49
- SelectItemQualifiedWildcardKind , WildcardAdditionalOptions , WindowType ,
49
+ visit_expressions_mut , Distinct , Expr as SQLExpr , GroupByExpr , NamedWindowExpr ,
50
+ OrderBy , SelectItemQualifiedWildcardKind , WildcardAdditionalOptions , WindowType ,
50
51
} ;
51
52
use sqlparser:: ast:: { NamedWindowDefinition , Select , SelectItem , TableWithJoins } ;
52
53
@@ -891,29 +892,42 @@ fn match_window_definitions(
891
892
named_windows : & [ NamedWindowDefinition ] ,
892
893
) -> Result < ( ) > {
893
894
for proj in projection. iter_mut ( ) {
894
- if let SelectItem :: ExprWithAlias {
895
- expr : SQLExpr :: Function ( f) ,
896
- alias : _,
897
- }
898
- | SelectItem :: UnnamedExpr ( SQLExpr :: Function ( f) ) = proj
895
+ if let SelectItem :: ExprWithAlias { expr, alias : _ }
896
+ | SelectItem :: UnnamedExpr ( expr) = proj
899
897
{
900
- for NamedWindowDefinition ( window_ident, window_expr) in named_windows. iter ( ) {
901
- if let Some ( WindowType :: NamedWindow ( ident) ) = & f. over {
902
- if ident. eq ( window_ident) {
903
- f. over = Some ( match window_expr {
904
- NamedWindowExpr :: NamedWindow ( ident) => {
905
- WindowType :: NamedWindow ( ident. clone ( ) )
906
- }
907
- NamedWindowExpr :: WindowSpec ( spec) => {
908
- WindowType :: WindowSpec ( spec. clone ( ) )
898
+ let mut err = None ;
899
+ visit_expressions_mut ( expr, |expr| {
900
+ if let SQLExpr :: Function ( f) = expr {
901
+ if let Some ( WindowType :: NamedWindow ( _) ) = & f. over {
902
+ for NamedWindowDefinition ( window_ident, window_expr) in
903
+ named_windows
904
+ {
905
+ if let Some ( WindowType :: NamedWindow ( ident) ) = & f. over {
906
+ if ident. eq ( window_ident) {
907
+ f. over = Some ( match window_expr {
908
+ NamedWindowExpr :: NamedWindow ( ident) => {
909
+ WindowType :: NamedWindow ( ident. clone ( ) )
910
+ }
911
+ NamedWindowExpr :: WindowSpec ( spec) => {
912
+ WindowType :: WindowSpec ( spec. clone ( ) )
913
+ }
914
+ } )
915
+ }
909
916
}
910
- } )
917
+ }
918
+ // All named windows must be defined with a WindowSpec.
919
+ if let Some ( WindowType :: NamedWindow ( ident) ) = & f. over {
920
+ err = Some ( DataFusionError :: Plan ( format ! (
921
+ "The window {ident} is not defined!"
922
+ ) ) ) ;
923
+ return ControlFlow :: Break ( ( ) ) ;
924
+ }
911
925
}
912
926
}
913
- }
914
- // All named windows must be defined with a WindowSpec.
915
- if let Some ( WindowType :: NamedWindow ( ident ) ) = & f . over {
916
- return plan_err ! ( "The window {ident} is not defined!" ) ;
927
+ ControlFlow :: Continue ( ( ) )
928
+ } ) ;
929
+ if let Some ( err ) = err {
930
+ return Err ( err ) ;
917
931
}
918
932
}
919
933
}
0 commit comments