@@ -656,14 +656,26 @@ pub fn generate_update_list(
656
656
Vec :: with_capacity ( update_list. len ( ) ) ,
657
657
|mut acc, ( index, scalar) | {
658
658
let field = schema. field ( * index) ;
659
+ let data_type = scalar. data_type ( ) ?;
659
660
let target_type = field. data_type ( ) ;
660
- let nullable_type = target_type. wrap_nullable ( ) ;
661
+ let left = if data_type != * target_type {
662
+ // change scalar's column datatype
663
+ let mut tmp_scalar = scalar. clone ( ) ;
664
+ if data_type. wrap_nullable ( ) == * target_type {
665
+ if let ScalarExpr :: BoundColumnRef ( ref mut bound_ref) = tmp_scalar {
666
+ bound_ref. column . data_type = Box :: new ( target_type. clone ( ) ) ;
667
+ }
668
+ }
669
+ wrap_cast ( & tmp_scalar, target_type)
670
+ } else {
671
+ scalar. clone ( )
672
+ } ;
661
673
662
674
let scalar = if col_indices. is_empty ( ) {
663
675
// The condition is always true.
664
676
// Replace column to the result of the following expression:
665
677
// CAST(expression, type)
666
- wrap_cast ( scalar , & nullable_type )
678
+ left
667
679
} else {
668
680
// Replace column to the result of the following expression:
669
681
// if(condition, CAST(expression, type), column)
@@ -675,30 +687,16 @@ pub fn generate_update_list(
675
687
field. name ( ) ,
676
688
column_binding,
677
689
) {
678
- // Create a new column_binding, ensuring its type is nullable
679
- let mut column = column_binding. clone ( ) ;
680
- column. data_type = Box :: new ( nullable_type. clone ( ) ) ;
681
690
right = Some ( ScalarExpr :: BoundColumnRef ( BoundColumnRef {
682
691
span : None ,
683
- column,
692
+ column : column_binding . clone ( ) ,
684
693
} ) ) ;
685
694
break ;
686
695
}
687
696
}
688
697
689
698
let right = right. ok_or_else ( || ErrorCode :: Internal ( "It's a bug" ) ) ?;
690
699
691
- // Ensure the scalar type is also nullable
692
- let mut scalar = scalar. clone ( ) ;
693
- if let ScalarExpr :: BoundColumnRef ( ref mut bound_ref) = scalar {
694
- bound_ref. column . data_type = Box :: new ( nullable_type. clone ( ) ) ;
695
- }
696
-
697
- // Convert left to nullable type
698
- let left = wrap_cast ( & scalar, & nullable_type) ;
699
- let right = wrap_cast ( & right, & nullable_type) ;
700
- let nullable_bool_type = DataType :: Boolean . wrap_nullable ( ) ;
701
- let predicate = wrap_cast ( & predicate, & nullable_bool_type) ;
702
700
// corner case: for merge into, if target_table's fields are not null, when after bind_join, it will
703
701
// change into nullable, so we need to cast this. but we will do cast after all matched clauses,please
704
702
// see `cast_data_type_for_merge()`.
0 commit comments