예제 #1
0
 /// <summary>
 /// Adds a File watcher under the specified integration name and directory.
 /// Allows a callback to be registered for when any file Create/Delete/Rename/Modify occurs.
 /// </summary>
 /// <param name="integrationName">Name of the registration. Used later to remove the file watcher.</param>
 /// <param name="directory">Directory to watch.</param>
 /// <param name="actionCallback">Callback for when any Create/Delete/Rename/Modify event occurs (All data about the event is lost). Wont occur more than once every second</param>
 public void AddFileWatcher(string integrationName, string directory, IntegrationFilesModifiedDelegate actionCallback)
 {
     // Create 2 entries.
     // First one is to map an integration name to a directory. This makes it so we can deregister by integration name
     // Second one is to store the actual file watcher data that we need to dispose of later.
     this.FileWatcherCache.Set(integrationName, directory);
     this.FileWatcherCache.GetOrCreate(directory, (entry) => this.CreateFileWatcherForIntegration(entry, integrationName, directory, actionCallback));
 }
예제 #2
0
        private FileWatcherData CreateFileWatcherForIntegration(ICacheEntry cacheEntry, string integrationName, string directory, IntegrationFilesModifiedDelegate callback)
        {
            var fileWatcher = new FileSystemWatcher(directory)
            {
                NotifyFilter          = NotifyFilters.Attributes | NotifyFilters.FileName | NotifyFilters.LastWrite,
                IncludeSubdirectories = false,
                EnableRaisingEvents   = true
            };

            // Add observables for each of the event types.
            // Each of them just returns a boolean because we need a shared return type from the observable.
            // We only care that *something* changed, we don't care what actually changed.
            var changedFileObserable = Observable.FromEventPattern <FileSystemEventHandler, FileSystemEventArgs>(h => fileWatcher.Changed += h, h => fileWatcher.Changed -= h)
                                       .Select(x => true);

            var createdFileObserable = Observable.FromEventPattern <FileSystemEventHandler, FileSystemEventArgs>(h => fileWatcher.Created += h, h => fileWatcher.Created -= h)
                                       .Select(x => true);

            var deletedFileObserable = Observable.FromEventPattern <FileSystemEventHandler, FileSystemEventArgs>(h => fileWatcher.Deleted += h, h => fileWatcher.Deleted -= h)
                                       .Select(x => true);

            var renamedFileObserable = Observable.FromEventPattern <RenamedEventHandler, RenamedEventArgs>(h => fileWatcher.Renamed += h, h => fileWatcher.Renamed -= h)
                                       .Select(x => true);

            // Merge all the different file watcher events into 1 observable
            // This allows us to throttle all the events coming through so we don't get more than 1 per second.
            var fileWatcherSubscription = Observable.Merge(changedFileObserable, createdFileObserable, deletedFileObserable, renamedFileObserable)
                                          .Throttle(TimeSpan.FromSeconds(1))
                                          .Subscribe(_ => callback?.Invoke(directory, integrationName));

            cacheEntry.RegisterPostEvictionCallback(this.OnCacheEntryEvicted);
            this.ApplicationLifetime.ApplicationStopping.Register(() => this.RemoveFileWatcher(integrationName));

            return(new FileWatcherData(fileWatcher, fileWatcherSubscription));
        }