@@ -28,7 +28,7 @@ use time::error::Format;
2828use time:: format_description:: well_known:: { Iso8601 , Rfc2822 , Rfc3339 } ;
2929use time:: format_description:: FormatItem ;
3030use time:: parsing:: Parsed ;
31- use time:: { OffsetDateTime , PrimitiveDateTime } ;
31+ use time:: { Month , OffsetDateTime , PrimitiveDateTime } ;
3232use time_fmt:: parse:: time_format_item:: parse_to_format_item;
3333
3434use crate :: TantivyDateTime ;
@@ -84,6 +84,11 @@ impl StrptimeParser {
8484 parsed. set_minute ( 0u8 ) ;
8585 parsed. set_second ( 0u8 ) ;
8686 }
87+ if parsed. year ( ) . is_none ( ) {
88+ let now = OffsetDateTime :: now_utc ( ) ;
89+ let year = infer_year ( parsed. month ( ) , now. month ( ) , now. year ( ) ) ;
90+ parsed. set_year ( year) ;
91+ }
8792 let date_time = parsed. try_into ( ) ?;
8893 Ok ( date_time)
8994 }
@@ -318,9 +323,26 @@ impl<'de> Deserialize<'de> for DateTimeOutputFormat {
318323 }
319324}
320325
326+ /// Infers the year of a parsed date time. It assumes that events appear more often delayed than in
327+ /// the future and, as a result, skews towards the past year.
328+ pub ( super ) fn infer_year (
329+ parsed_month_opt : Option < Month > ,
330+ this_month : Month ,
331+ this_year : i32 ,
332+ ) -> i32 {
333+ let Some ( parsed_month) = parsed_month_opt else {
334+ return this_year;
335+ } ;
336+ if parsed_month as u8 > this_month as u8 + 3 {
337+ return this_year - 1 ;
338+ }
339+ this_year
340+ }
341+
321342#[ cfg( test) ]
322343mod tests {
323344 use time:: macros:: datetime;
345+ use time:: Month ;
324346
325347 use super :: * ;
326348
@@ -453,4 +475,28 @@ mod tests {
453475 "datetime string `2021-01-01TABC` does not match strptime format `%Y-%m-%d`"
454476 ) ;
455477 }
478+
479+ #[ test]
480+ fn test_infer_year ( ) {
481+ let inferred_year = infer_year ( None , Month :: January , 2024 ) ;
482+ assert_eq ! ( inferred_year, 2024 ) ;
483+
484+ let inferred_year = infer_year ( Some ( Month :: December ) , Month :: January , 2024 ) ;
485+ assert_eq ! ( inferred_year, 2023 ) ;
486+
487+ let inferred_year = infer_year ( Some ( Month :: January ) , Month :: January , 2024 ) ;
488+ assert_eq ! ( inferred_year, 2024 ) ;
489+
490+ let inferred_year = infer_year ( Some ( Month :: February ) , Month :: January , 2024 ) ;
491+ assert_eq ! ( inferred_year, 2024 ) ;
492+
493+ let inferred_year = infer_year ( Some ( Month :: March ) , Month :: January , 2024 ) ;
494+ assert_eq ! ( inferred_year, 2024 ) ;
495+
496+ let inferred_year = infer_year ( Some ( Month :: April ) , Month :: January , 2024 ) ;
497+ assert_eq ! ( inferred_year, 2024 ) ;
498+
499+ let inferred_year = infer_year ( Some ( Month :: May ) , Month :: January , 2024 ) ;
500+ assert_eq ! ( inferred_year, 2023 ) ;
501+ }
456502}
0 commit comments