private static void FindMissingChaosParameterReferences(ChaosSchedule schedule) { bool hasError = false; var squashedSchedule = ChaosSchedulerUtil.GetSortedChaosScheduleItemsList(schedule); var errorStrings = new List <string>() { StringResources.ChaosScheduler_NonExistentChaosParameter }; foreach (DayOfWeek day in ChaosSchedule.AllDaysOfWeek) { var dayErrors = ChaosSchedulerUtil.FindMissingChaosParameterReferencesForDay(schedule, squashedSchedule[day]); var dayHasError = dayErrors.Count > 0; hasError = hasError || dayHasError; if (dayHasError) { errorStrings.Add(string.Format("{0}: {1}", Enum.GetName(typeof(DayOfWeek), day), JsonConvert.SerializeObject(dayErrors))); } } if (hasError) { throw new System.ArgumentException(string.Join("\n", errorStrings).Replace(", [", ",\n[")); } }
private static void FindScheduleConflicts(ChaosSchedule schedule) { bool hasError = false; var squashedSchedule = ChaosSchedulerUtil.GetSortedChaosScheduleItemsList(schedule); var errorString = new StringBuilder(); foreach (DayOfWeek day in ChaosSchedule.AllDaysOfWeek) { var conflicts = ChaosSchedulerUtil.FindScheduleConflictsForDay(squashedSchedule[day]); bool dayHasError = conflicts.Count > 0; hasError = hasError || dayHasError; if (dayHasError) { errorString.AppendLine(string.Format("{0} :\n{1}", Enum.GetName(typeof(DayOfWeek), day), ChaosSchedulerUtil.PrettyPrintScheduleConflicts(conflicts))); } } if (hasError) { var ret = string.Format("{0}\n \n{1}", errorString.ToString(), StringResources.ChaosScheduler_ScheduleConflict); if (ret.Length > Constants.ErrorMessageMaxCharLength) { var moreString = string.Format("...\n \n{0}\n{1}\n", StringResources.ChaosScheduler_ScheduleConflict, StringResources.ChaosScheduler_MoreScheduleConflicts); ret = ret.Substring(0, Constants.ErrorMessageMaxCharLength - moreString.Length) + moreString; } throw new System.ArgumentException(ret); } }
internal ChaosScheduleEventInstancesEnumerator(ChaosSchedule schedule, DateTime dayInWeek) { /* * ChaosScheduleEventInstancesEnumerator that returns event instances based on the schedule definition. * Schedules repeat on a weekly basis starting with Sunday as the first day of the week. * * In order to generate the event instances: * 1. Determine the starting Sunday of the week for which dayInWeek is in. This is the starting datetime of that week's repetition cycle. * 2. Convert the ChaosScheduleJobs of the schedule to a list of ChaosScheduleItems for each day of the week. * 3. Turn each schedule item into an ChaosScheduleEventInstance by using the day of the week and time as an offset to the starting Sunday * 4. Left join event instances if the start time of the future event is within one minute of the previous event's end time and they use the same ChaosParameters * 5. If there are 2 or more event instances left, join the last item to the first item if the last item's endtime is within a minute of the first item's start time plus a week (next cycle start). * 6. If there is 1 event instance left and it's end time is within one minute of it's start time plus 7 days (one cycle), then this event continues itself and * should be just one long run until the schedule expires, so set the end time to the schedule's expiry date */ this.position = -1; this.eventInstances = new List <ChaosScheduleEventInstance>(); while (dayInWeek.DayOfWeek != DayOfWeek.Sunday) { dayInWeek = dayInWeek.AddDays(-1); } // dayInWeek is now the start of Sunday of the week. dayInWeek = new DateTime(dayInWeek.Year, dayInWeek.Month, dayInWeek.Day, 0, 0, 0, 0, DateTimeKind.Utc); var squashedSchedule = ChaosSchedulerUtil.GetSortedChaosScheduleItemsList(schedule); var fullEventInstances = new List <ChaosScheduleEventInstance>(); foreach (DayOfWeek dayOfWeek in new List <DayOfWeek>() { DayOfWeek.Sunday, DayOfWeek.Monday, DayOfWeek.Tuesday, DayOfWeek.Wednesday, DayOfWeek.Thursday, DayOfWeek.Friday, DayOfWeek.Saturday }) { foreach (ChaosScheduleItem scheduleEvent in squashedSchedule[dayOfWeek]) { fullEventInstances.Add( new ChaosScheduleEventInstance( scheduleEvent.ChaosParameters, schedule.ChaosParametersDictionary[scheduleEvent.ChaosParameters], dayInWeek.Add(new TimeSpan(scheduleEvent.Time.StartTime.Hour, scheduleEvent.Time.StartTime.Minute, 0)), dayInWeek.Add(new TimeSpan(scheduleEvent.Time.EndTime.Hour, scheduleEvent.Time.EndTime.Minute, 0)))); } dayInWeek = dayInWeek.AddDays(1); } foreach (var eventInstance in fullEventInstances) { if (this.eventInstances.Count == 0) { this.eventInstances.Add(eventInstance); } else { var lastEventInstance = this.eventInstances[this.eventInstances.Count - 1]; if (eventInstance.Start - lastEventInstance.End <= new TimeSpan(0, 1, 0) && lastEventInstance.ChaosParametersReferenceName == eventInstance.ChaosParametersReferenceName) { lastEventInstance.End = eventInstance.End; } else { this.eventInstances.Add(eventInstance); } } } if (this.eventInstances.Count > 1) { if (this.eventInstances[0].Start.AddDays(7) - this.eventInstances[this.eventInstances.Count - 1].End <= new TimeSpan(0, 1, 0)) { this.eventInstances[0].Start = this.eventInstances[this.eventInstances.Count - 1].Start.AddDays(-7); this.eventInstances.RemoveAt(this.eventInstances.Count - 1); } } if (this.eventInstances.Count == 1 && this.eventInstances[0].Start.AddDays(7) - this.eventInstances[0].End <= new TimeSpan(0, 1, 0)) { this.eventInstances[0].End = new DateTime(schedule.ExpiryDate.Ticks, DateTimeKind.Utc); } }