private static void ParseFreeBusyRaster(
            ExchangeUserDict users,
            DateTime baseTime,
            string emailAddress,
            string freeBusyRaster,
            Dictionary <ExchangeUser, FreeBusy> result)
        {
            ExchangeUser user = null;

            if (emailAddress == null || !users.TryGetValue(emailAddress, out user))
            {
                return;
            }

            FreeBusy freeBusy = new FreeBusy();

            freeBusy.User = user;

            FreeBusyConverter.ParseRasterFreeBusy(baseTime,
                                                  kFreeBusyInterval,
                                                  freeBusyRaster,
                                                  freeBusy);

            FreeBusyConverter.CondenseFreeBusyTimes(freeBusy.All);

            result[user] = freeBusy;
        }
Exemple #2
0
        public void TestFastFreeBusyLookup()
        {
            _requestor.ValidMethod  = Method.GET;
            _requestor.ResponseBody = getResponseXML("FreeBusyResponse.xml");

            // These dates correspond to when the response XML was captured
            DateTime      start = DateUtil.ParseDateToUtc("2007-12-25T01:46:50Z");
            DateTime      end   = DateUtil.ParseDateToUtc("2008-01-08T01:42:50Z");
            DateTimeRange range = new DateTimeRange(start, end);

            ExchangeUserDict users = new ExchangeUserDict();

            users.Add(_user.Email, _user);

            Dictionary <ExchangeUser, FreeBusy> result = _webdav.LoadFreeBusy(exchangeServer,
                                                                              users,
                                                                              range);

            Assert.AreEqual(1, result.Count);

            FreeBusy fb = result[_user];

            Assert.AreEqual(6, fb.All.Count);
            Assert.AreEqual(6, fb.Busy.Count);
            Assert.AreEqual(0, fb.OutOfOffice.Count);
            Assert.AreEqual(0, fb.Tentative.Count);

            //dumpFreeBusy(fb.Busy);

            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T18:00:00Z"), fb.Busy[0].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T18:30:00Z"), fb.Busy[0].End);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T20:30:00Z"), fb.Busy[1].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T21:00:00Z"), fb.Busy[1].End);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T17:30:00Z"), fb.Busy[2].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T18:00:00Z"), fb.Busy[2].End);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T21:00:00Z"), fb.Busy[3].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T21:30:00Z"), fb.Busy[3].End);

            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T18:00:00Z"), fb.All[0].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T18:30:00Z"), fb.All[0].End);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T20:30:00Z"), fb.All[1].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-26T21:00:00Z"), fb.All[1].End);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T17:30:00Z"), fb.All[2].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T18:00:00Z"), fb.All[2].End);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T21:00:00Z"), fb.All[3].Start);
            Assert.AreEqual(DateUtil.ParseDateToUtc("2007-12-31T21:30:00Z"), fb.All[3].End);
        }
 private static void ClearFreeBusy(
     FreeBusy freeBusy)
 {
     freeBusy.All.Clear();
     freeBusy.Busy.Clear();
     freeBusy.Tentative.Clear();
     freeBusy.OutOfOffice.Clear();
 }
        public void TestParseRasterFreeBusy()
        {
            DateTime startDate = new DateTime(2008, 05, 1, 10, 0, 0, DateTimeKind.Utc);
            DateTime date1 = new DateTime(2008, 05, 1, 10, 15, 0, DateTimeKind.Utc);
            DateTime date2 = new DateTime(2008, 05, 1, 10, 30, 0, DateTimeKind.Utc);
            DateTime date3 = new DateTime(2008, 05, 1, 10, 45, 0, DateTimeKind.Utc);
            DateTime date4 = new DateTime(2008, 05, 1, 11, 0, 0, DateTimeKind.Utc);
            DateTime date5 = new DateTime(2008, 05, 1, 11, 15, 0, DateTimeKind.Utc);
            FreeBusy freeBusy = new FreeBusy();

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "1", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 0);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 1);
            Assert.AreEqual(freeBusy.Tentative[0].Start, startDate);
            Assert.AreEqual(freeBusy.Tentative[0].End, date1);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "2", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 1);
            Assert.AreEqual(freeBusy.Busy.Count, 1);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            Assert.AreEqual(freeBusy.All[0].Start, startDate);
            Assert.AreEqual(freeBusy.All[0].End, date1);
            Assert.AreEqual(freeBusy.Busy[0].Start, startDate);
            Assert.AreEqual(freeBusy.Busy[0].End, date1);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "3", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 1);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 1);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            Assert.AreEqual(freeBusy.All[0].Start, startDate);
            Assert.AreEqual(freeBusy.All[0].End, date1);
            Assert.AreEqual(freeBusy.OutOfOffice[0].Start, startDate);
            Assert.AreEqual(freeBusy.OutOfOffice[0].End, date1);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "4", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 0);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "11", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 0);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 1);
            Assert.AreEqual(freeBusy.Tentative[0].Start, startDate);
            Assert.AreEqual(freeBusy.Tentative[0].End, date2);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "22", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 1);
            Assert.AreEqual(freeBusy.Busy.Count, 1);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            Assert.AreEqual(freeBusy.All[0].Start, startDate);
            Assert.AreEqual(freeBusy.All[0].End, date2);
            Assert.AreEqual(freeBusy.Busy[0].Start, startDate);
            Assert.AreEqual(freeBusy.Busy[0].End, date2);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "33", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 1);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 1);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            Assert.AreEqual(freeBusy.All[0].Start, startDate);
            Assert.AreEqual(freeBusy.All[0].End, date2);
            Assert.AreEqual(freeBusy.OutOfOffice[0].Start, startDate);
            Assert.AreEqual(freeBusy.OutOfOffice[0].End, date2);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "44", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 0);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "0114", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 0);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 1);
            Assert.AreEqual(freeBusy.Tentative[0].Start, date1);
            Assert.AreEqual(freeBusy.Tentative[0].End, date3);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "0224", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 1);
            Assert.AreEqual(freeBusy.Busy.Count, 1);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            Assert.AreEqual(freeBusy.All[0].Start, date1);
            Assert.AreEqual(freeBusy.All[0].End, date3);
            Assert.AreEqual(freeBusy.Busy[0].Start, date1);
            Assert.AreEqual(freeBusy.Busy[0].End, date3);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "0334", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 1);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 1);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            Assert.AreEqual(freeBusy.All[0].Start, date1);
            Assert.AreEqual(freeBusy.All[0].End, date3);
            Assert.AreEqual(freeBusy.OutOfOffice[0].Start, date1);
            Assert.AreEqual(freeBusy.OutOfOffice[0].End, date3);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "0440", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 0);
            Assert.AreEqual(freeBusy.Busy.Count, 0);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 0);
            Assert.AreEqual(freeBusy.Tentative.Count, 0);
            ClearFreeBusy(freeBusy);

            FreeBusyConverter.ParseRasterFreeBusy(startDate, 15, "40312", freeBusy);
            Assert.AreEqual(freeBusy.All.Count, 2);
            Assert.AreEqual(freeBusy.Busy.Count, 1);
            Assert.AreEqual(freeBusy.OutOfOffice.Count, 1);
            Assert.AreEqual(freeBusy.Tentative.Count, 1);
            Assert.AreEqual(freeBusy.All[0].Start, date2);
            Assert.AreEqual(freeBusy.All[0].End, date3);
            Assert.AreEqual(freeBusy.All[1].Start, date4);
            Assert.AreEqual(freeBusy.All[1].End, date5);
            Assert.AreEqual(freeBusy.Busy[0].Start, date4);
            Assert.AreEqual(freeBusy.Busy[0].End, date5);
            Assert.AreEqual(freeBusy.Tentative[0].Start, date3);
            Assert.AreEqual(freeBusy.Tentative[0].End, date4);
            Assert.AreEqual(freeBusy.OutOfOffice[0].Start, date2);
            Assert.AreEqual(freeBusy.OutOfOffice[0].End, date3);
            ClearFreeBusy(freeBusy);
        }
        private static void ParseFreeBusyRaster(
            ExchangeUserDict users,
            DateTime baseTime,
            string emailAddress,
            string freeBusyRaster,
            Dictionary<ExchangeUser, FreeBusy> result)
        {
            ExchangeUser user = null;

            if (emailAddress == null || !users.TryGetValue(emailAddress, out user))
            {
                return;
            }

            FreeBusy freeBusy = new FreeBusy();
            freeBusy.User = user;

            FreeBusyConverter.ParseRasterFreeBusy(baseTime,
                                                  kFreeBusyInterval,
                                                  freeBusyRaster,
                                                  freeBusy);

            FreeBusyConverter.CondenseFreeBusyTimes(freeBusy.All);

            result[user] = freeBusy;
        }
        private FreeBusy createFreeBusy(ExchangeUser user)
        {
            FreeBusy result = new FreeBusy();
            result.User = user;

            result.All = _freeBusy.GetRange(0, _freeBusy.Count);
            result.Busy = _freeBusy.GetRange(0, _freeBusy.Count);
            return result;
        }
        private static void RecordFreeBusyInterval(
            DateTime baseTime,
            BusyStatus state,
            int freeBusyInterval,
            int start,
            int end,
            FreeBusy freeBusy)
        {
            DateTime eventStart = baseTime.AddMinutes(start * freeBusyInterval);
            DateTime eventEnd = baseTime.AddMinutes(end * freeBusyInterval);
            DateTimeRange range = new DateTimeRange(eventStart, eventEnd);

            // Handle the state
            switch (state)
            {
                default:
                case BusyStatus.Free:
                    // We don't record these
                    break;

                case BusyStatus.Busy:
                    // Busy is recorded in busy and all
                    freeBusy.All.Add(range);
                    freeBusy.Busy.Add(range);
                    break;

                case BusyStatus.Tentative:
                    freeBusy.Tentative.Add(range);
                    break;

                case BusyStatus.OutOfOffice:
                    // OOO is recorded in out of office and all
                    freeBusy.All.Add(range);
                    freeBusy.OutOfOffice.Add(range);
                    break;
            }
        }
        /// <summary>
        /// Converst Exchange raster free busy string to FreeBusy
        /// </summary>
        /// <param name="baseTime">The start date of the free busy</param>
        /// <param name="freeBusyInterval">The granularity of the free busy in minutes</param>
        /// <param name="freeBusyRaster">The raster to parse</param>
        /// <param name="freeBusy">The free busy result</param>
        /// <returns>void</returns>
        public static void ParseRasterFreeBusy(
            DateTime baseTime,
            int freeBusyInterval,
            string freeBusyRaster,
            FreeBusy freeBusy)
        {
            BusyStatus oldState = BusyStatus.Free;
            int startRun = 0;
            int idx = 0;

            if (string.IsNullOrEmpty(freeBusyRaster))
            {
                return;
            }

            log.DebugFormat("Parsing the raster {0}", freeBusyRaster);

            foreach (char current in freeBusyRaster)
            {
                BusyStatus newState = ConvertRasterToFreeBusy(current);

                if (newState != oldState)
                {
                    RecordFreeBusyInterval(baseTime,
                                           oldState,
                                           freeBusyInterval,
                                           startRun,
                                           idx,
                                           freeBusy);

                    oldState = newState;
                    startRun = idx;
                }

                idx++;
            }

            RecordFreeBusyInterval(baseTime,
                                   oldState,
                                   freeBusyInterval,
                                   startRun,
                                   idx,
                                   freeBusy);

            log.DebugFormat("Parsed the raster into {0} busy and {1} tentative ranges",
                            freeBusy.Busy.Count,
                            freeBusy.Tentative.Count);

        }
        /// <summary>
        /// Combines the free busy and appointment blocks supplied to the exchange user object
        /// If no appointments are supplied the user will still have free busy time blocks assigned
        /// to them, with a null appointment assigned to the free busy time.
        /// </summary>
        /// <param name="exchangeUser">Exchange users to apply freeBusy and appointments</param>
        /// <param name="freeBusy">The collection of FreeBusy blocks to assign to exchangeUser</param>
        /// <param name="appointments">The collection of appointment blocks to assign to exchangeUser</param>
        /// <param name="window">Window to merge for</param>
        protected void MergeFreeBusyWithAppointments(
            ExchangeUser exchangeUser,
            FreeBusy freeBusy,
            List<Appointment> appointments,
            DateTimeRange window)
        {
            using (BlockTimer bt = new BlockTimer("MergeFreeBusyWithAppointments"))
            {
                IntervalTree<FreeBusyTimeBlock> busyIntervals =
                    new IntervalTree<FreeBusyTimeBlock>();
                FreeBusyCollection busyTimes = new FreeBusyCollection();
                int appointmentsCount = 0;
                List<DateTimeRange> combinedTimes =
                    FreeBusyConverter.MergeFreeBusyLists(freeBusy.All, freeBusy.Tentative);

                /* Add the date ranges from each collection in the FreeBusy object */
                ConvertFreeBusyToBlocks(window,
                                        combinedTimes,
                                        busyTimes,
                                        busyIntervals);

                if (appointments != null && appointments.Count > 0)
                {
                    appointmentsCount = appointments.Count;
                    foreach (Appointment appt in appointments)
                    {
                        log.DebugFormat("Appt \"{0}\" {1} {2} response = {3} status = {4} busy = {5}",
                                        appt.Subject,
                                        appt.Range,
                                        appt.StartDate.Kind,
                                        appt.ResponseStatus,
                                        appt.MeetingStatus,
                                        appt.BusyStatus);

                        if (appt.BusyStatus == BusyStatus.Free)
                        {
                            continue;
                        }

                        DateTimeRange range = new DateTimeRange(appt.StartDate, appt.EndDate);
                        List<FreeBusyTimeBlock> result =
                            busyIntervals.FindAll(range, IntervalTreeMatch.Overlap);

                        log.DebugFormat("Found {0} ranges overlap {1}", result.Count, range);

                        foreach (FreeBusyTimeBlock block in result)
                        {
                            log.DebugFormat("Adding \"{0}\" to FB {1} {2}",
                                            appt.Subject,
                                            block.Range,
                                            block.StartDate.Kind);
                            block.Appointments.Add(appt);
                        }

                        busyTimes.Appointments.Add(appt);
                    }
                }

                foreach (FreeBusyTimeBlock block in busyTimes.Values)
                {
                    block.Appointments.Sort(CompareAppointmentsByRanges);
                }

                log.InfoFormat("Merge Result of {0} + Appointment {1} -> {2}",
                               combinedTimes.Count,
                               appointmentsCount,
                               busyTimes.Count);

                /* Assign the data structure to the exchange user */
                exchangeUser.BusyTimes = busyTimes;
            }
        }