public void MSOXORULE_S01_TC11_AddExtendedRule_OP_OOF_REPLY() { this.CheckMAPIHTTPTransportSupported(); #region Prepare value for ruleProperties variable RuleProperties ruleProperties = AdapterHelper.GenerateRuleProperties(this.Site, Constants.RuleNameOOFReply); #endregion #region Create a reply template in the TestUser1's Inbox folder. ulong replyTemplateMessageId; uint replyTemplateMessageHandler; string replyTemplateSubject = Common.GenerateResourceName(this.Site, Constants.ReplyTemplateSubject); TaggedPropertyValue[] replyTemplateProperties = new TaggedPropertyValue[1]; replyTemplateProperties[0] = new TaggedPropertyValue(); PropertyTag replyTemplatePropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagBody, PropertyType = (ushort)PropertyType.PtypString }; replyTemplateProperties[0].PropertyTag = replyTemplatePropertyTag; replyTemplateProperties[0].Value = Encoding.Unicode.GetBytes(Constants.ReplyTemplateBody + "\0"); byte[] guidByte = this.OxoruleAdapter.CreateReplyTemplate(this.InboxFolderHandle, this.InboxFolderID, true, replyTemplateSubject, replyTemplateProperties, out replyTemplateMessageId, out replyTemplateMessageHandler); #endregion #region TestUser1 gets the reply template. #region Step1: TestUser1 gets a table of the messages. uint contentsTableHandleOfFAIMessage; RopGetContentsTableResponse ropGetContentsTableResponseOfFAIMessage = this.OxoruleAdapter.RopGetContentsTable(this.InboxFolderHandle, ContentTableFlag.Associated, out contentsTableHandleOfFAIMessage); Site.Assert.AreEqual<uint>(0, ropGetContentsTableResponseOfFAIMessage.ReturnValue, "Getting DAF contents table should succeed"); #endregion #region Step2: TestUser1 sets the interested columns of the message table. // Here are 2 interested columns listed as below. PropertyTag[] propertyTagOfFAIMessage = new PropertyTag[2]; PropertyTag pidTagMessageSubject = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagSubject, PropertyType = (ushort)PropertyType.PtypString }; propertyTagOfFAIMessage[0] = pidTagMessageSubject; PropertyTag pidTagReplyTemplateId = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagReplyTemplateId, PropertyType = (ushort)PropertyType.PtypBinary }; propertyTagOfFAIMessage[1] = pidTagReplyTemplateId; // Query rows which include the property values of the interested columns. RopQueryRowsResponse ropQueryRowsResponseOfFAIMessage = this.OxoruleAdapter.QueryPropertiesInTable(contentsTableHandleOfFAIMessage, propertyTagOfFAIMessage); Site.Assert.AreNotEqual<ushort>(0, ropQueryRowsResponseOfFAIMessage.RowCount, "There should be message generated in TestUser1's Inbox folder"); byte[] replyTemplateId = null; for (int i = 0; i < ropQueryRowsResponseOfFAIMessage.RowCount; i++) { string messageSubject = AdapterHelper.PropertyValueConvertToString(ropQueryRowsResponseOfFAIMessage.RowData.PropertyRows[i].PropertyValues[0].Value); if (messageSubject.Equals(replyTemplateSubject, StringComparison.CurrentCultureIgnoreCase)) { replyTemplateId = ropQueryRowsResponseOfFAIMessage.RowData.PropertyRows[i].PropertyValues[1].Value; } } byte[] pidTagReplyTemplateIdValue = new byte[replyTemplateId.Length - 2]; Array.Copy(replyTemplateId, 2, pidTagReplyTemplateIdValue, 0, replyTemplateId.Length - 2); #endregion #endregion #region TestUser1 gets the message entry ID and the Inbox folder's entry ID. byte[] messageEntryId = this.OxoruleAdapter.GetMessageEntryId(this.InboxFolderHandle, this.InboxFolderID, replyTemplateMessageHandler, replyTemplateMessageId); #endregion #region Prepare rules' data ReplyActionDataOfExtendedRule ruleActionData = new ReplyActionDataOfExtendedRule(); ruleActionData.MessageEIDSize = 0x46; ruleActionData.ReplyTemplateMessageEID = messageEntryId; ruleActionData.ReplyTemplateGUID = guidByte; #endregion #region TestUser1 creates an FAI message for the OP_OOF_REPLY extended rule. RopCreateMessageResponse ropCreateMessageResponse; uint extendedRuleMessageHandle1 = this.OxoruleAdapter.RopCreateMessage(this.InboxFolderHandle, this.InboxFolderID, Convert.ToByte(true), out ropCreateMessageResponse); Site.Assert.AreEqual<uint>(0, ropCreateMessageResponse.ReturnValue, "Creating the FAI message should succeed."); NamedPropertyInfo namedPropertyInfo1 = new NamedPropertyInfo { NoOfNamedProps = 0 }; TaggedPropertyValue[] extendedRuleProperties1 = AdapterHelper.GenerateExtendedRuleTestData(ruleProperties.Name, 0, (uint)RuleState.ST_ENABLED, Constants.PidTagRuleProvider, ActionType.OP_OOF_REPLY, ruleActionData, ruleProperties.ConditionSubjectName, namedPropertyInfo1); // Set properties for extended rule FAI message. RopSetPropertiesResponse ropSetPropertiesResponse = this.OxoruleAdapter.RopSetProperties(extendedRuleMessageHandle1, extendedRuleProperties1); Site.Assert.AreEqual<uint>(0, ropSetPropertiesResponse.ReturnValue, "Setting property for Extended rule FAI message should succeed."); // Save changes of message. RopSaveChangesMessageResponse ropSaveChangesMessagResponse = this.OxoruleAdapter.RopSaveChangesMessage(extendedRuleMessageHandle1); Site.Assert.AreEqual(0, (int)ropSaveChangesMessagResponse.ReturnValue, "Saving Extend rule message should succeed."); #endregion #region TestUser1 gets the OP_OOF_REPLY extended rule. #region Step1: TestUser1 gets a table of all messages which are placed in the Inbox folder. ropGetContentsTableResponseOfFAIMessage = this.OxoruleAdapter.RopGetContentsTable(this.InboxFolderHandle, ContentTableFlag.Associated, out contentsTableHandleOfFAIMessage); Site.Assert.AreEqual<uint>(0, ropGetContentsTableResponseOfFAIMessage.ReturnValue, "Getting DAF contents table should succeed"); #endregion #region Step2: TestUser1 sets the interested columns of the message table in the Inbox folder. // Here are 6 interested columns listed as below. propertyTagOfFAIMessage = new PropertyTag[6]; PropertyTag pidTagRuleMessageNameTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagRuleMessageName, PropertyType = (ushort)PropertyType.PtypString }; propertyTagOfFAIMessage[0] = pidTagRuleMessageNameTag; PropertyTag pidTagMessageClassTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagMessageClass, PropertyType = (ushort)PropertyType.PtypString }; propertyTagOfFAIMessage[1] = pidTagMessageClassTag; PropertyTag pidTagRuleMessageStatePropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagRuleMessageState, PropertyType = (ushort)PropertyType.PtypInteger32 }; propertyTagOfFAIMessage[2] = pidTagRuleMessageStatePropertyTag; PropertyTag pidTagRuleMessageProviderPropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagRuleMessageProvider, PropertyType = (ushort)PropertyType.PtypString }; propertyTagOfFAIMessage[3] = pidTagRuleMessageProviderPropertyTag; PropertyTag pidTagExtendedRuleMessageActionsPropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagExtendedRuleMessageActions, PropertyType = (ushort)PropertyType.PtypBinary }; propertyTagOfFAIMessage[4] = pidTagExtendedRuleMessageActionsPropertyTag; PropertyTag pidTagExtendedRuleMessageConditionPropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagExtendedRuleMessageCondition, PropertyType = (ushort)PropertyType.PtypBinary }; propertyTagOfFAIMessage[5] = pidTagExtendedRuleMessageConditionPropertyTag; // Query rows which include the property values of the interested columns. ropQueryRowsResponseOfFAIMessage = this.OxoruleAdapter.QueryPropertiesInTable(contentsTableHandleOfFAIMessage, propertyTagOfFAIMessage); Site.Assert.AreEqual<uint>(0, ropQueryRowsResponseOfFAIMessage.ReturnValue, "Querying Rows Response of FAI Message should succeed, the actual returned value is {0}", ropQueryRowsResponseOfFAIMessage.ReturnValue); ExtendedRuleActions extendedRuleAction = new ExtendedRuleActions(); ReplyActionDataOfExtendedRule replyActionData = new ReplyActionDataOfExtendedRule(); for (int i = 0; i < ropQueryRowsResponseOfFAIMessage.RowCount; i++) { // Since the PidTagMessageClass property of Extended rule MUST have a value of "IPM.ExtendedRule.Message", use PidTagMessageClass property to get the extended rule data. System.Text.UnicodeEncoding converter = new UnicodeEncoding(); string messageClass = converter.GetString(ropQueryRowsResponseOfFAIMessage.RowData.PropertyRows.ToArray()[i].PropertyValues[1].Value); if (messageClass == "IPM.ExtendedRule.Message" + "\0") { byte[] extendedRuleMessageActionBinary = ropQueryRowsResponseOfFAIMessage.RowData.PropertyRows[i].PropertyValues[4].Value; byte[] extendedRuleMessageActionBuffer = new byte[extendedRuleMessageActionBinary.Length - 2]; // Remove the two length bytes to get the extended rule action data. Array.Copy(extendedRuleMessageActionBinary, 2, extendedRuleMessageActionBuffer, 0, extendedRuleMessageActionBinary.Length - 2); extendedRuleAction.Deserialize(extendedRuleMessageActionBuffer); replyActionData.Deserialize(extendedRuleAction.RuleActionBuffer.Actions[0].ActionDataValue.Serialize()); break; } } #endregion #region Capture Code // Add the debug information. Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXORULE_R998: the Message EntryID is {0}, and the ReplyTemplateMessageEID in the action data is {1}", messageEntryId, replyActionData.ReplyTemplateMessageEID); bool isVerifiedR998 = Common.CompareByteArray(ruleActionData.ReplyTemplateMessageEID, replyActionData.ReplyTemplateMessageEID); // Verify MS-OXORULE requirement: MS-OXORULE_R998. Site.CaptureRequirementIfIsTrue( isVerifiedR998, 998, @"[OP_REPLY and OP_OOF_REPLY ActionData Structure] [Buffer Format for Extended Rules] ReplyTemplateMessageEID (70 bytes): A Message EntryID structure, as specified in [MS-OXCDATA] section 2.2.4.2, that contains the entry ID of the reply template."); // Add the debug information. Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXORULE_R1000"); bool isVerifiedR1000 = Common.CompareByteArray(ruleActionData.ReplyTemplateGUID, replyActionData.ReplyTemplateGUID); // Verify MS-OXORULE requirement: MS-OXORULE_R1000. // IF the value of the ReplyTemplateGUID field in OP_OOF_REPLY action data is equal to the value of the PidTagReplyTemplateId property that is set on the reply template, R1000 can be verified. Site.CaptureRequirementIfIsTrue( isVerifiedR1000, 1000, @"[OP_REPLY and OP_OOF_REPLY ActionData Structure] [Buffer Format for Extended Rules] ReplyTemplateGUID (16 bytes): A GUID that is generated by the client in the process of creating a reply template."); // Add the debug information. Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXORULE_R1002: the value of PidTagReplyTemplateId property is {0}, and the ReplyTemplateGUID in the action data is {1}", pidTagReplyTemplateIdValue, replyActionData.ReplyTemplateGUID); bool isVerifiedR1002 = isVerifiedR998 && isVerifiedR1000 && replyActionData.MessageEIDSize == ruleActionData.MessageEIDSize; // Verify MS-OXORULE requirement: MS-OXORULE_R1002. Site.CaptureRequirementIfIsTrue( isVerifiedR1002, 1002, @"[OP_REPLY and OP_OOF_REPLY ActionData Structure] [Buffer Format for Extended Rules] The value of the ReplyTemplateGUID field in OP_OOF_REPLY action data is equal to the value of the PidTagReplyTemplateId property that is set on the reply template."); #endregion #endregion }
/// <summary> /// This method help to convert the property value, which is of variable bytes, to ExtendedRuleActions structure. /// </summary> /// <param name="byteArray">The byte array to be converted.</param> /// <returns>Return the ExtendedRuleActions structure.</returns> public static ExtendedRuleActions PropertyValueConvertToExtendedRuleActions(byte[] byteArray) { // The first 2 bytes of byteArray only indicates the total number of subsequent bytes, // byteArrayTobeConvert is the actual bytes used to convert to the ExtendedRuleActions structure, // which should not include the first 2 bytes of byteArray. byte[] byteArrayTobeConvert = new byte[byteArray.Length - 2]; Array.Copy(byteArray, 2, byteArrayTobeConvert, 0, byteArray.Length - 2); // De-serialize the byte array into the ExtendedRuleActions structure. ExtendedRuleActions extendedRuleActions = new ExtendedRuleActions(); extendedRuleActions.Deserialize(byteArrayTobeConvert); return extendedRuleActions; }
public void MSOXORULE_S02_TC16_ServerExecuteExtendedRule_Action_OP_COPY() { this.CheckMAPIHTTPTransportSupported(); #region Prepare value for ruleProperties variable. RuleProperties ruleProperties = AdapterHelper.GenerateRuleProperties(this.Site, Constants.RuleNameMoveOne); #endregion #region TestUser1 creates folder1 in server store. RopCreateFolderResponse createFolderResponse; uint newFolderHandle = this.OxoruleAdapter.RopCreateFolder(this.InboxFolderHandle, Common.GenerateResourceName(this.Site, "User1Folder01"), "TestForOP_COPY", out createFolderResponse); ulong newFolderId = createFolderResponse.FolderId; Site.Assert.AreEqual<uint>(0, createFolderResponse.ReturnValue, "Creating folder operation should succeed."); #endregion #region Prepare rules' data MoveCopyActionDataOfExtendedRule copyActionData = new MoveCopyActionDataOfExtendedRule(); // Get the created folder1 entry id. byte[] folder1EId = this.OxoruleAdapter.GetFolderEntryId(StoreObjectType.Mailbox, newFolderHandle, newFolderId); // Get the store object's entry id byte[] storeEId = this.GetStoreObjectEntryID(StoreObjectType.Mailbox, this.Server, this.User1ESSDN); copyActionData.FolderEID = folder1EId; copyActionData.StoreEID = storeEId; copyActionData.FolderEIDSize = (uint)folder1EId.Length; copyActionData.StoreEIDSize = (uint)storeEId.Length; #endregion #region TestUser1 creates an FAI message for the extended rule. RopCreateMessageResponse ropCreateMessageResponse; uint extendedRuleMessageHandle1 = this.OxoruleAdapter.RopCreateMessage(this.InboxFolderHandle, this.InboxFolderID, Convert.ToByte(true), out ropCreateMessageResponse); Site.Assert.AreEqual<uint>(0, ropCreateMessageResponse.ReturnValue, "Creating the FAI message should succeed."); NamedPropertyInfo namedPropertyInfo1 = new NamedPropertyInfo { NoOfNamedProps = 0 }; TaggedPropertyValue[] extendedRuleProperties1 = AdapterHelper.GenerateExtendedRuleTestData(ruleProperties.Name, 0, (uint)RuleState.ST_ENABLED, Constants.PidTagRuleProvider, ActionType.OP_COPY, copyActionData, ruleProperties.ConditionSubjectName, namedPropertyInfo1); // Set properties for extended rule FAI message. RopSetPropertiesResponse ropSetPropertiesResponse = this.OxoruleAdapter.RopSetProperties(extendedRuleMessageHandle1, extendedRuleProperties1); Site.Assert.AreEqual<uint>(0, ropSetPropertiesResponse.ReturnValue, "Setting property for Extended rule FAI message should succeed."); // Save changes of message. RopSaveChangesMessageResponse ropSaveChangesMessagResponse = this.OxoruleAdapter.RopSaveChangesMessage(extendedRuleMessageHandle1); Site.Assert.AreEqual(0, (int)ropSaveChangesMessagResponse.ReturnValue, "Saving Extend rule message should succeed."); #endregion #region TestUser1 gets the extended rule. #region Step1: TestUser1 gets a table of all messages which are placed in the Inbox folder. uint contentsTableHandleOfFAIMessage; RopGetContentsTableResponse ropGetContentsTableResponseOfFAIMessage = this.OxoruleAdapter.RopGetContentsTable(this.InboxFolderHandle, ContentTableFlag.Associated, out contentsTableHandleOfFAIMessage); Site.Assert.AreEqual<uint>(0, ropGetContentsTableResponseOfFAIMessage.ReturnValue, "Getting contents table should succeed, the actual returned value is {0}", ropGetContentsTableResponseOfFAIMessage.ReturnValue); #endregion #region Step2: TestUser1 sets the interested columns of the message table in the Inbox folder. // Here are 6 interested columns listed as below. PropertyTag[] propertyTagOfFAIMessage = new PropertyTag[6]; PropertyTag pidTagRuleMessageNameTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagRuleMessageName, PropertyType = (ushort)PropertyType.PtypString }; propertyTagOfFAIMessage[0] = pidTagRuleMessageNameTag; PropertyTag pidTagMessageClassTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagMessageClass, PropertyType = (ushort)PropertyType.PtypString }; propertyTagOfFAIMessage[1] = pidTagMessageClassTag; PropertyTag pidTagRuleMessageStatePropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagRuleMessageState, PropertyType = (ushort)PropertyType.PtypInteger32 }; propertyTagOfFAIMessage[2] = pidTagRuleMessageStatePropertyTag; PropertyTag pidTagRuleMessageProviderPropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagRuleMessageProvider, PropertyType = (ushort)PropertyType.PtypString }; propertyTagOfFAIMessage[3] = pidTagRuleMessageProviderPropertyTag; PropertyTag pidTagExtendedRuleMessageActionsPropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagExtendedRuleMessageActions, PropertyType = (ushort)PropertyType.PtypBinary }; propertyTagOfFAIMessage[4] = pidTagExtendedRuleMessageActionsPropertyTag; PropertyTag pidTagExtendedRuleMessageConditionPropertyTag = new PropertyTag { PropertyId = (ushort)PropertyId.PidTagExtendedRuleMessageCondition, PropertyType = (ushort)PropertyType.PtypBinary }; propertyTagOfFAIMessage[5] = pidTagExtendedRuleMessageConditionPropertyTag; // Query rows which include the property values of the interested columns. RopQueryRowsResponse ropQueryRowsResponseOfFAIMessage = this.OxoruleAdapter.QueryPropertiesInTable(contentsTableHandleOfFAIMessage, propertyTagOfFAIMessage); Site.Assert.AreEqual<uint>(0, ropQueryRowsResponseOfFAIMessage.ReturnValue, "Querying Rows Response of FAI Message should succeed, the actual returned value is {0}", ropQueryRowsResponseOfFAIMessage.ReturnValue); MoveCopyActionDataOfExtendedRule copyActionDataOfQueryRowsResponse = new MoveCopyActionDataOfExtendedRule(); for (int i = 0; i < ropQueryRowsResponseOfFAIMessage.RowCount; i++) { System.Text.UnicodeEncoding converter = new UnicodeEncoding(); string messageName = converter.GetString(ropQueryRowsResponseOfFAIMessage.RowData.PropertyRows.ToArray()[i].PropertyValues[0].Value); if (messageName == ruleProperties.Name + "\0") { byte[] extendedRuleMessageActionBinary = ropQueryRowsResponseOfFAIMessage.RowData.PropertyRows.ToArray()[i].PropertyValues[4].Value; byte[] extendedRuleMessageActionBuffer = new byte[extendedRuleMessageActionBinary.Length - 2]; Array.Copy(extendedRuleMessageActionBinary, 2, extendedRuleMessageActionBuffer, 0, extendedRuleMessageActionBinary.Length - 2); ExtendedRuleActions extendedRuleActions = new ExtendedRuleActions(); extendedRuleActions.Deserialize(extendedRuleMessageActionBuffer); copyActionDataOfQueryRowsResponse.Deserialize(extendedRuleActions.RuleActionBuffer.Actions[0].ActionDataValue.Serialize()); } } // Add the debug information this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXORULE_R977"); bool isVerifiedR977 = Common.CompareByteArray(folder1EId, copyActionDataOfQueryRowsResponse.FolderEID); // Verify MS-OXORULE requirement: MS-OXORULE_R977 this.Site.CaptureRequirementIfIsTrue( isVerifiedR977, 977, @"[In OP_MOVE and OP_COPY ActionData Structure] [Buffer Format for Extended Rules] FolderEID (variable): A Folder EntryID structure, as specified in [MS-OXCDATA] section 2.2.4.1, [In OP_COPY action data] identifies the destination folder."); #endregion #endregion #region TestUser2 delivers a message to TestUser1 to trigger the rule. // TestUser2 deliver a message to trigger these rules. string mailSubject = Common.GenerateResourceName(this.Site, ruleProperties.ConditionSubjectName + "Title"); this.SUTAdapter.SendMailToRecipient(this.User2Name, this.User2Password, this.User1Name, mailSubject); // Wait for the mail to be received and the rule to take effect. Thread.Sleep(this.WaitForTheRuleToTakeEffect); #endregion #region TestUser1 gets the message content to verify the rule evaluation. uint inboxFolderContentsTableHandle = 0; PropertyTag[] propertyTagList = new PropertyTag[1]; propertyTagList[0].PropertyId = (ushort)PropertyId.PidTagSubject; propertyTagList[0].PropertyType = (ushort)PropertyType.PtypString; uint rowCount = 0; RopQueryRowsResponse getInboxMailMessageContent = this.GetExpectedMessage(this.InboxFolderHandle, ref inboxFolderContentsTableHandle, propertyTagList, ref rowCount, 1, mailSubject); uint newFolder1ContentsTableHandle = 0; rowCount = 0; RopQueryRowsResponse getNewFolder1MailMessageContent = this.GetExpectedMessage(newFolderHandle, ref newFolder1ContentsTableHandle, propertyTagList, ref rowCount, 1, mailSubject); Site.Assert.AreEqual<uint>(0, getNewFolder1MailMessageContent.ReturnValue, "getNewFolder1MailMessageContent should succeed."); #region Capture code this.VerifyActionTypeOP_COPY(mailSubject, getNewFolder1MailMessageContent, getInboxMailMessageContent, ruleProperties); // Add the debug information this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXORULE_R969, since the destination folder is created in the user's mailbox, try to verify the message was copy to the folder"); // Verify MS-OXORULE requirement: MS-OXORULE_R969 bool isVerifiedR969 = getInboxMailMessageContent.RowCount != 0 && getNewFolder1MailMessageContent.RowCount != 0; this.Site.CaptureRequirementIfIsTrue( isVerifiedR969, 969, @"[In OP_MOVE and OP_COPY ActionData Structure] [Buffer Format for Extended Rules] The destination folder for a Copy action in an extended rule MUST be in the user's mailbox."); #endregion #endregion #region Delete the newly created folder. RopDeleteFolderResponse deleteFolder = this.OxoruleAdapter.RopDeleteFolder(this.InboxFolderHandle, newFolderId); Site.Assert.AreEqual<uint>(0, deleteFolder.ReturnValue, "Deleting folder should succeed."); #endregion }
/// <summary> /// Query properties in contents table. /// </summary> /// <param name="tableHandle">Handle of a specific contents table.</param> /// <param name="propertyTags">Array of PropertyTag structures. This field specifies the property values that are visible in table rows.</param> /// <returns>Response of this query rows.</returns> public RopQueryRowsResponse QueryPropertiesInTable(uint tableHandle, PropertyTag[] propertyTags) { // Set the properties in propertyTags to be visible. RopSetColumnsResponse setColumnsResponse = this.RopSetColumns(tableHandle, 0x00, propertyTags); // Query properties values specified in propertyTags. RopQueryRowsResponse queryRowsResponse = this.RopQueryRows(tableHandle, 0x00, 0x01, 1000); // That the two Rops are successful means that the propertyTags in request is correct if (setColumnsResponse.ReturnValue == 0 && queryRowsResponse.ReturnValue == 0 && queryRowsResponse.RowData.PropertyRows != null) { // Verify PropertyTags this.VerifyPropertiesInTable(propertyTags, queryRowsResponse); for (int i = 0; i < propertyTags.Length; i++) { // If the property queried is PidTagRuleActions if (propertyTags[i].PropertyId == (ushort)PropertyId.PidTagRuleActions) { for (int j = 0; j < queryRowsResponse.RowData.PropertyRows.Count; j++) { // Verify structure RuleAction RuleAction ruleAction = new RuleAction(); ruleAction.Deserialize(queryRowsResponse.RowData.PropertyRows[j].PropertyValues[i].Value); this.VerifyRuleAction(ruleAction); } } // If the property queried is PidTagExtendedRuleMessageActions if (propertyTags[i].PropertyId == (ushort)PropertyId.PidTagExtendedRuleMessageActions) { for (int j = 0; j < queryRowsResponse.RowData.PropertyRows.Count; j++) { if (BitConverter.ToUInt32(queryRowsResponse.RowData.PropertyRows[j].PropertyValues[i].Value, 0) != (uint)ErrorCodeValue.NotFound) { // Verify structure RuleAction ExtendedRuleActions ruleAction = new ExtendedRuleActions(); byte[] extendedRuleMessageActionBuffer = new byte[queryRowsResponse.RowData.PropertyRows[j].PropertyValues[i].Value.Length - 2]; Array.Copy(queryRowsResponse.RowData.PropertyRows[j].PropertyValues[i].Value, 2, extendedRuleMessageActionBuffer, 0, queryRowsResponse.RowData.PropertyRows[j].PropertyValues[i].Value.Length - 2); ruleAction.Deserialize(extendedRuleMessageActionBuffer); this.VerifyExtendRuleAction(ruleAction.RuleActionBuffer); } } } } } return queryRowsResponse; }