public void GetNextOccurrence_Boundaries_ReturnsExpectedNextOccurrence()
        {
            WeeklySchedule schedule = new WeeklySchedule();
            schedule.Add(DayOfWeek.Monday, new TimeSpan(9, 0, 0));
            schedule.Add(DayOfWeek.Wednesday, new TimeSpan(8, 30, 0));
            schedule.Add(DayOfWeek.Wednesday, new TimeSpan(18, 0, 0));
            schedule.Add(DayOfWeek.Friday, new TimeSpan(10, 0, 0));

            // before time on last schedule day - expect last schedule time
            DateTime nextOccurrence = schedule.GetNextOccurrence(DateTime.Parse("2015-05-29T09:59:59"));
            Assert.Equal(DayOfWeek.Friday, nextOccurrence.DayOfWeek);
            Assert.Equal(new TimeSpan(10, 0, 0), nextOccurrence.TimeOfDay);

            // after time on last schedule day - expect advance to beginning of schedule
            nextOccurrence = schedule.GetNextOccurrence(DateTime.Parse("2015-05-29T10:00:01"));
            Assert.Equal(DayOfWeek.Monday, nextOccurrence.DayOfWeek);
            Assert.Equal(new TimeSpan(9, 0, 0), nextOccurrence.TimeOfDay);

            nextOccurrence = schedule.GetNextOccurrence(DateTime.Parse("2015-06-01T08:59:59"));
            Assert.Equal(DayOfWeek.Monday, nextOccurrence.DayOfWeek);
            Assert.Equal(new TimeSpan(9, 0, 0), nextOccurrence.TimeOfDay);

            nextOccurrence = schedule.GetNextOccurrence(DateTime.Parse("2015-06-01T09:00:01"));
            Assert.Equal(DayOfWeek.Wednesday, nextOccurrence.DayOfWeek);
            Assert.Equal(new TimeSpan(8, 30, 0), nextOccurrence.TimeOfDay);

            nextOccurrence = schedule.GetNextOccurrence(DateTime.Parse("2015-06-03T08:30:01"));
            Assert.Equal(DayOfWeek.Wednesday, nextOccurrence.DayOfWeek);
            Assert.Equal(new TimeSpan(18, 00, 0), nextOccurrence.TimeOfDay);

            nextOccurrence = schedule.GetNextOccurrence(DateTime.Parse("2015-06-03T18:00:01"));
            Assert.Equal(DayOfWeek.Friday, nextOccurrence.DayOfWeek);
            Assert.Equal(new TimeSpan(10, 00, 0), nextOccurrence.TimeOfDay);
        }
        public void FormatNextOccurrences_ReturnsExpectedString()
        {
            DateTime now = new DateTime(2015, 9, 16, 10, 30, 00);
            TimerInfo timerInfo = new TimerInfo(new CronSchedule("0 0 * * * *"));
            string result = timerInfo.FormatNextOccurrences(10, now);

            string expected =
                "The next 10 occurrences of the schedule will be:\r\n" +
                "9/16/2015 11:00:00 AM\r\n" +
                "9/16/2015 12:00:00 PM\r\n" +
                "9/16/2015 1:00:00 PM\r\n" +
                "9/16/2015 2:00:00 PM\r\n" +
                "9/16/2015 3:00:00 PM\r\n" +
                "9/16/2015 4:00:00 PM\r\n" +
                "9/16/2015 5:00:00 PM\r\n" +
                "9/16/2015 6:00:00 PM\r\n" +
                "9/16/2015 7:00:00 PM\r\n" +
                "9/16/2015 8:00:00 PM\r\n";
            Assert.Equal(expected, result);

            timerInfo = new TimerInfo(new DailySchedule("2:00:00"));
            result = timerInfo.FormatNextOccurrences(5, now);

            expected =
                "The next 5 occurrences of the schedule will be:\r\n" +
                "9/17/2015 2:00:00 AM\r\n" +
                "9/18/2015 2:00:00 AM\r\n" +
                "9/19/2015 2:00:00 AM\r\n" +
                "9/20/2015 2:00:00 AM\r\n" +
                "9/21/2015 2:00:00 AM\r\n";
            Assert.Equal(expected, result);

            WeeklySchedule weeklySchedule = new WeeklySchedule();
            weeklySchedule.Add(DayOfWeek.Monday, new TimeSpan(8, 0, 0));
            weeklySchedule.Add(DayOfWeek.Wednesday, new TimeSpan(9, 30, 0));
            weeklySchedule.Add(DayOfWeek.Wednesday, new TimeSpan(21, 30, 0));
            weeklySchedule.Add(DayOfWeek.Friday, new TimeSpan(10, 0, 0));

            timerInfo = new TimerInfo(weeklySchedule);

            result = timerInfo.FormatNextOccurrences(5, now);

            expected =
                "The next 5 occurrences of the schedule will be:\r\n" +
                "9/16/2015 9:30:00 PM\r\n" +
                "9/18/2015 10:00:00 AM\r\n" +
                "9/21/2015 8:00:00 AM\r\n" +
                "9/23/2015 9:30:00 AM\r\n" +
                "9/23/2015 9:30:00 PM\r\n";
            Assert.Equal(expected, result);
        }
        public void GetNextOccurrence_EmptySchedule_Throws()
        {
            WeeklySchedule schedule = new WeeklySchedule();

            Assert.Throws<InvalidOperationException>(() => schedule.GetNextOccurrence(DateTime.Now));
        }
        private void VerifySchedule(Tuple<DayOfWeek, TimeSpan>[] scheduleData, DateTime now)
        {
            WeeklySchedule schedule = new WeeklySchedule();
            foreach (var occurrence in scheduleData)
            {
                schedule.Add(occurrence.Item1, occurrence.Item2);
            }

            var expectedSchedule = scheduleData.GroupBy(p => p.Item1);

            // loop through the full schedule a few times, ensuring we cross over
            // a month boundary ensuring day handling is correct
            for (int i = 0; i < 10; i++)
            {
                // run through the entire schedule once, ordering the expected times per day
                foreach (var expectedScheduleDay in expectedSchedule)
                {
                    foreach (TimeSpan time in expectedScheduleDay.OrderBy(p => p.Item2).Select(p => p.Item2))
                    {
                        DateTime nextOccurrence = schedule.GetNextOccurrence(now);
                        Assert.Equal(expectedScheduleDay.Key, nextOccurrence.DayOfWeek);
                        Assert.Equal(time, nextOccurrence.TimeOfDay);
                        now = nextOccurrence + TimeSpan.FromSeconds(1);
                    }
                }
            }
        }
        public void ToString_ReturnsCorrectValue()
        {
            WeeklySchedule schedule = new WeeklySchedule();
            schedule.Add(DayOfWeek.Monday, new TimeSpan(9, 0, 0));
            schedule.Add(DayOfWeek.Wednesday, new TimeSpan(8, 30, 0));
            schedule.Add(DayOfWeek.Wednesday, new TimeSpan(18, 0, 0));
            schedule.Add(DayOfWeek.Friday, new TimeSpan(10, 0, 0));

            Assert.Equal("Weekly: 4 occurrences", schedule.ToString());
        }