X-Git-Url: https://code.grnet.gr/git/pithos-ms-client/blobdiff_plain/268bec7f0c945b230da1107d25a683b5479ef8b7..d21f3c7700f8be0b6db8bfa8d21f9847a231fc2e:/trunk/Pithos.Core/Agents/PollAgent.cs diff --git a/trunk/Pithos.Core/Agents/PollAgent.cs b/trunk/Pithos.Core/Agents/PollAgent.cs index 3483559..d1974bf 100644 --- a/trunk/Pithos.Core/Agents/PollAgent.cs +++ b/trunk/Pithos.Core/Agents/PollAgent.cs @@ -79,13 +79,34 @@ namespace Pithos.Core.Agents [System.ComponentModel.Composition.Import] public NetworkAgent NetworkAgent { get; set; } + [System.ComponentModel.Composition.Import] + public Selectives Selectives { get; set; } + public IStatusNotification StatusNotification { get; set; } + public bool Pause + { + get { + return _pause; + } + set { + _pause = value; + if (!_pause) + _unPauseEvent.Set(); + else + { + _unPauseEvent.Reset(); + } + } + } + private bool _firstPoll = true; //The Sync Event signals a manual synchronisation private readonly AsyncManualResetEvent _syncEvent = new AsyncManualResetEvent(); + private readonly AsyncManualResetEvent _unPauseEvent = new AsyncManualResetEvent(true); + private readonly ConcurrentDictionary _lastSeen = new ConcurrentDictionary(); private readonly ConcurrentDictionary _accounts = new ConcurrentDictionary(); @@ -117,6 +138,7 @@ namespace Pithos.Core.Agents var nextSince = since; try { + await _unPauseEvent.WaitAsync(); UpdateStatus(PithosStatus.PollSyncing); var tasks = from accountInfo in _accounts.Values @@ -164,8 +186,12 @@ namespace Pithos.Core.Agents { var sync = _syncEvent.WaitAsync(); var wait = TaskEx.Delay(TimeSpan.FromSeconds(Settings.PollingInterval), NetworkAgent.CancellationToken); + var signaledTask = await TaskEx.WhenAny(sync, wait); - + + //Pausing takes precedence over manual sync or awaiting + _unPauseEvent.Wait(); + //Wait for network processing to finish before polling var pauseTask=NetworkAgent.ProceedEvent.WaitAsync(); await TaskEx.WhenAll(signaledTask, pauseTask); @@ -274,7 +300,7 @@ namespace Pithos.Core.Agents var differencer = _differencer.PostSnapshot(accountInfo, cleanRemotes); - var filterUris = SelectiveUris[accountInfo.AccountKey]; + var filterUris = Selectives.SelectiveUris[accountInfo.AccountKey]; ProcessDeletedFiles(accountInfo, differencer.Deleted.FilterDirectlyBelow(filterUris)); @@ -295,6 +321,7 @@ namespace Pithos.Core.Agents .Except(NetworkAgent.GetEnumerable(), new LocalFileComparer()) .ToList(); + await _unPauseEvent.WaitAsync(); //Queue all the actions foreach (var message in distinctActions) { @@ -355,6 +382,7 @@ namespace Pithos.Core.Agents readonly AccountsDifferencer _differencer = new AccountsDifferencer(); private Dictionary> _selectiveUris = new Dictionary>(); + private bool _pause; /// /// Deletes local files that are not found in the list of cloud files @@ -607,17 +635,6 @@ namespace Pithos.Core.Agents } } - public void SetSyncUris(Uri accountKey, Uri[] uris) - { - SelectiveUris[accountKey]=uris.ToList(); - } - - protected Dictionary> SelectiveUris - { - get { return _selectiveUris;} - set { _selectiveUris = value; } - } - public void AddAccount(AccountInfo accountInfo) { //Avoid adding a duplicate accountInfo @@ -643,36 +660,44 @@ namespace Pithos.Core.Agents var client = new CloudFilesClient(accountInfo); foreach (var folderUri in added) { - string account; - string container; - var segmentsCount = folderUri.Segments.Length; - if (segmentsCount < 3) - continue; - if (segmentsCount==3) - { - account = folderUri.Segments[1].TrimEnd('/'); - container = folderUri.Segments[2].TrimEnd('/'); - } - else - { - account = folderUri.Segments[2].TrimEnd('/'); - container = folderUri.Segments[3].TrimEnd('/'); - } - IList items; - if(segmentsCount>3) + try { - var folder =String.Join("", folderUri.Segments.Splice(4)); - items = client.ListObjects(account, container, folder); + + string account; + string container; + var segmentsCount = folderUri.Segments.Length; + if (segmentsCount < 3) + continue; + if (segmentsCount == 3) + { + account = folderUri.Segments[1].TrimEnd('/'); + container = folderUri.Segments[2].TrimEnd('/'); + } + else + { + account = folderUri.Segments[2].TrimEnd('/'); + container = folderUri.Segments[3].TrimEnd('/'); + } + IList items; + if (segmentsCount > 3) + { + var folder = String.Join("", folderUri.Segments.Splice(4)); + items = client.ListObjects(account, container, folder); + } + else + { + items = client.ListObjects(account, container); + } + var actions = CreatesToActions(accountInfo, items); + foreach (var action in actions) + { + NetworkAgent.Post(action); + } } - else + catch (Exception exc) { - items = client.ListObjects(account, container); + Log.WarnFormat("Listing of new selective path [{0}] failed with \r\n{1}", folderUri, exc); } - var actions=CreatesToActions(accountInfo, items); - foreach (var action in actions) - { - NetworkAgent.Post(action); - } } //Need to get a listing of each of the URLs, then post them to the NetworkAgent