@@ -20,7 +20,7 @@ use arrow::array::{
2020 Array , ArrayRef , AsArray , BooleanBufferBuilder , DictionaryArray , PrimitiveArray ,
2121} ;
2222use arrow:: datatypes:: { ArrowDictionaryKeyType , ArrowNativeType , DataType , Field } ;
23- use datafusion_common:: Result ;
23+ use datafusion_common:: { Result , exec_err } ;
2424use std:: marker:: PhantomData ;
2525use std:: sync:: Arc ;
2626
@@ -45,12 +45,6 @@ impl<K: ArrowDictionaryKeyType + Send + Sync> DictionaryGroupValuesColumn<K> {
4545
4646 fn into_dict ( values : ArrayRef ) -> ArrayRef {
4747 let num_values = values. len ( ) ;
48- assert ! (
49- Self :: valid_bounds:: <K >( num_values) ,
50- "Dictionary key type {:?} cannot hold {} values" ,
51- K :: DATA_TYPE ,
52- num_values
53- ) ;
5448 let keys: PrimitiveArray < K > = ( 0 ..num_values)
5549 . map ( |i| ( !values. is_null ( i) ) . then ( || K :: Native :: usize_as ( i) ) )
5650 . collect ( ) ;
@@ -59,8 +53,20 @@ impl<K: ArrowDictionaryKeyType + Send + Sync> DictionaryGroupValuesColumn<K> {
5953
6054 /// Returns the index of the first null in `values`, or `None` if there are no nulls.
6155 fn null_sentinel_index ( values : & ArrayRef ) -> Option < usize > {
62- ( values. null_count ( ) > 0 )
63- . then ( || ( 0 ..values. len ( ) ) . find ( |& i| values. is_null ( i) ) . unwrap ( ) )
56+ values. nulls ( ) ?. iter ( ) . position ( |valid| !valid)
57+ }
58+
59+ /// Returns an error if adding `additional` groups would overflow the key type's range.
60+ // https://github.com/apache/datafusion/issues/23127
61+ fn check_key_overflow ( current_len : usize , additional : usize ) -> Result < ( ) > {
62+ if !Self :: valid_bounds :: < K > ( current_len + additional) {
63+ return exec_err ! (
64+ "Dictionary key type {:?} cannot represent {} groups" ,
65+ K :: DATA_TYPE ,
66+ current_len + additional
67+ ) ;
68+ }
69+ Ok ( ( ) )
6470 }
6571
6672 fn valid_bounds < T : ArrowDictionaryKeyType > ( num_values : usize ) -> bool {
@@ -91,6 +97,7 @@ impl<K: ArrowDictionaryKeyType + Send + Sync> GroupColumn
9197 }
9298
9399 fn append_val ( & mut self , array : & ArrayRef , row : usize ) -> Result < ( ) > {
100+ Self :: check_key_overflow ( self . inner . len ( ) , 1 ) ?;
94101 let dict = array. as_dictionary :: < K > ( ) ;
95102 match dict. key ( row) {
96103 None => self . inner . append_val ( & self . null_array , 0 ) ,
@@ -154,6 +161,7 @@ impl<K: ArrowDictionaryKeyType + Send + Sync> GroupColumn
154161 }
155162
156163 fn vectorized_append ( & mut self , array : & ArrayRef , rows : & [ usize ] ) -> Result < ( ) > {
164+ Self :: check_key_overflow ( self . inner . len ( ) , rows. len ( ) ) ?;
157165 let dict = array. as_dictionary :: < K > ( ) ;
158166 let dict_keys = dict. keys ( ) ;
159167
0 commit comments