/// <summary>
        /// Define the configuration of a recurring meeting.
        /// </summary>
        /// <param name="basePattern">A recurrence pattern.</param>
        /// <param name="range">A recurrence range.</param>
        /// <returns>A calendar item to be created.</returns>
        private CalendarItemType DefineRecurringMeeting(RecurrencePatternBaseType basePattern, RecurrenceRangeBaseType range)
        {
            CalendarItemType meetingItem = null;
            if (basePattern != null && range != null)
            {
                meetingItem = new CalendarItemType();

                // Define common property.
                meetingItem.UID = Guid.NewGuid().ToString();
                meetingItem.Subject = Common.GenerateResourceName(this.Site, Common.GetConfigurationPropertyValue("MeetingSubject", this.Site));
                meetingItem.Location = this.Location;
                meetingItem.IsResponseRequested = false;
                meetingItem.IsResponseRequestedSpecified = true;
                meetingItem.ConferenceType = 1;
                meetingItem.ConferenceTypeSpecified = true;
                meetingItem.AllowNewTimeProposal = true;
                meetingItem.AllowNewTimeProposalSpecified = true;
                meetingItem.LegacyFreeBusyStatus = LegacyFreeBusyType.OOF;
                meetingItem.LegacyFreeBusyStatusSpecified = true;

                DateTime startTime = DateTime.UtcNow.AddHours(3);
                meetingItem.Start = startTime;
                meetingItem.StartSpecified = true;

                DateTime endTime = startTime.AddHours(1);
                meetingItem.End = endTime;
                meetingItem.EndSpecified = true;

                // Set recurrence with specified pattern and range values.
                RecurrenceType recurrence = new RecurrenceType();
                AbsoluteYearlyRecurrencePatternType patternAbsoluteYearlyRecurrence = null;

                IntervalRecurrencePatternBaseType patternIntervalRecurrence = basePattern as IntervalRecurrencePatternBaseType;
                if (patternIntervalRecurrence != null)
                {
                    // Set the pattern's Interval.
                    patternIntervalRecurrence.Interval = this.PatternInterval;
                    recurrence.Item = patternIntervalRecurrence;
                }
                else
                {
                    patternAbsoluteYearlyRecurrence = basePattern as AbsoluteYearlyRecurrencePatternType;
                    if (patternAbsoluteYearlyRecurrence != null)
                    {
                        recurrence.Item = patternAbsoluteYearlyRecurrence;
                    }
                    else
                    {
                        RelativeYearlyRecurrencePatternType patternRelativeYearlyRecurrence = basePattern as RelativeYearlyRecurrencePatternType;
                        if (patternRelativeYearlyRecurrence != null)
                        {
                            recurrence.Item = patternRelativeYearlyRecurrence;
                        }
                    }
                }

                // Set the range's StartDate.
                DateTime startDate = startTime.AddMonths(1);
                range.StartDate = new DateTime(startDate.Year, startDate.Month, startDate.Day, 0, 0, 0, DateTimeKind.Utc);

                EndDateRecurrenceRangeType endDateRange = range as EndDateRecurrenceRangeType;
                if (endDateRange != null)
                {
                    if (patternAbsoluteYearlyRecurrence != null)
                    {
                        endDateRange.EndDate = range.StartDate.AddYears(8);
                    }
                    else
                    {
                        endDateRange.EndDate = range.StartDate.AddMonths(8);
                    }

                    recurrence.Item1 = endDateRange;
                }
                else
                {
                    recurrence.Item1 = range;
                }

                meetingItem.Recurrence = recurrence;

                meetingItem.RequiredAttendees = new AttendeeType[] { GetAttendeeOrResource(this.AttendeeEmailAddress) };
                meetingItem.Resources = new AttendeeType[] { GetAttendeeOrResource(this.RoomEmailAddress) };
            }

            return meetingItem;
        }
        public void MSOXWSMTGS_S01_TC20_CreateItemErrorCalendarInvalidDayForWeeklyRecurrence()
        {
            Site.Assume.IsTrue(Common.IsRequirementEnabled(12052, this.Site), "Exchange 2007, Exchange 2010 and Exchange 2013 do not support ErrorCalendarInvalidDayForWeeklyRecurrence.");

            #region Define a calendar item
            int timeInterval = this.TimeInterval;
            DateTime startTime = DateTime.Now.AddHours(timeInterval);

            WeeklyRecurrencePatternType pattern = new WeeklyRecurrencePatternType();
            pattern.DaysOfWeek = "Random";
            IntervalRecurrencePatternBaseType patternIntervalRecurrence = pattern as IntervalRecurrencePatternBaseType;
            patternIntervalRecurrence.Interval = this.PatternInterval;
            RecurrenceType recurrence = new RecurrenceType();
            recurrence.Item = patternIntervalRecurrence;
            EndDateRecurrenceRangeType endDateRange = new EndDateRecurrenceRangeType();
            DateTime startDate = startTime.AddMonths(1);
            endDateRange.StartDate = new DateTime(startDate.Year, startDate.Month, startDate.Day, 0, 0, 0, DateTimeKind.Utc);
            endDateRange.EndDate = endDateRange.StartDate.AddMonths(8);
            recurrence.Item1 = endDateRange;

            CalendarItemType calendarItem = new CalendarItemType();
            calendarItem.UID = Guid.NewGuid().ToString();
            calendarItem.Subject = this.Subject;
            calendarItem.Start = startTime;
            calendarItem.StartSpecified = true;
            timeInterval++;
            calendarItem.End = startTime.AddHours(timeInterval);
            calendarItem.EndSpecified = true;
            calendarItem.Location = this.Location;
            calendarItem.Recurrence = new RecurrenceType();
            calendarItem.Recurrence = recurrence;
            calendarItem.RequiredAttendees = new AttendeeType[] { GetAttendeeOrResource(this.AttendeeEmailAddress) };
            calendarItem.OptionalAttendees = new AttendeeType[] { GetAttendeeOrResource(this.OrganizerEmailAddress) };
            #endregion

            #region Create the recurring calendar item and extract the Id of an occurrence item
            CreateItemType createItemRequest = new CreateItemType();
            createItemRequest.Items = new NonEmptyArrayOfAllItemsType();
            createItemRequest.Items.Items = new ItemType[] { calendarItem };
            createItemRequest.MessageDispositionSpecified = true;
            createItemRequest.MessageDisposition = MessageDispositionType.SaveOnly;
            createItemRequest.SendMeetingInvitationsSpecified = true;
            createItemRequest.SendMeetingInvitations = CalendarItemCreateOrDeleteOperationType.SendToNone;
            CreateItemResponseType response = this.MTGSAdapter.CreateItem(createItemRequest);

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXWSMTGS_R12052");

            // Verify MS-OXWSMSG requirement: MS-OXWSMTGS_R12052
            Site.CaptureRequirementIfAreEqual<ResponseCodeType>(
                ResponseCodeType.ErrorCalendarInvalidDayForWeeklyRecurrence,
                response.ResponseMessages.Items[0].ResponseCode,
                12052,
                @"[In Appendix C: Product Behavior] Implementation does support the ErrorCalendarInvalidDayForWeeklyRecurrence to specify that invalid values of Day, WeekDay, and WeekendDay were used to specify the weekly recurrence. (Exchange 2016 and above follow this behavior.)");
            #endregion

            #region Clean up organizer's calendar folders.
            this.CleanupFoldersByRole(Role.Organizer, new List<DistinguishedFolderIdNameType>() { DistinguishedFolderIdNameType.calendar });
            #endregion
        }
        /// <summary>
        /// Verify Recurrence property of a recurring meeting
        /// </summary>
        /// <param name="recurrence">An instance of RecurrenceType</param>
        private void VerifyReccurrenceType(RecurrenceType recurrence)
        {
            this.VerifyRecurrencePatternType(recurrence.Item);

            // Add the debug information
            this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXWSMTGS_R391");

            // Verify MS-OXWSMTGS requirement: MS-OXWSMTGS_R391
            this.Site.CaptureRequirementIfIsNotNull(
                recurrence.Item1,
                391,
                @"[In t:RecurrenceType Complex Type] The RecurrenceRangeTypes group specifies the recurrence patterns with numbered recurrences, non-ending recurrence patterns, and recurrence patterns with a set start and end date, as specified in [MS-OXWSCDATA] section 2.2.7.2.");
        }
        /// <summary>
        /// Verify the RecurrenceType structure.
        /// </summary>
        /// <param name="recurrenceType">Specified the recurrence pattern and recurrence range for calendar items and meeting requests.</param>
        /// <param name="isSchemaValidated">The result of schema validation, true means valid.</param>
        private void VerifyRecurrenceType(RecurrenceType recurrenceType, bool isSchemaValidated)
        {
            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXWSMTGS_R389");

            // Verify MS-OXWSMTGS requirement: MS-OXWSMTGS_R389
            Site.CaptureRequirementIfIsTrue(
             isSchemaValidated,
             389,
             @"[In t:RecurrenceType Complex Type] [its schema is] <xs:complexType name=""RecurrenceType"">
                      <xs:sequence>
                        <xs:group
                          ref=""t:RecurrencePatternTypes""
                         />
                        <xs:group
                          ref=""t:RecurrenceRangeTypes""
                         />
                      </xs:sequence>
                    </xs:complexType>");

            if (recurrenceType.Item != null)
            {
                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXWSCDATA_R1343");

                // Verify MS-OXWSCDATA requirement: MS-OXWSCDATA_R1343
                this.Site.CaptureRequirementIfIsTrue(
                    isSchemaValidated,
                    "MS-OXWSCDATA",
                    1343,
                    @"[In t:RecurrencePatternTypes Group] The group [t:RecurrencePatternTypes] is define as follow:
    <xs:group name=""t:RecurrencePatternTypes"">
        <xs:sequence>
        <xs:choice>
            <xs:element name=""t:RelativeYearlyRecurrence""
            type=""t:RelativeYearlyRecurrencePatternType""
            />
            <xs:element name=""AbsoluteYearlyRecurrence""
            type=""t:AbsoluteYearlyRecurrencePatternType""
            />
            <xs:element name=""RelativeMonthlyRecurrence""
            type=""t:RelativeMonthlyRecurrencePatternType""
            />
            <xs:element name=""AbsoluteMonthlyRecurrence""
            type=""t:AbsoluteMonthlyRecurrencePatternType""
            />
            <xs:element name=""WeeklyRecurrence""
            type=""t:WeeklyRecurrencePatternType""
            />
            <xs:element name=""DailyRecurrence""
            type=""t:DailyRecurrencePatternType""
            />
        </xs:choice>
        </xs:sequence>
    </xs:group>");

                this.VerifyRecurrencePatternTypes(recurrenceType.Item, isSchemaValidated);
            }

            if (recurrenceType.Item1 != null)
            {
                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXWSCDATA_R1351");

                // Verify MS-OXWSCDATA requirement: MS-OXWSCDATA_R1351
                this.Site.CaptureRequirementIfIsTrue(
                    isSchemaValidated,
                    "MS-OXWSCDATA",
                    1351,
                    @"[In t:RecurrenceRangeTypes Group] The group [t:RecurrenceRangeTypes] is defined as follow:
    <xs:group name=""t:RecurrenceRangeTypes"">
      <xs:sequence>
        <xs:choice>
          <xs:element name=""NoEndRecurrence""
            type=""t:NoEndRecurrenceRangeType""
           />
          <xs:element name=""EndDateRecurrence""
            type=""t:EndDateRecurrenceRangeType""
           />
          <xs:element name=""NumberedRecurrence""
            type=""t:NumberedRecurrenceRangeType""
           />
        </xs:choice>
      </xs:sequence>
    </xs:group>");

                this.VerifyRecurrenceRangeTypes(recurrenceType.Item1, isSchemaValidated);
            }
        }