From c2d54b0733c096814f80d4ee5f96948422cd773d Mon Sep 17 00:00:00 2001 From: Den Delimarsky <1389609+dend@users.noreply.github.com> Date: Wed, 28 Apr 2021 18:27:42 -0700 Subject: [PATCH] Update how file changes are handled Instead of relying on MemoryCache, I am using Rx, per a suggestion from Twitter, which enables me to automatically de-dupe things on the fly instead of using a polling method for a temporary cache. --- .../Espresso.Shell/Espresso.Shell.csproj | 1 + .../espresso/Espresso.Shell/Program.cs | 41 ++++++------------- 2 files changed, 13 insertions(+), 29 deletions(-) diff --git a/src/modules/espresso/Espresso.Shell/Espresso.Shell.csproj b/src/modules/espresso/Espresso.Shell/Espresso.Shell.csproj index 6c3fac8cd6..8e140bda75 100644 --- a/src/modules/espresso/Espresso.Shell/Espresso.Shell.csproj +++ b/src/modules/espresso/Espresso.Shell/Espresso.Shell.csproj @@ -8,6 +8,7 @@ + diff --git a/src/modules/espresso/Espresso.Shell/Program.cs b/src/modules/espresso/Espresso.Shell/Program.cs index da51c6e699..180159a88c 100644 --- a/src/modules/espresso/Espresso.Shell/Program.cs +++ b/src/modules/espresso/Espresso.Shell/Program.cs @@ -6,10 +6,12 @@ using Espresso.Shell.Core; using Espresso.Shell.Models; using Newtonsoft.Json; using System; -using System.Collections.Specialized; using System.CommandLine; using System.CommandLine.Invocation; using System.IO; +using System.Linq; +using System.Reactive.Concurrency; +using System.Reactive.Linq; using System.Runtime.Caching; using System.Threading; @@ -22,10 +24,6 @@ namespace Espresso.Shell private static FileSystemWatcher watcher = null; public static Mutex Mutex { get => mutex; set => mutex = value; } - private static MemoryCache _memoryCache; - private static CacheItemPolicy _cacheItemPolicy; - private const int CacheExpirationTimeframe = 1000; - static int Main(string[] args) { bool instantiated; @@ -107,16 +105,8 @@ namespace Espresso.Shell { // Configuration file is used, therefore we disregard any other command-line parameter // and instead watch for changes in the file. - try { - var cacheConfig = new NameValueCollection() - { - {"CacheMemoryLimitMegabytes", "1"}, - {"PollingInterval", TimeSpan.FromMilliseconds(1000).ToString()}, - }; - _memoryCache = new MemoryCache("EventCache", cacheConfig); - watcher = new FileSystemWatcher { Path = Path.GetDirectoryName(config), @@ -125,12 +115,14 @@ namespace Espresso.Shell Filter = Path.GetFileName(config) }; - _cacheItemPolicy = new CacheItemPolicy() - { - RemovedCallback = HandleCacheRemoval - }; - - watcher.Changed += new FileSystemEventHandler(HandleEspressoConfigChange); + Observable.FromEventPattern( + h => watcher.Changed += h, + h => watcher.Changed -= h + ) + .SubscribeOn(TaskPoolScheduler.Default) + .Select(e => e.EventArgs) + .Throttle(TimeSpan.FromMilliseconds(25)) + .Subscribe(HandleEspressoConfigChange); // Initially the file might not be updated, so we need to start processing // settings right away. @@ -166,23 +158,14 @@ namespace Espresso.Shell new ManualResetEvent(false).WaitOne(); } - private static void HandleCacheRemoval(CacheEntryRemovedArguments args) + private static void HandleEspressoConfigChange(FileSystemEventArgs fileEvent) { - if (args.RemovedReason != CacheEntryRemovedReason.Expired) return; - - var fileEvent = (FileSystemEventArgs)args.CacheItem.Value; Console.WriteLine("Resetting keep-awake to normal state due to settings change."); ResetNormalPowerState(); Console.WriteLine("Detected a file change. Reacting..."); ProcessSettings(fileEvent.FullPath); } - private static void HandleEspressoConfigChange(object sender, FileSystemEventArgs e) - { - _cacheItemPolicy.AbsoluteExpiration = DateTimeOffset.Now.AddMilliseconds(CacheExpirationTimeframe); - _memoryCache.Set(e.Name, e, _cacheItemPolicy); - } - private static void ProcessSettings(string fullPath) { try