@@ -26,13 +26,16 @@ use arrow::datatypes::DataType::{
2626 Date32 , Date64 , Duration , Interval , Time32 , Time64 , Timestamp ,
2727} ;
2828use arrow:: datatypes:: TimeUnit :: { Microsecond , Millisecond , Nanosecond , Second } ;
29- use arrow:: datatypes:: { DataType , Field , FieldRef , TimeUnit } ;
29+ use arrow:: datatypes:: {
30+ DataType , Field , FieldRef , IntervalUnit as ArrowIntervalUnit , TimeUnit ,
31+ } ;
3032use datafusion_common:: types:: { NativeType , logical_date} ;
3133
3234use datafusion_common:: {
3335 Result , ScalarValue ,
3436 cast:: {
35- as_date32_array, as_date64_array, as_int32_array, as_time32_millisecond_array,
37+ as_date32_array, as_date64_array, as_int32_array, as_interval_dt_array,
38+ as_interval_mdn_array, as_interval_ym_array, as_time32_millisecond_array,
3639 as_time32_second_array, as_time64_microsecond_array, as_time64_nanosecond_array,
3740 as_timestamp_microsecond_array, as_timestamp_millisecond_array,
3841 as_timestamp_nanosecond_array, as_timestamp_second_array,
@@ -56,7 +59,7 @@ use datafusion_macros::user_doc;
5659 argument(
5760 name = "part" ,
5861 description = r#"Part of the date to return. The following date parts are supported:
59-
62+
6063 - year
6164 - quarter (emits value in inclusive range [1, 4] based on which quartile of the year the date is in)
6265 - month
@@ -349,6 +352,7 @@ fn seconds(array: &dyn Array, unit: TimeUnit) -> Result<ArrayRef> {
349352
350353fn epoch ( array : & dyn Array ) -> Result < ArrayRef > {
351354 const SECONDS_IN_A_DAY : f64 = 86400_f64 ;
355+ const DAYS_PER_MONTH : f64 = 30_f64 ;
352356
353357 let f: Float64Array = match array. data_type ( ) {
354358 Timestamp ( Second , _) => as_timestamp_second_array ( array) ?. unary ( |x| x as f64 ) ,
@@ -373,7 +377,19 @@ fn epoch(array: &dyn Array) -> Result<ArrayRef> {
373377 Time64 ( Nanosecond ) => {
374378 as_time64_nanosecond_array ( array) ?. unary ( |x| x as f64 / 1_000_000_000_f64 )
375379 }
376- Interval ( _) | Duration ( _) => return seconds ( array, Second ) ,
380+ Interval ( ArrowIntervalUnit :: YearMonth ) => as_interval_ym_array ( array) ?
381+ . unary ( |x| x as f64 * DAYS_PER_MONTH * SECONDS_IN_A_DAY ) ,
382+ Interval ( ArrowIntervalUnit :: DayTime ) => as_interval_dt_array ( array) ?. unary ( |x| {
383+ x. days as f64 * SECONDS_IN_A_DAY + x. milliseconds as f64 / 1_000_f64
384+ } ) ,
385+ Interval ( ArrowIntervalUnit :: MonthDayNano ) => {
386+ as_interval_mdn_array ( array) ?. unary ( |x| {
387+ x. months as f64 * DAYS_PER_MONTH * SECONDS_IN_A_DAY
388+ + x. days as f64 * SECONDS_IN_A_DAY
389+ + x. nanoseconds as f64 / 1_000_000_000_f64
390+ } )
391+ }
392+ Duration ( _) => return seconds ( array, Second ) ,
377393 d => return exec_err ! ( "Cannot convert {d:?} to epoch" ) ,
378394 } ;
379395 Ok ( Arc :: new ( f) )
0 commit comments