예제 #1
0
        public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(session, "session");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            Util.ThrowOnNullArgument(callbackContext, "callbackContext");
            if (!WorkingSetPublisher.IsGroupWSPublishingEnabled())
            {
                COWGroupMessageWSPublishing.Tracer.Information((long)this.GetHashCode(), "COWGroupMessageWSPublishing.SkipItemOperation: skipping group message working set publishing as the feature is disabled.");
                return(true);
            }
            switch (callbackContext.COWGroupMessageWSPublishingState)
            {
            case COWProcessorState.Unknown:
                callbackContext.COWGroupMessageWSPublishingState = this.InspectNotification(operation, session, item, onBeforeNotification, onDumpster);
                COWGroupMessageWSPublishing.Tracer.TraceDebug <StoreObjectId, COWProcessorState>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.SkipItemOperation: inspected item {0} and result is {1}.", itemId, callbackContext.COWGroupMessageWSPublishingState);
                return(true);

            case COWProcessorState.DoNotProcess:
                COWGroupMessageWSPublishing.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.SkipItemOperation: skipping notification for item {0} because it should not be processed.", itemId);
                return(true);

            case COWProcessorState.ProcessAfterSave:
                return(onBeforeNotification);

            case COWProcessorState.Processed:
                COWGroupMessageWSPublishing.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.SkipItemOperation: skipping notification for item {0} because it has already been processed.", itemId);
                return(true);

            default:
                return(true);
            }
        }
예제 #2
0
        public void ItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, CoreFolder folder, bool onBeforeNotification, OperationResult result, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(session, "session");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            EnumValidator.ThrowIfInvalid <OperationResult>(result, "result");
            Util.ThrowOnNullArgument(item, "item");
            Util.ThrowOnNullArgument(callbackContext, "callbackContext");
            if (callbackContext.COWGroupMessageWSPublishingState != COWProcessorState.ProcessAfterSave)
            {
                COWGroupMessageWSPublishing.Tracer.TraceError <COWProcessorState>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.ItemOperation: Skipping working set publishing because the state doesn't indicate processing is needed: {0}", callbackContext.COWGroupMessageWSPublishingState);
                return;
            }
            if (onBeforeNotification)
            {
                COWGroupMessageWSPublishing.Tracer.TraceError((long)this.GetHashCode(), "COWGroupMessageWSPublishing.ItemOperation: Skipping working set publishing because we should only publish after saving");
                return;
            }
            if (result != OperationResult.Succeeded)
            {
                COWGroupMessageWSPublishing.Tracer.TraceDebug <OperationResult>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.ItemOperation: Skipping working set publishing of message because the operation wasn't successful: {0}", result);
                return;
            }
            MailboxSession mailboxSession = session as MailboxSession;

            if (mailboxSession == null)
            {
                COWGroupMessageWSPublishing.Tracer.TraceError <OperationResult>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.ItemOperation: Skipping working set publishing the session is not a mailbox session", result);
                return;
            }
            if (mailboxSession.MailboxOwner == null || mailboxSession.MailboxOwner.MailboxInfo == null)
            {
                COWGroupMessageWSPublishing.Tracer.TraceError <OperationResult>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.ItemOperation: Skipping working set publishing, the session does not contain the mailbox info", result);
                return;
            }
            string    displayName = mailboxSession.DisplayName;
            string    groupId     = mailboxSession.MailboxOwner.MailboxInfo.PrimarySmtpAddress.ToString();
            Exception ex          = this.groupWSPublisher.PublishGroupPost(item, displayName, groupId);

            if (ex == null)
            {
                COWGroupMessageWSPublishing.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.ItemOperation: working set publishing of message {0} from group mailbox successful", itemId);
            }
            else
            {
                COWGroupMessageWSPublishing.Tracer.TraceDebug <StoreObjectId, string>((long)this.GetHashCode(), "COWGroupMessageWSPublishing.ItemOperation: working set publishing of message {0} from group mailbox failed. Error: {1}", itemId, ex.ToString());
            }
            callbackContext.COWGroupMessageWSPublishingState = COWProcessorState.Processed;
        }
예제 #3
0
 public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
 {
     EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
     EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
     if (onBeforeNotification && COWTriggerAction.Update == operation)
     {
         if (settings.CurrentFolderId != null)
         {
             if (settings.CurrentFolderId.Equals(dumpster.AuditsFolderId))
             {
                 throw new AccessDeniedException(ServerStrings.ExAuditsUpdateDenied);
             }
             if (settings.CurrentFolderId.Equals(dumpster.AdminAuditLogsFolderId))
             {
                 throw new AccessDeniedException(ServerStrings.ExAdminAuditLogsUpdateDenied);
             }
             if (dumpster.IsAuditFolder(settings.CurrentFolderId))
             {
                 throw new AccessDeniedException((dumpster.AuditsFolderId != null) ? ServerStrings.ExAuditsUpdateDenied : ServerStrings.ExAdminAuditLogsUpdateDenied);
             }
         }
         else if (itemId != null)
         {
             StoreObjectId parentIdFromMessageId = IdConverter.GetParentIdFromMessageId(itemId);
             if (parentIdFromMessageId.Equals(dumpster.AuditsFolderId))
             {
                 throw new AccessDeniedException(ServerStrings.ExAuditsUpdateDenied);
             }
             if (parentIdFromMessageId.Equals(dumpster.AdminAuditLogsFolderId))
             {
                 throw new AccessDeniedException(ServerStrings.ExAdminAuditLogsUpdateDenied);
             }
             if (dumpster.IsAuditFolder(settings.CurrentFolderId))
             {
                 throw new AccessDeniedException((dumpster.AuditsFolderId != null) ? ServerStrings.ExAuditsUpdateDenied : ServerStrings.ExAdminAuditLogsUpdateDenied);
             }
         }
     }
     return(true);
 }
예제 #4
0
 public void ItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, CoreFolder folder, bool onBeforeNotification, OperationResult result, CallbackContext callbackContext)
 {
     EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
     EnumValidator.ThrowIfInvalid <OperationResult>(result, "result");
     EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
 }
예제 #5
0
        public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(session, "session");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            MailboxSession mailboxSession = session as MailboxSession;

            if (mailboxSession == null || !Utils.IsTeamMailbox(session) || !ClientInfo.MOMT.IsMatch(session.ClientInfoString))
            {
                return(true);
            }
            if (callbackContext.SiteMailboxMessageDedupState == COWProcessorState.DoNotProcess)
            {
                COWSiteMailboxMessageDedup.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.SkipItemOperation: skipping notification for item {0} because it should not be processed.", itemId);
                return(true);
            }
            if (callbackContext.SiteMailboxMessageDedupState == COWProcessorState.Processed)
            {
                COWSiteMailboxMessageDedup.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.SkipItemOperation: skipping notification for item {0} because it was already processed.", itemId);
                return(true);
            }
            if (callbackContext.SiteMailboxMessageDedupState == COWProcessorState.ProcessAfterSave)
            {
                return(onBeforeNotification);
            }
            if (onDumpster || item == null || operation != COWTriggerAction.Create)
            {
                callbackContext.SiteMailboxMessageDedupState = COWProcessorState.DoNotProcess;
                return(true);
            }
            if (!settings.IsSiteMailboxMessageDedupEnabled())
            {
                callbackContext.SiteMailboxMessageDedupState = COWProcessorState.DoNotProcess;
                COWSiteMailboxMessageDedup.Tracer.Information <string>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.SkipItemOperation: skipping message dedup for site mailbox {0} because the feature is disabled for the mailbox.", mailboxSession.DisplayName);
                return(true);
            }
            ExDateTime now  = ExDateTime.Now;
            bool       flag = false;

            try
            {
                flag = this.IsDuplicateMessageBySiteMailboxDrop(mailboxSession, item);
            }
            catch (StoragePermanentException arg)
            {
                COWSiteMailboxMessageDedup.Tracer.TraceError <StoragePermanentException>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.SkipItemOperation: got store permanent exception: {0}", arg);
            }
            catch (StorageTransientException arg2)
            {
                COWSiteMailboxMessageDedup.Tracer.TraceError <StorageTransientException>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.SkipItemOperation: got store transient exception: {0}", arg2);
            }
            if (flag)
            {
                callbackContext.SiteMailboxMessageDedupState = COWProcessorState.ProcessAfterSave;
            }
            else
            {
                callbackContext.SiteMailboxMessageDedupState = COWProcessorState.DoNotProcess;
            }
            COWSiteMailboxMessageDedup.Tracer.TraceDebug((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.SkipItemOperation: inspecting message {0} dragged & dropped to site mailbox {1} costed {2} milliseconds, and the result is {3}.", new object[]
            {
                itemId,
                mailboxSession.DisplayName,
                (ExDateTime.Now - now).TotalMilliseconds,
                callbackContext.SiteMailboxMessageDedupState
            });
            return(true);
        }
예제 #6
0
        public void ItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, CoreFolder folder, bool onBeforeNotification, OperationResult result, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(session, "session");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            EnumValidator.ThrowIfInvalid <OperationResult>(result, "result");
            Util.ThrowOnNullArgument(item, "item");
            MailboxSession mailboxSession = session as MailboxSession;
            ExDateTime     now            = ExDateTime.Now;

            try
            {
                item.PropertyBag.Load(COWSiteMailboxMessageDedup.PropsForMessageRemoval);
                if (item.Id != null && item.Id.ObjectId != null)
                {
                    StoreObjectId storeObjectId = item.PropertyBag.TryGetProperty(StoreObjectSchema.ParentItemId) as StoreObjectId;
                    if (storeObjectId != null)
                    {
                        using (CoreFolder coreFolder = CoreFolder.Bind(session, storeObjectId))
                        {
                            DeleteItemFlags deleteItemFlags = DeleteItemFlags.HardDelete | DeleteItemFlags.SuppressReadReceipt;
                            coreFolder.DeleteItems(deleteItemFlags, new StoreObjectId[]
                            {
                                item.Id.ObjectId
                            });
                        }
                        COWSiteMailboxMessageDedup.Tracer.TraceDebug <StoreObjectId, string, double>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.ItemOperation: deleting message {0} from site mailbox {1} used {2} milliseconds", itemId, mailboxSession.DisplayName, (ExDateTime.Now - now).TotalMilliseconds);
                    }
                }
            }
            catch (StoragePermanentException arg)
            {
                COWSiteMailboxMessageDedup.Tracer.TraceError <StoragePermanentException>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.ItemOperation: got store permanent exception: {0}", arg);
            }
            catch (StorageTransientException arg2)
            {
                COWSiteMailboxMessageDedup.Tracer.TraceError <StorageTransientException>((long)this.GetHashCode(), "COWSiteMailboxMessageDedup.ItemOperation: got store transient exception: {0}", arg2);
            }
            callbackContext.SiteMailboxMessageDedupState = COWProcessorState.Processed;
        }
예제 #7
0
        public void ItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, CoreFolder folder, bool onBeforeNotification, OperationResult result, CallbackContext callbackContext)
        {
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <OperationResult>(result, "result");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            StoreObjectId storeObjectId = ((ICoreObject)item).StoreObjectId;

            if (storeObjectId is OccurrenceStoreObjectId)
            {
                return;
            }
            if (onBeforeNotification)
            {
                List <string> legallyDirtyProperties = item.GetLegallyDirtyProperties();
                if (legallyDirtyProperties != null && legallyDirtyProperties.Count > 0)
                {
                    COWSettings.AddMetadata(settings, item, operation);
                    if (state == COWTriggerActionState.Save)
                    {
                        StoreObjectId destinationFolderId;
                        if (settings.IsOnlyInPlaceHoldEnabled())
                        {
                            settings.Session.CowSession.CheckAndCreateDiscoveryHoldsFolder(callbackContext.SessionWithBestAccess);
                            destinationFolderId = dumpster.RecoverableItemsDiscoveryHoldsFolderId;
                        }
                        else
                        {
                            destinationFolderId = dumpster.RecoverableItemsVersionsFolderId;
                        }
                        StoreObjectId copyOnWriteGeneratedId = dumpster.CopyItemToDumpster(callbackContext.SessionWithBestAccess, destinationFolderId, item);
                        dumpster.Results.CopyOnWriteGeneratedId = copyOnWriteGeneratedId;
                        return;
                    }
                }
            }
            else if (operation == COWTriggerAction.Update && state == COWTriggerActionState.Save && result == OperationResult.Failed)
            {
                dumpster.RollbackItemVersion(callbackContext.SessionWithBestAccess, item, dumpster.Results.CopyOnWriteGeneratedId);
                dumpster.Results.CopyOnWriteGeneratedId = null;
            }
        }
예제 #8
0
 public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
 {
     EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
     EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
     return(true);
 }
예제 #9
0
        public void ItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, CoreFolder folder, bool onBeforeNotification, OperationResult result, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(session, "session");
            Util.ThrowOnNullArgument(item, "item");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            EnumValidator.ThrowIfInvalid <OperationResult>(result, "result");
            COWContactLogging.Tracer.TraceDebug((long)this.GetHashCode(), "COWContactLogging.ItemOperation: Start.");
            string valueOrDefault = item.PropertyBag.GetValueOrDefault <string>(StoreObjectSchema.ItemClass, string.Empty);

            COWContactLogging.Tracer.TraceDebug <string>((long)this.GetHashCode(), "COWContactLogging.ItemOperation: ItemClass: {0}", valueOrDefault);
            HashSet <StorePropertyDefinition> hashSet = new HashSet <StorePropertyDefinition>();
            List <IContactChangeTracker>      list    = new List <IContactChangeTracker>(COWContactLogging.ChangeTrackers.Length);

            foreach (IContactChangeTracker contactChangeTracker in COWContactLogging.ChangeTrackers)
            {
                if (contactChangeTracker.ShouldLoadPropertiesForFurtherCheck(operation, valueOrDefault, itemId, item))
                {
                    COWContactLogging.Tracer.TraceDebug <string>((long)this.GetHashCode(), "COWContactLogging.ItemOperation: Tracker {0} interested.", contactChangeTracker.Name);
                    list.Add(contactChangeTracker);
                    StorePropertyDefinition[] properties = contactChangeTracker.GetProperties(itemId, item);
                    if (properties != null && properties.Length > 0)
                    {
                        COWContactLogging.Tracer.TraceDebug <string, int>((long)this.GetHashCode(), "COWContactLogging.ItemOperation: Tracker {0} returned {1} properties for tracking", contactChangeTracker.Name, properties.Length);
                        hashSet.UnionWith(properties);
                    }
                }
            }
            if (hashSet.Count == 0)
            {
                COWContactLogging.Tracer.TraceDebug((long)this.GetHashCode(), "COWContactLogging.ItemOperation: No properties marked as interesting by any tracker.");
                return;
            }
            hashSet.Add(ItemSchema.Id);
            hashSet.Add(StoreObjectSchema.ItemClass);
            StorePropertyDefinition[] array = new StorePropertyDefinition[hashSet.Count];
            hashSet.CopyTo(array, 0, hashSet.Count);
            item.PropertyBag.Load(array);
            bool flag = false;

            foreach (IContactChangeTracker contactChangeTracker2 in list)
            {
                if (contactChangeTracker2.ShouldLogContact(itemId, item))
                {
                    flag = true;
                    break;
                }
            }
            if (!flag)
            {
                COWContactLogging.Tracer.TraceDebug((long)this.GetHashCode(), "COWContactLogging.ItemOperation: No trackers are interested after doing further checks.");
                return;
            }
            COWContactLogging.ContactChangeLogEvent contactChangeLogEvent = new COWContactLogging.ContactChangeLogEvent();
            contactChangeLogEvent.Add("ClientInfo", session.ClientInfoString);
            contactChangeLogEvent.Add("Action", operation.ToString());
            COWContactLogging.Tracer.TraceDebug <COWTriggerAction, string, int>((long)this.GetHashCode(), "COWContactLogging.ItemOperation: Tracking change {0} made by client {1} across a total of {2} properties", operation, session.ClientInfoString, hashSet.Count);
            this.LogInterestingPropertyValues(contactChangeLogEvent, operation, item, hashSet);
            ContactChangeLogger contactChangeLogger = new ContactChangeLogger(session);

            contactChangeLogger.LogEvent(contactChangeLogEvent);
        }
예제 #10
0
        public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(settings, "settings");
            Util.ThrowOnNullArgument(session, "session");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            if (onDumpster)
            {
                return(true);
            }
            if (COWSettings.IsImapPoisonMessage(onBeforeNotification, operation, session, item))
            {
                return(true);
            }
            switch (operation)
            {
            case COWTriggerAction.Create:
            case COWTriggerAction.ItemBind:
            case COWTriggerAction.Submit:
                break;

            case COWTriggerAction.Update:
                return(!settings.LegalHoldEnabled());

            default:
                if (operation != COWTriggerAction.FolderBind)
                {
                    return(true);
                }
                break;
            }
            return(true);
        }
예제 #11
0
        public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
        {
            if (!COWContactLogging.COWContactLoggingConfiguration.Instance.IsLoggingEnabled())
            {
                return(true);
            }
            Util.ThrowOnNullArgument(session, "session");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            if (item == null)
            {
                COWContactLogging.Tracer.TraceDebug((long)this.GetHashCode(), "COWContactLogging.SkipItemOperation: Item is null");
                return(true);
            }
            if (!onBeforeNotification)
            {
                COWContactLogging.Tracer.TraceDebug((long)this.GetHashCode(), "COWContactLogging.SkipItemOperation: Not onBeforeNotification");
                return(true);
            }
            string valueOrDefault = item.PropertyBag.GetValueOrDefault <string>(StoreObjectSchema.ItemClass, string.Empty);

            COWContactLogging.Tracer.TraceDebug <string>((long)this.GetHashCode(), "COWContactLogging.SkipItemOperation: ItemClass: {0}", valueOrDefault);
            if (ObjectClass.IsPlace(valueOrDefault))
            {
                return(true);
            }
            if (!ObjectClass.IsContact(valueOrDefault) && !ObjectClass.IsDistributionList(valueOrDefault) && !ObjectClass.IsContactsFolder(valueOrDefault))
            {
                return(true);
            }
            foreach (IContactChangeTracker contactChangeTracker in COWContactLogging.ChangeTrackers)
            {
                if (contactChangeTracker.ShouldLoadPropertiesForFurtherCheck(operation, valueOrDefault, itemId, item))
                {
                    COWContactLogging.Tracer.TraceDebug((long)this.GetHashCode(), "COWContactLogging.SkipItemOperation: A tracker interested.");
                    return(false);
                }
            }
            return(true);
        }
예제 #12
0
        public void ItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, CoreFolder folder, bool onBeforeNotification, OperationResult result, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(session, "session");
            Util.ThrowOnNullArgument(item, "item");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            EnumValidator.ThrowIfInvalid <OperationResult>(result, "result");
            COWContactLinking.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWContactLinking.ItemOperation: processing contact linking for item {0}.", itemId);
            MailboxSession                   mailboxSession                = (MailboxSession)session;
            MailboxInfoForLinking            mailboxInfo                   = MailboxInfoForLinking.CreateFromMailboxSession(mailboxSession);
            ContactLinkingPerformanceTracker performanceTracker            = new ContactLinkingPerformanceTracker(mailboxSession);
            DirectoryPersonSearcher          directoryPersonSearcher       = new DirectoryPersonSearcher(mailboxSession.MailboxOwner);
            ContactStoreForContactLinking    contactStoreForContactLinking = new ContactStoreForCowContactLinking(mailboxSession, performanceTracker);
            ContactLinkingLogger             logger = new ContactLinkingLogger("COWContactLinking", mailboxInfo);
            AutomaticLink automaticLink             = new AutomaticLink(mailboxInfo, logger, performanceTracker, directoryPersonSearcher, contactStoreForContactLinking);

            automaticLink.LinkNewOrUpdatedContactBeforeSave(item, new Func <ContactInfoForLinking, IContactStoreForContactLinking, IEnumerable <ContactInfoForLinking> >(this.GetOtherContactsEnumeratorForCOW));
            if (!onBeforeNotification)
            {
                item.SaveFlags |= PropertyBagSaveFlags.ForceNotificationPublish;
                try
                {
                    item.Save(SaveMode.NoConflictResolution);
                }
                finally
                {
                    item.SaveFlags &= ~PropertyBagSaveFlags.ForceNotificationPublish;
                }
            }
            callbackContext.ContactLinkingProcessingState = ContactLinkingProcessingState.Processed;
        }
예제 #13
0
        public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(session, "session");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            switch (callbackContext.ContactLinkingProcessingState)
            {
            case ContactLinkingProcessingState.DoNotProcess:
                COWContactLinking.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWContactLinking.SkipItemOperation: skipping notification for item {0} because it should not be processed.", itemId);
                return(true);

            case ContactLinkingProcessingState.ProcessBeforeSave:
                return(!onBeforeNotification || state != COWTriggerActionState.Flush);

            case ContactLinkingProcessingState.ProcessAfterSave:
                return(onBeforeNotification);

            case ContactLinkingProcessingState.Processed:
                COWContactLinking.Tracer.TraceDebug <StoreObjectId>((long)this.GetHashCode(), "COWContactLinking.SkipItemOperation: skipping notification for item {0} because it has already been processed.", itemId);
                return(true);
            }
            callbackContext.ContactLinkingProcessingState = this.InspectNotification(operation, session, item, onBeforeNotification, onDumpster);
            COWContactLinking.Tracer.TraceDebug <StoreObjectId, ContactLinkingProcessingState>((long)this.GetHashCode(), "COWContactLinking.SkipItemOperation: inspected item {0} and result is {1}.", itemId, callbackContext.ContactLinkingProcessingState);
            return(callbackContext.ContactLinkingProcessingState != ContactLinkingProcessingState.ProcessBeforeSave || !onBeforeNotification || state != COWTriggerActionState.Flush);
        }
예제 #14
0
        public void ItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, CoreFolder folder, bool onBeforeNotification, OperationResult result, CallbackContext callbackContext)
        {
            Util.ThrowOnNullArgument(dumpster, "dumpster");
            EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
            EnumValidator.ThrowIfInvalid <OperationResult>(result, "result");
            EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
            MailboxSession sessionWithBestAccess = callbackContext.SessionWithBestAccess;

            if (onBeforeNotification)
            {
                if (CalendarLoggingHelper.ShouldLog(item, operation))
                {
                    StoreObjectId storeObjectId = ((ICoreObject)item).StoreObjectId;
                    CalendarLoggingHelper.AddMetadata(item, operation, null);
                    if (operation == COWTriggerAction.Update && state == COWTriggerActionState.Save && CalendarLoggingHelper.ShouldBeCopiedOnWrite(storeObjectId))
                    {
                        if (settings.HoldEnabled() && item.IsLegallyDirty)
                        {
                            return;
                        }
                        if (!settings.IsCurrentFolderItemEnabled(sessionWithBestAccess, item) && !COWCalendarLogging.IsParkedMessagesFolder(settings, sessionWithBestAccess))
                        {
                            return;
                        }
                        if (dumpster.IsDumpsterOverCalendarLoggingQuota(sessionWithBestAccess, settings))
                        {
                            ExTraceGlobals.CalendarLoggingTracer.Information <string, string>((long)session.GetHashCode(), "User {0} has exceeded the calendar logging quota of {1}", session.UserLegacyDN, settings.CalendarLoggingQuota.Value.ToString("A"));
                            StorageGlobals.EventLogger.LogEvent(StorageEventLogConstants.Tuple_COWCalendarLoggingStopped, session.UserLegacyDN, new object[]
                            {
                                session.UserLegacyDN
                            });
                        }
                        else if (dumpster.IsDumpsterOverWarningQuota(settings))
                        {
                            ExTraceGlobals.CalendarLoggingTracer.Information <string, string>((long)session.GetHashCode(), "Disabling calendar logging for user {0}, since it has exceeded the dumpster warning quota of {1}", session.UserLegacyDN, settings.DumpsterWarningQuota.Value.ToString("A"));
                            dumpster.DisableCalendarLogging();
                        }
                        else
                        {
                            StoreObjectId calendarLogGeneratedId = this.PerformCopyOnWrite(sessionWithBestAccess, dumpster, storeObjectId);
                            dumpster.Results.CalendarLogGeneratedId = calendarLogGeneratedId;
                        }
                    }
                    COWSettings.AddMetadata(settings, item, operation);
                    return;
                }
            }
            else if (operation == COWTriggerAction.Update && state == COWTriggerActionState.Save && result == OperationResult.Failed)
            {
                dumpster.RollbackItemVersion(sessionWithBestAccess, item, dumpster.Results.CalendarLogGeneratedId);
                dumpster.Results.CalendarLogGeneratedId = null;
            }
        }
예제 #15
0
 public bool SkipItemOperation(COWSettings settings, IDumpsterItemOperations dumpster, COWTriggerAction operation, COWTriggerActionState state, StoreSession session, StoreObjectId itemId, CoreItem item, bool onBeforeNotification, bool onDumpster, bool success, CallbackContext callbackContext)
 {
     Util.ThrowOnNullArgument(settings, "settings");
     Util.ThrowOnNullArgument(session, "session");
     Util.ThrowOnNullArgument(dumpster, "dumpster");
     EnumValidator.ThrowIfInvalid <COWTriggerAction>(operation, "operation");
     EnumValidator.ThrowIfInvalid <COWTriggerActionState>(state, "state");
     if (onDumpster)
     {
         ExTraceGlobals.CalendarLoggingTracer.Information <string>((long)session.GetHashCode(), "Skipping calendar COW item operation for user {0}, since the operation is on dumpster", session.UserLegacyDN);
         return(true);
     }
     if (!CalendarLoggingHelper.ShouldLog(operation))
     {
         ExTraceGlobals.CalendarLoggingTracer.Information <string, COWTriggerAction>((long)session.GetHashCode(), "Skipping calendar COW item operation for user {0}, since the trigger action {1} is not interesting", session.UserLegacyDN, operation);
         return(true);
     }
     if (!onBeforeNotification && operation != COWTriggerAction.Update)
     {
         ExTraceGlobals.CalendarLoggingTracer.Information <string>((long)session.GetHashCode(), "Skipping calendar COW item operation for user {0}, since we are only interested in on-before notifications and update trigger actions", session.UserLegacyDN);
         return(true);
     }
     if (COWSettings.IsImapPoisonMessage(onBeforeNotification, operation, session, item))
     {
         ExTraceGlobals.CalendarLoggingTracer.Information <string>((long)session.GetHashCode(), "Skipping calendar COW item operation for user {0}, since the items is marked as IMAP poison message", session.UserLegacyDN);
         return(true);
     }
     if (!settings.IsCalendarLoggingEnabled())
     {
         ExTraceGlobals.CalendarLoggingTracer.Information <string>((long)session.GetHashCode(), "Skipping calendar COW item operation for user {0}, since calendar logging is disabled for this user", session.UserLegacyDN);
         return(true);
     }
     return(false);
 }