public static LocalFolder Bind(MailboxSession mailboxSession, StoreId folderId) { return(LocalFolder.Bind(mailboxSession, folderId, delegate(LocalFolder folder) { folder.Initialize(); })); }
private bool SynchronizeFolder(MailboxSession mailboxSession, LocalFolder localFolder, ItemSynchronizer itemSynchronizer) { BaseFolderType folder = this.GetFolder(mailboxSession, localFolder); this.ActualLevelOfDetails = new SharingLevelOfDetails(folder); this.OriginalLevelOfDetails = new SharingLevelOfDetails(localFolder.LoadLevelOfDetails()); if (this.OriginalLevelOfDetails == LevelOfDetails.None) { SharingEngine.Tracer.TraceDebug <SharingEngine, SharingLevelOfDetails>((long)this.GetHashCode(), "{0}: Access level changed from None to {1}. Saving the actual access level.", this, this.ActualLevelOfDetails); localFolder.SaveLevelOfDetails(this.ActualLevelOfDetails); } if (this.ActualLevelOfDetails == LevelOfDetails.None) { SharingEngine.Tracer.TraceDebug <LocalFolder>((long)this.GetHashCode(), "{0}: Permissions revoked for this folder.", localFolder); localFolder.DeleteAllItems(); localFolder.DeleteSyncState(); localFolder.SaveLevelOfDetails(this.ActualLevelOfDetails); SharingEngine.Tracer.TraceDebug <LocalFolder>((long)this.GetHashCode(), "{0}: All items have been deleted.", localFolder); SharingLog.LogEntry(mailboxSession, "User no longer has permissions to the publisher's folder. All items have been removed."); return(true); } if (this.ActualLevelOfDetails > this.OriginalLevelOfDetails) { SharingEngine.Tracer.TraceDebug <SharingEngine>((long)this.GetHashCode(), "{0}: Permission to the remote folder has increased. Resetting the sync state.", this); this.SyncState = null; localFolder.DeleteSyncState(); } SharingLog.LogEntry(mailboxSession, "Current permissions to the publisher's folder: " + this.ActualLevelOfDetails); return(this.SynchronizeFolderItems(mailboxSession, localFolder, itemSynchronizer)); }
private BaseFolderType GetFolder(MailboxSession mailboxSession, LocalFolder localFolder) { BaseFolderType folder; try { folder = this.ExchangeService.GetFolder(localFolder.RemoteFolderId); } catch (FailedCommunicationException ex) { SharingEngine.Tracer.TraceDebug <SharingEngine, FailedCommunicationException>((long)this.GetHashCode(), "{0}: GetFolder failed with the following exception: {1}", this, ex); SharingLog.LogEntry(mailboxSession, "GetFolder failed with the following exception: " + ex); SharingEngine.Tracer.TraceDebug <SharingEngine>((long)this.GetHashCode(), "{0}: Failure was due connection error which might indicate the EWS endpoint needs update", this); Uri uri; try { uri = this.Discover(); } catch (LocalizedException ex2) { SharingEngine.Tracer.TraceDebug <SharingEngine, LocalizedException>((long)this.GetHashCode(), "{0}: Unable to discover new EWS endpoint because of exception: {1}", this, ex2); throw new AutodiscoverFailedException(ex2, ex); } if (StringComparer.OrdinalIgnoreCase.Equals(uri.ToString(), this.ExchangeService.Url)) { SharingEngine.Tracer.TraceDebug <SharingEngine>((long)this.GetHashCode(), "{0}: EWS endpoint continues to be the same, failing with original exception", this); throw ex; } this.ExchangeService.Url = uri.ToString(); folder = this.ExchangeService.GetFolder(localFolder.RemoteFolderId); SharingLog.LogEntry(mailboxSession, "The Sharing Url for this subscription has been updated to " + uri); this.UpdateSubscriptionData(mailboxSession, uri); } return(folder); }
private bool SynchronizeFolderItems(MailboxSession mailboxSession, LocalFolder localFolder, ItemSynchronizer itemSynchronizer) { bool result = false; SharingEngine.Tracer.TraceDebug <SharingEngine>((long)this.GetHashCode(), "{0}: Start syncing folder", this); try { while (this.BatchSync(mailboxSession, localFolder, itemSynchronizer)) { if (this.Deadline.IsOver) { SharingEngine.Tracer.TraceDebug <SharingEngine>((long)this.GetHashCode(), "{0}: Timed out while syncing new items.", this); break; } } } finally { localFolder.DeleteSelectedItems(); } this.EnforceLevelOfDetails(mailboxSession, localFolder, itemSynchronizer); localFolder.SaveLevelOfDetails(this.ActualLevelOfDetails); SharingEngine.Tracer.TraceDebug <SharingEngine>((long)this.GetHashCode(), "{0}: End syncing folder", this); if (!this.Deadline.IsOver) { result = true; localFolder.UpdateLastSyncTimes(); SharingLog.LogEntry(mailboxSession, "Synchronization completed."); } return(result); }
private bool Execute(MailboxSession mailboxSession, LocalFolder localFolder, ItemSynchronizer itemSynchronizer, Deadline processingDeadline) { SharingEngine.Tracer.TraceDebug <SharingEngine>(0L, "{0}: Starting synchrounous execution", this); this.Deadline = processingDeadline; bool flag = false; bool flag2; try { flag2 = this.SynchronizeFolder(mailboxSession, localFolder, itemSynchronizer); flag = true; } finally { if (!flag) { PerformanceCounters.FolderSynchronizationFailures.Increment(); } else { this.UpdateTimeBasedPerfCounters(); } } if (flag2) { PerformanceCounters.FoldersProcessedSynchronously.Increment(); } else { PerformanceCounters.SynchronizationTimeouts.Increment(); } SharingEngine.Tracer.TraceDebug <SharingEngine>(0L, "{0}: Ended synchrounous execution", this); return(flag2); }
private void EnforceLevelOfDetails(MailboxSession mailboxSession, LocalFolder localFolder, ItemSynchronizer itemSynchronizer) { if (this.OriginalLevelOfDetails > this.ActualLevelOfDetails) { SharingEngine.Tracer.TraceDebug <SharingEngine, SharingLevelOfDetails, SharingLevelOfDetails>((long)this.GetHashCode(), "{0}: Updating existing items due to permission changes. Original level: {1}. Actual level: {2}.", this, this.OriginalLevelOfDetails, this.ActualLevelOfDetails); localFolder.ProcessAllItems(delegate(StoreId localItemId) { itemSynchronizer.EnforceLevelOfDetails(mailboxSession, localItemId, this.ActualLevelOfDetails); }); } }
private static LocalFolder BindToLocalFolder(MailboxSession mailboxSession, StoreId sharingFolderId) { LocalFolder result; try { result = LocalFolder.BindOnly(mailboxSession, sharingFolderId); } catch (ObjectNotFoundException ex) { SharingEngine.Tracer.TraceError <IExchangePrincipal, ObjectNotFoundException>(0L, "{0}: Failed to bind to local folder. Exception: {1}", mailboxSession.MailboxOwner, ex); throw new SharingFolderNotFoundException(ex); } return(result); }
private static LocalFolder Bind(MailboxSession mailboxSession, StoreId folderId, LocalFolder.ProcessFolderDelegate processFolder) { SharingBindingManager sharingBindingManager = new SharingBindingManager(mailboxSession); SharingBindingData sharingBindingDataInFolder = sharingBindingManager.GetSharingBindingDataInFolder(folderId); if (sharingBindingDataInFolder == null) { LocalFolder.Tracer.TraceError <IExchangePrincipal, StoreId>(0L, "{0}: Unable to find the binding for folder {1}, fail sync", mailboxSession.MailboxOwner, folderId); throw new SubscriptionNotFoundException(); } bool flag = false; Item item = null; Folder folder = null; LocalFolder localFolder = null; try { item = LocalFolder.BindToBindingMessage(mailboxSession, sharingBindingDataInFolder.Id); folder = Folder.Bind(mailboxSession, folderId, LocalFolder.extraProperties); localFolder = new LocalFolder(mailboxSession, folder, sharingBindingDataInFolder.RemoteFolderId, item); processFolder(localFolder); flag = true; } finally { if (!flag) { if (localFolder != null) { localFolder.Dispose(); } else { if (item != null) { item.Dispose(); } if (folder != null) { folder.Dispose(); } } localFolder = null; } } return(localFolder); }
private void SafeUpdateBindingItem(Action <Item> stampBindingItem) { stampBindingItem(this.binding); ConflictResolutionResult conflictResolutionResult = this.binding.Save(SaveMode.ResolveConflicts); if (conflictResolutionResult.SaveStatus == SaveResult.IrresolvableConflict) { LocalFolder.Tracer.TraceDebug <LocalFolder>((long)this.GetHashCode(), "{0}: Conflict occurs when saving the binding message. Reload and try saving again.", this); StoreObjectId objectId = this.binding.Id.ObjectId; this.binding.Dispose(); this.binding = LocalFolder.BindToBindingMessage(this.mailboxSession, objectId); this.binding.OpenAsReadWrite(); stampBindingItem(this.binding); this.binding.Save(SaveMode.NoConflictResolution); } this.binding.Load(); }
public static ItemSynchronizer Create(LocalFolder localFolder, CultureInfo clientCulture) { switch (localFolder.Type) { case StoreObjectType.CalendarFolder: ItemSynchronizer.Tracer.TraceDebug(0L, "ItemSynchronizer.Create: Creating synchronizer for Calendar folder."); return(new CalendarItemSynchronizer(localFolder, clientCulture)); case StoreObjectType.ContactsFolder: ItemSynchronizer.Tracer.TraceDebug(0L, "ItemSynchronizer.Create: Creating synchronizer for Contacts folder."); return(new ContactItemSynchronizer(localFolder)); default: ItemSynchronizer.Tracer.TraceWarning <StoreObjectType>(0L, "ItemSynchronizer.Create: No custom synchronizer for type {0}. Creating default synchronizer.", localFolder.Type); return(new DefaultItemSynchronizer(localFolder)); } }
public static bool SyncFolder(MailboxSession mailboxSession, StoreId sharingFolderId, Deadline processingDeadline) { if (!SharingEngine.tracker.Start(mailboxSession.MailboxOwner.MailboxInfo.MailboxGuid, sharingFolderId)) { SharingEngine.Tracer.TraceError <StoreId>(0L, "{0}: Folder is already syncing", sharingFolderId); throw new PendingSynchronizationException(); } bool result = true; SharingEngine sharingEngine = null; LocalFolder localFolder = null; ItemSynchronizer itemSynchronizer = null; try { SharingLog.LogEntry(mailboxSession, "Starting sync for folder " + sharingFolderId); localFolder = SharingEngine.GetLocalFolder(mailboxSession, sharingFolderId); localFolder.UpdateLastAttemptedSyncTime(); itemSynchronizer = SharingEngine.CreateItemSynchronizer(mailboxSession, localFolder); sharingEngine = SharingEngine.Create(mailboxSession, sharingFolderId); result = sharingEngine.Execute(mailboxSession, localFolder, itemSynchronizer, processingDeadline); } catch (Exception arg) { SharingLog.LogEntry(mailboxSession, string.Format("Synchronization finished unexpectedly due to the following error: {0}, External Url {1}", arg, (sharingEngine != null && sharingEngine.ExchangeService != null) ? sharingEngine.ExchangeService.Url : "Not specified")); throw; } finally { SharingEngine.UnblockFolderSync(mailboxSession.MailboxOwner.MailboxInfo.MailboxGuid, sharingFolderId); if (itemSynchronizer != null) { itemSynchronizer = null; } if (localFolder != null) { localFolder.Dispose(); localFolder = null; } if (sharingEngine != null) { sharingEngine.Dispose(); } } return(result); }
public ItemSynchronizer(LocalFolder localFolder) { this.localFolder = localFolder; }
public CalendarItemSynchronizer(LocalFolder localFolder, CultureInfo clientCulture) : base(localFolder) { this.appointmentTranslator = new AppointmentTranslator(clientCulture); }
public ContactItemSynchronizer(LocalFolder localFolder) : base(localFolder) { }
private static ItemSynchronizer CreateItemSynchronizer(MailboxSession mailboxSession, LocalFolder localFolder) { IEnumerable <CultureInfo> preferredCultures = mailboxSession.MailboxOwner.PreferredCultures; CultureInfo cultureInfo = preferredCultures.Any <CultureInfo>() ? preferredCultures.First <CultureInfo>() : CultureInfo.CurrentCulture; SharingEngine.Tracer.TraceDebug <CultureInfo, IExchangePrincipal>(0L, "Culture {0} has been selected for mailbox {1}.", cultureInfo, mailboxSession.MailboxOwner); return(ItemSynchronizer.Create(localFolder, cultureInfo)); }
private bool BatchSync(MailboxSession mailboxSession, LocalFolder localFolder, ItemSynchronizer itemSynchronizer) { List <ItemIdType> list = new List <ItemIdType>(); if (string.IsNullOrEmpty(this.SyncState)) { this.SyncState = localFolder.LoadSyncState(); } Changes changes = this.ExchangeService.GetChanges(128, this.SyncState); if (changes == null) { SharingEngine.Tracer.TraceDebug <LocalFolder>((long)this.GetHashCode(), "{0}: Unable to retrieve changes", localFolder); return(false); } SharingEngine.Tracer.TraceDebug <SharingEngine, int>((long)this.GetHashCode(), "{0}: Called SyncFolderItems. Got {1} changes", this, changes.Items.Length); foreach (ItemChange itemChange in changes.Items) { switch (itemChange.ChangeType) { case ItemChangeType.Create: case ItemChangeType.Update: list.Add(itemChange.Id); break; case ItemChangeType.Delete: { StoreId localIdFromRemoteId = localFolder.GetLocalIdFromRemoteId(itemChange.Id.Id); if (localIdFromRemoteId != null) { localFolder.SelectItemToDelete(localIdFromRemoteId); } break; } } } if (list.Count > 0) { SharingEngine.Tracer.TraceDebug <SharingEngine, int>((long)this.GetHashCode(), "{0}: Processing {1} creates/updates", this, list.Count); IEnumerable <ItemType> item = this.ExchangeService.GetItem(list.ToArray(), localFolder.Type); if (item != null) { int num = 0; foreach (ItemType remoteItem in item) { if (this.Deadline.IsOver) { SharingEngine.Tracer.TraceError <SharingEngine>((long)this.GetHashCode(), "{0}: run out of time for completing the sync", this); return(true); } if (!this.TrySyncOneItem(mailboxSession, itemSynchronizer, remoteItem)) { num++; SharingEngine.Tracer.TraceError <SharingEngine, int>((long)this.GetHashCode(), "{0}: Item failed to sync. Total number of failures during this batch: {1}.", this, num); if (num == 30) { SharingEngine.Tracer.TraceError <SharingEngine>((long)this.GetHashCode(), "{0}: Too many items have failed. Ending batch loop.", this); break; } } } SharingLog.LogEntry(mailboxSession, string.Format("Synchronized {0} out of {1} items during this batch.", list.Count - num, list.Count)); if (num == list.Count || num == 30) { SharingEngine.Tracer.TraceError <SharingEngine>((long)this.GetHashCode(), "{0}: Excessive errors while processing batch. Sync state will not be saved.", this); throw new BatchSynchronizationFailedException(); } } } localFolder.SaveSyncState(changes.SyncState); this.SyncState = changes.SyncState; return(changes.MoreChangesAvailable); }
public static LocalFolder BindOnly(MailboxSession mailboxSession, StoreId folderId) { return(LocalFolder.Bind(mailboxSession, folderId, delegate(LocalFolder folder) { })); }
public void CreateAppointment(ExchangeService exchangeService, MailboxSession session, CalendarItemType remoteItem, LocalFolder localFolder) { AppointmentTranslator.Tracer.TraceDebug <AppointmentTranslator, string>((long)this.GetHashCode(), "{0}: Creating appointment {1}", this, remoteItem.ItemId.Id); CalendarItem calendarItem = CalendarItem.Create(session, localFolder.Id); bool flag = false; try { this.UpdateAppointment(exchangeService, session, remoteItem, calendarItem); flag = true; } catch (LastOccurrenceDeletionException arg) { AppointmentTranslator.Tracer.TraceDebug <AppointmentTranslator, string, LastOccurrenceDeletionException>((long)this.GetHashCode(), "{0}: All occurrences in the series were deleted - {1}, Error - {2}, We will delete the local item because there are no instances.", this, remoteItem.ItemId.Id, arg); localFolder.SelectItemToDelete(calendarItem.Id.ObjectId); flag = true; } finally { if (!flag && calendarItem.Id != null) { localFolder.SelectItemToDelete(calendarItem.Id.ObjectId); } calendarItem.Dispose(); } }
public DefaultItemSynchronizer(LocalFolder localFolder) : base(localFolder) { }