From d7fffd15cb148bab2fa9a9e58d3f323231aac5e3 Mon Sep 17 00:00:00 2001 From: Ruben Pollan Date: Tue, 28 Aug 2018 19:55:13 +0200 Subject: Add support for month and year frequency --- src/date.rs | 30 +++++++++++++++++++++++++++++- src/periodic.rs | 28 ++++++++++++++++++---------- 2 files changed, 47 insertions(+), 11 deletions(-) (limited to 'src') diff --git a/src/date.rs b/src/date.rs index b703766..f77b5d5 100644 --- a/src/date.rs +++ b/src/date.rs @@ -4,7 +4,7 @@ use std::ops::Add; use errors::EventError; use chrono; -use chrono::{TimeZone, Duration}; +use chrono::{TimeZone, Duration, Datelike}; use chrono::offset::Utc; use chrono_tz::{Tz, UTC}; @@ -64,6 +64,34 @@ impl Date { }; Ok(date) } + + pub fn month(&self) -> u32 { + match *self { + Date::Time(t) => t.month(), + Date::AllDay(d) => d.month(), + } + } + + pub fn with_month(&self, month: u32) -> Option { + Some(match *self { + Date::Time(t) => Date::Time(t.with_month(month)?), + Date::AllDay(d) => Date::AllDay(d.with_month(month)?), + }) + } + + pub fn year(&self) -> i32 { + match *self { + Date::Time(t) => t.year(), + Date::AllDay(d) => d.year(), + } + } + + pub fn with_year(&self, year: i32) -> Option { + Some(match *self { + Date::Time(t) => Date::Time(t.with_year(year)?), + Date::AllDay(d) => Date::AllDay(d.with_year(year)?), + }) + } } impl Ord for Date { diff --git a/src/periodic.rs b/src/periodic.rs index af9810c..b4bf7bf 100644 --- a/src/periodic.rs +++ b/src/periodic.rs @@ -68,8 +68,8 @@ impl Periodic { events.push(e); count += count; } - start = start + self.freq.duration(self.interval); - end = end + self.freq.duration(self.interval); + start = self.freq.next_date(start, self.interval); + end = self.freq.next_date(end, self.interval); } events } @@ -87,15 +87,23 @@ impl fmt::Display for Periodic { } impl Freq { - pub fn duration(&self, count: i64) -> Duration { + pub fn next_date(&self, date: Date, count: i64) -> Date { match self { - Freq::Secondly => Duration::seconds(count), - Freq::Minutely => Duration::minutes(count), - Freq::Hourly => Duration::hours(count), - Freq::Daily => Duration::days(count), - Freq::Weekly => Duration::weeks(count), - Freq::Monthly => Duration::days(count * 30), // FIXME - Freq::Yearly => Duration::days(count * 365), // FIXME + Freq::Secondly => date + Duration::seconds(count), + Freq::Minutely => date + Duration::minutes(count), + Freq::Hourly => date + Duration::hours(count), + Freq::Daily => date + Duration::days(count), + Freq::Weekly => date + Duration::weeks(count), + Freq::Monthly => { + let month = date.month(); + if month == 12 { + let date = date.with_month(1).unwrap(); + date.with_year(date.year() + 1).unwrap() + } else { + date.with_month(month + 1).unwrap() + } + } + Freq::Yearly => date.with_year(date.year() + 1).unwrap(), } } } -- cgit v1.2.3