none
Recurring appointment does not show up in query RRS feed

  • Question

  • Please Help! 

    Steps to reproduce:

    1. Create an appointment series that recurs daily for 3 days (can be of any length days).

    2.  Open up any occurrence within the series.

    3.  Change the time for the single occurrence to a half an hour later (Can change it to be anytime in the day, doesn't matter)

    4.  Click on "Save"

    RESULT:  The "CalendarItems_ItemChange" event handler gets triggered but the single occurrence that was modified does not show up in the query.  

    Here is the trace output:

    Before changing the appointment time on 8/23:
    Recurring Appt Name: test2pm Date: 8/22/2012 2:00 PM
    Recurring Appt Name: test2pm Date: 8/23/2012 2:00 PM
    Recurring Appt Name: test2pm Date: 8/24/2012 2:00 PM

    After changing the appointment time on 8/23 to 2:30pm:
    Recurring Appt Name: test2pm Date: 8/22/2012 2:00 PM
    A first chance exception of type 'System.Runtime.InteropServices.COMException' occurred in RecurringApptProblem.DLL
    Recurring Appt Name: test2pm Date: 8/24/2012 2:00 PM

    Here is the code:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Xml.Linq;
    using Outlook = Microsoft.Office.Interop.Outlook;
    using Office = Microsoft.Office.Core;
    using System.Runtime.InteropServices;
    namespace RecurringApptProblem
    {
        public partial class ThisAddIn
        {
            private Outlook.Folder m_calendarFolder = null;
            private Outlook.Items m_calendarItems = null;
            private void ThisAddIn_Startup(object sender, System.EventArgs e)
            {
                m_calendarFolder = (Outlook.Folder)Application.Session.GetDefaultFolder(Outlook.OlDefaultFolders.olFolderCalendar);
                                       
                m_calendarItems = m_calendarFolder.Items;
                m_calendarItems.ItemChange += new Outlook.ItemsEvents_ItemChangeEventHandler(CalendarItems_ItemChange);
                m_calendarItems.ItemAdd += new Outlook.ItemsEvents_ItemAddEventHandler(CalendarItems_ItemAdd);
            }
            private void CalendarItems_ItemAdd(object Item)
            {
                Outlook.AppointmentItem apptItem = Item as Outlook.AppointmentItem;
                System.Diagnostics.Debug.WriteLine(String.Format("CalendarItems_ItemAdd - Appt Name: {0} Date: {1}", apptItem.Subject, apptItem.Start.ToShortDateString() + " " + apptItem.Start.ToShortTimeString()));
                if (Item != null)
                {
                    Marshal.ReleaseComObject(Item);
                    Item = null;
                }
                GC.Collect();
                GC.WaitForPendingFinalizers();
            }
            private void CalendarItems_ItemChange(object Item)
            {
                System.Diagnostics.Debug.WriteLine("CalendarItems_ItemChange");
                Outlook.Items olItems = null;
                try
                {
                    DateTime startDate = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, 0, 0, 0);
                    DateTime endDate = DateTime.Now.AddDays(10);
                    string filter =
             String.Format("[Start] >= \"{0}\" AND [Start] <= \"{1}\"", startDate.ToShortDateString(), endDate.ToShortDateString());
                    olItems = m_calendarFolder.Items;
                    olItems.IncludeRecurrences = true;
                    Outlook.Items listItems = olItems.Restrict(filter) as Outlook.Items;
                    if (listItems != null)
                    {
                        Outlook.AppointmentItem apptItem = null;
                        List<Outlook.AppointmentItem> listAppts = new List<Outlook.AppointmentItem>();
                        for (int i = 1; i <= listItems.Count; i++)
                        {
                            try
                            {
                                apptItem = (Outlook.AppointmentItem)listItems[i];
                                if (apptItem != null)
                                {
                                    if (apptItem.IsRecurring)
                                    {
                                        Outlook.RecurrencePattern pattern = apptItem.GetRecurrencePattern();
                                        DateTime date = new DateTime(startDate.Year, startDate.Month, startDate.Day, apptItem.Start.Hour, apptItem.Start.Minute, apptItem.Start.Second);
                                        while (date <= endDate)
                                        {
                                            try
                                            {
                                                Outlook.AppointmentItem recurrenceItem = pattern.GetOccurrence(date);
                                                if (recurrenceItem != null)
                                                {
                                                    System.Diagnostics.Debug.WriteLine(String.Format("Recurring Appt Name: {0} Date: {1}", recurrenceItem.Subject, recurrenceItem.Start.ToShortDateString() + " " + recurrenceItem.Start.ToShortTimeString()));
                                                }
                                            }
                                            catch (Exception e)
                                            {
                                            }
                                            date = date.AddDays(1);
                                        }
                                        Marshal.ReleaseComObject(pattern);
                                        pattern = null;
                                    }
                                    else
                                    {
                                        System.Diagnostics.Debug.WriteLine(String.Format("Appt Name: {0} Date: {1}", apptItem.Subject, apptItem.Start.ToShortDateString() + " " + apptItem.Start.ToShortTimeString()));
                                    }
                                }
                            }
                            catch (Exception e)
                            {
                            }
                        }
                        Marshal.ReleaseComObject(listItems);
                        listItems = null;
                    }
                }
                catch (Exception ex)
                {
                }
                finally
                {
                    if (olItems != null)
                    {
                        Marshal.ReleaseComObject(olItems);
                        olItems = null;
                    }
                    if (Item != null)
                    {
                        Marshal.ReleaseComObject(Item);
                        Item = null;
                    }
                    GC.Collect();
                    GC.WaitForPendingFinalizers();
                }
            }
                              
            private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
            {
            }
            #region VSTO generated code
            /// <summary>
            /// Required method for Designer support - do not modify
            /// the contents of this method with the code editor.
            /// </summary>
            private void InternalStartup()
            {
                this.Startup += new System.EventHandler(ThisAddIn_Startup);
                this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
            }
            
            #endregion
        }
    }


    • Edited by alexkfh Wednesday, August 22, 2012 6:34 PM
    Wednesday, August 22, 2012 6:32 PM

Answers

  • Individual occurences of a recurring series don't actually exist as individual entities, except where they've been modified or deleted. Then they exist as members of the Exceptions collection.
     
    In all cases the master appointment is the only one directly exposed.
     
    If IsRecurring == true the appointment is a recurring one. You use appointment.GetRecurrencePattern(), which is used to get the pattern start and end, number of instances, and so on. You then calculate the next item in the series using the pattern, and use pattern.GetOccurrence() to get that occurrence. If you get an exception or a null object you open the pattern.Exceptions collection and find one where the OriginalDate == the date you calculated. An exception usually means a deleted instance, those have Deleted == true on the individual Exception object.
     
    Nothing is easy when it comes to recurring items.

    --
    Ken Slovak
    [MVP-Outlook]
    http://www.slovaktech.com
    Author: Professional Programming Outlook 2007
    "alexkfh" <=?utf-8?B?YWxleGtmaA==?=> wrote in message news:c3cd627d-9547-477f-a07f-ae738e29561d...

    Please Help! 

    Steps to reproduce:

    1. Create an appointment series that recurs daily for 3 days (can be of any length days).

    2.  Open up any occurrence within the series.

    3.  Change the time for the single occurrence to a half an hour later (Can change it to be anytime in the day, doesn't matter)

    4.  Click on "Save"

    RESULT:  The "CalendarItems_ItemChange" event handler gets triggered but the single occurrence that was modified does not show up in the query.  

    Here is the trace output:

    Before changing the appointment time on 8/23:
    Recurring Appt Name: test2pm Date: 8/22/2012 2:00 PM
    Recurring Appt Name: test2pm Date: 8/23/2012 2:00 PM
    Recurring Appt Name: test2pm Date: 8/24/2012 2:00 PM

    After changing the appointment time on 8/23 to 2:30pm:
    Recurring Appt Name: test2pm Date: 8/22/2012 2:00 PM
    A first chance exception of type 'System.Runtime.InteropServices.COMException' occurred in RecurringApptProblem.DLL
    Recurring Appt Name: test2pm Date: 8/24/2012 2:00 PM

    Here is the code:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Xml.Linq;
    using Outlook = Microsoft.Office.Interop.Outlook;
    using Office = Microsoft.Office.Core;
    using System.Runtime.InteropServices;
    namespace RecurringApptProblem
    {
        public partial class ThisAddIn
        {
            private Outlook.Folder m_calendarFolder = null;
            private Outlook.Items m_calendarItems = null;
            private void ThisAddIn_Startup(object sender, System.EventArgs e)
            {
                m_calendarFolder = (Outlook.Folder)Application.Session.GetDefaultFolder(Outlook.OlDefaultFolders.olFolderCalendar);
                                       
                m_calendarItems = m_calendarFolder.Items;
                m_calendarItems.ItemChange += new Outlook.ItemsEvents_ItemChangeEventHandler(CalendarItems_ItemChange);
                m_calendarItems.ItemAdd += new Outlook.ItemsEvents_ItemAddEventHandler(CalendarItems_ItemAdd);
            }
            private void CalendarItems_ItemAdd(object Item)
            {
                Outlook.AppointmentItem apptItem = Item as Outlook.AppointmentItem;
                System.Diagnostics.Debug.WriteLine(String.Format("CalendarItems_ItemAdd - Appt Name: {0} Date: {1}", apptItem.Subject, apptItem.Start.ToShortDateString() + " " + apptItem.Start.ToShortTimeString()));
                if (Item != null)
                {
                    Marshal.ReleaseComObject(Item);
                    Item = null;
                }
                GC.Collect();
                GC.WaitForPendingFinalizers();
            }
            private void CalendarItems_ItemChange(object Item)
            {
                System.Diagnostics.Debug.WriteLine("CalendarItems_ItemChange");
                Outlook.Items olItems = null;
                try
                {
                    DateTime startDate = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, 0, 0, 0);
                    DateTime endDate = DateTime.Now.AddDays(10);
                    string filter =
             String.Format("[Start] >= \"{0}\" AND [Start] <= \"{1}\"", startDate.ToShortDateString(), endDate.ToShortDateString());
                    olItems = m_calendarFolder.Items;
                    olItems.IncludeRecurrences = true;
                    Outlook.Items listItems = olItems.Restrict(filter) as Outlook.Items;
                    if (listItems != null)
                    {
                        Outlook.AppointmentItem apptItem = null;
                        List<Outlook.AppointmentItem> listAppts = new List<Outlook.AppointmentItem>();
                        for (int i = 1; i <= listItems.Count; i++)
                        {
                            try
                            {
                                apptItem = (Outlook.AppointmentItem)listItems[i];
                                if (apptItem != null)
                                {
                                    if (apptItem.IsRecurring)
                                    {
                                        Outlook.RecurrencePattern pattern = apptItem.GetRecurrencePattern();
                                        DateTime date = new DateTime(startDate.Year, startDate.Month, startDate.Day, apptItem.Start.Hour, apptItem.Start.Minute, apptItem.Start.Second);
                                        while (date <= endDate)
                                        {
                                            try
                                            {
                                                Outlook.AppointmentItem recurrenceItem = pattern.GetOccurrence(date);
                                                if (recurrenceItem != null)
                                                {
                                                    System.Diagnostics.Debug.WriteLine(String.Format("Recurring Appt Name: {0} Date: {1}", recurrenceItem.Subject, recurrenceItem.Start.ToShortDateString() + " " + recurrenceItem.Start.ToShortTimeString()));
                                                }
                                            }
                                            catch (Exception e)
                                            {
                                            }
                                            date = date.AddDays(1);
                                        }
                                        Marshal.ReleaseComObject(pattern);
                                        pattern = null;
                                    }
                                    else
                                    {
                                        System.Diagnostics.Debug.WriteLine(String.Format("Appt Name: {0} Date: {1}", apptItem.Subject, apptItem.Start.ToShortDateString() + " " + apptItem.Start.ToShortTimeString()));
                                    }
                                }
                            }
                            catch (Exception e)
                            {
                            }
                        }
                        Marshal.ReleaseComObject(listItems);
                        listItems = null;
                    }
                }
                catch (Exception ex)
                {
                }
                finally
                {
                    if (olItems != null)
                    {
                        Marshal.ReleaseComObject(olItems);
                        olItems = null;
                    }
                    if (Item != null)
                    {
                        Marshal.ReleaseComObject(Item);
                        Item = null;
                    }
                    GC.Collect();
                    GC.WaitForPendingFinalizers();
                }
            }
                              
            private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
            {
            }
            #region VSTO generated code
            /// <summary>
            /// Required method for Designer support - do not modify
            /// the contents of this method with the code editor.
            /// </summary>
            private void InternalStartup()
            {
                this.Startup += new System.EventHandler(ThisAddIn_Startup);
                this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
            }
            
            #endregion
        }
    }



    Ken Slovak MVP - Outlook
    • Marked as answer by alexkfh Thursday, August 23, 2012 6:15 PM
    Wednesday, August 22, 2012 7:15 PM

All replies

  • Individual occurences of a recurring series don't actually exist as individual entities, except where they've been modified or deleted. Then they exist as members of the Exceptions collection.
     
    In all cases the master appointment is the only one directly exposed.
     
    If IsRecurring == true the appointment is a recurring one. You use appointment.GetRecurrencePattern(), which is used to get the pattern start and end, number of instances, and so on. You then calculate the next item in the series using the pattern, and use pattern.GetOccurrence() to get that occurrence. If you get an exception or a null object you open the pattern.Exceptions collection and find one where the OriginalDate == the date you calculated. An exception usually means a deleted instance, those have Deleted == true on the individual Exception object.
     
    Nothing is easy when it comes to recurring items.

    --
    Ken Slovak
    [MVP-Outlook]
    http://www.slovaktech.com
    Author: Professional Programming Outlook 2007
    "alexkfh" <=?utf-8?B?YWxleGtmaA==?=> wrote in message news:c3cd627d-9547-477f-a07f-ae738e29561d...

    Please Help! 

    Steps to reproduce:

    1. Create an appointment series that recurs daily for 3 days (can be of any length days).

    2.  Open up any occurrence within the series.

    3.  Change the time for the single occurrence to a half an hour later (Can change it to be anytime in the day, doesn't matter)

    4.  Click on "Save"

    RESULT:  The "CalendarItems_ItemChange" event handler gets triggered but the single occurrence that was modified does not show up in the query.  

    Here is the trace output:

    Before changing the appointment time on 8/23:
    Recurring Appt Name: test2pm Date: 8/22/2012 2:00 PM
    Recurring Appt Name: test2pm Date: 8/23/2012 2:00 PM
    Recurring Appt Name: test2pm Date: 8/24/2012 2:00 PM

    After changing the appointment time on 8/23 to 2:30pm:
    Recurring Appt Name: test2pm Date: 8/22/2012 2:00 PM
    A first chance exception of type 'System.Runtime.InteropServices.COMException' occurred in RecurringApptProblem.DLL
    Recurring Appt Name: test2pm Date: 8/24/2012 2:00 PM

    Here is the code:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Xml.Linq;
    using Outlook = Microsoft.Office.Interop.Outlook;
    using Office = Microsoft.Office.Core;
    using System.Runtime.InteropServices;
    namespace RecurringApptProblem
    {
        public partial class ThisAddIn
        {
            private Outlook.Folder m_calendarFolder = null;
            private Outlook.Items m_calendarItems = null;
            private void ThisAddIn_Startup(object sender, System.EventArgs e)
            {
                m_calendarFolder = (Outlook.Folder)Application.Session.GetDefaultFolder(Outlook.OlDefaultFolders.olFolderCalendar);
                                       
                m_calendarItems = m_calendarFolder.Items;
                m_calendarItems.ItemChange += new Outlook.ItemsEvents_ItemChangeEventHandler(CalendarItems_ItemChange);
                m_calendarItems.ItemAdd += new Outlook.ItemsEvents_ItemAddEventHandler(CalendarItems_ItemAdd);
            }
            private void CalendarItems_ItemAdd(object Item)
            {
                Outlook.AppointmentItem apptItem = Item as Outlook.AppointmentItem;
                System.Diagnostics.Debug.WriteLine(String.Format("CalendarItems_ItemAdd - Appt Name: {0} Date: {1}", apptItem.Subject, apptItem.Start.ToShortDateString() + " " + apptItem.Start.ToShortTimeString()));
                if (Item != null)
                {
                    Marshal.ReleaseComObject(Item);
                    Item = null;
                }
                GC.Collect();
                GC.WaitForPendingFinalizers();
            }
            private void CalendarItems_ItemChange(object Item)
            {
                System.Diagnostics.Debug.WriteLine("CalendarItems_ItemChange");
                Outlook.Items olItems = null;
                try
                {
                    DateTime startDate = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, 0, 0, 0);
                    DateTime endDate = DateTime.Now.AddDays(10);
                    string filter =
             String.Format("[Start] >= \"{0}\" AND [Start] <= \"{1}\"", startDate.ToShortDateString(), endDate.ToShortDateString());
                    olItems = m_calendarFolder.Items;
                    olItems.IncludeRecurrences = true;
                    Outlook.Items listItems = olItems.Restrict(filter) as Outlook.Items;
                    if (listItems != null)
                    {
                        Outlook.AppointmentItem apptItem = null;
                        List<Outlook.AppointmentItem> listAppts = new List<Outlook.AppointmentItem>();
                        for (int i = 1; i <= listItems.Count; i++)
                        {
                            try
                            {
                                apptItem = (Outlook.AppointmentItem)listItems[i];
                                if (apptItem != null)
                                {
                                    if (apptItem.IsRecurring)
                                    {
                                        Outlook.RecurrencePattern pattern = apptItem.GetRecurrencePattern();
                                        DateTime date = new DateTime(startDate.Year, startDate.Month, startDate.Day, apptItem.Start.Hour, apptItem.Start.Minute, apptItem.Start.Second);
                                        while (date <= endDate)
                                        {
                                            try
                                            {
                                                Outlook.AppointmentItem recurrenceItem = pattern.GetOccurrence(date);
                                                if (recurrenceItem != null)
                                                {
                                                    System.Diagnostics.Debug.WriteLine(String.Format("Recurring Appt Name: {0} Date: {1}", recurrenceItem.Subject, recurrenceItem.Start.ToShortDateString() + " " + recurrenceItem.Start.ToShortTimeString()));
                                                }
                                            }
                                            catch (Exception e)
                                            {
                                            }
                                            date = date.AddDays(1);
                                        }
                                        Marshal.ReleaseComObject(pattern);
                                        pattern = null;
                                    }
                                    else
                                    {
                                        System.Diagnostics.Debug.WriteLine(String.Format("Appt Name: {0} Date: {1}", apptItem.Subject, apptItem.Start.ToShortDateString() + " " + apptItem.Start.ToShortTimeString()));
                                    }
                                }
                            }
                            catch (Exception e)
                            {
                            }
                        }
                        Marshal.ReleaseComObject(listItems);
                        listItems = null;
                    }
                }
                catch (Exception ex)
                {
                }
                finally
                {
                    if (olItems != null)
                    {
                        Marshal.ReleaseComObject(olItems);
                        olItems = null;
                    }
                    if (Item != null)
                    {
                        Marshal.ReleaseComObject(Item);
                        Item = null;
                    }
                    GC.Collect();
                    GC.WaitForPendingFinalizers();
                }
            }
                              
            private void ThisAddIn_Shutdown(object sender, System.EventArgs e)
            {
            }
            #region VSTO generated code
            /// <summary>
            /// Required method for Designer support - do not modify
            /// the contents of this method with the code editor.
            /// </summary>
            private void InternalStartup()
            {
                this.Startup += new System.EventHandler(ThisAddIn_Startup);
                this.Shutdown += new System.EventHandler(ThisAddIn_Shutdown);
            }
            
            #endregion
        }
    }



    Ken Slovak MVP - Outlook
    • Marked as answer by alexkfh Thursday, August 23, 2012 6:15 PM
    Wednesday, August 22, 2012 7:15 PM
  • Thanks Ken for your quick response!

    I tried iterating over the Exception collection class and none of them appear to be appointment item objects.   Am I doing this correctly?   After I modify a single occurence this code below is entered but "recurrenceItem" is always null. 

           System.Collections.IEnumerator iter = pattern.Exceptions.GetEnumerator();
                                                while (iter.MoveNext())
                                                {
                                                    Outlook.AppointmentItem recurrenceItem = iter.Current as Outlook.AppointmentItem;
                                                    if (recurrenceItem != null)
                                                    {
                                                        if (recurrenceItem.Start.Month == date.Month &&
                                                           recurrenceItem.Start.Day == date.Day &&
                                                            recurrenceItem.Start.Year == date.Year)
                                                        {
                                                            System.Diagnostics.Debug.WriteLine(String.Format("Recurring Appt Name3: {0} Date: {1}", recurrenceItem.Subject, recurrenceItem.Start.ToShortDateString() + " " + recurrenceItem.Start.ToShortTimeString()));
                                                        }
                                                    }
                                                }

    Thursday, August 23, 2012 5:12 PM
  • Exceptions collection contains Exception objects. Each of them has OriginalDate property and AppointmentItem property that points to appointmentitem for that exception.
    Thursday, August 23, 2012 5:57 PM
  • Each member of the Exceptions collection is an Exception object. Exception.AppointmentItem is used to get a reference to the related appointment.

    --
    Ken Slovak
    [MVP-Outlook]
    http://www.slovaktech.com
    Author: Professional Programming Outlook 2007
    "alexkfh" <=?utf-8?B?YWxleGtmaA==?=> wrote in message news:e5537bae-d7a8-474b-b6e3-0082a0e3c356...

    Thanks Ken for your quick response!

    I tried iterating over the Exception collection class and none of them appear to be appointment item objects.   Am I doing this correctly?   After I modify a single occurence this code below is entered but "recurrenceItem" is always null. 

           System.Collections.IEnumerator iter = pattern.Exceptions.GetEnumerator();
                                                while (iter.MoveNext())
                                                {
                                                    Outlook.AppointmentItem recurrenceItem = iter.Current as Outlook.AppointmentItem;
                                                    if (recurrenceItem != null)
                                                    {
                                                        if (recurrenceItem.Start.Month == date.Month &&
                                                           recurrenceItem.Start.Day == date.Day &&
                                                            recurrenceItem.Start.Year == date.Year)
                                                        {
                                                            System.Diagnostics.Debug.WriteLine(String.Format("Recurring Appt Name3: {0} Date: {1}", recurrenceItem.Subject, recurrenceItem.Start.ToShortDateString() + " " + recurrenceItem.Start.ToShortTimeString()));
                                                        }
                                                    }
                                                }


    Ken Slovak MVP - Outlook
    Thursday, August 23, 2012 5:59 PM
  • Thanks everyone!  Problem is fixed!
    Thursday, August 23, 2012 6:16 PM