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.
This commit is contained in:
Den Delimarsky 2021-04-28 18:27:42 -07:00
parent 7d71e8828c
commit c2d54b0733
No known key found for this signature in database
GPG key ID: E1BE1355085F0BCF
2 changed files with 13 additions and 29 deletions

View file

@ -8,6 +8,7 @@
<ItemGroup>
<PackageReference Include="Newtonsoft.Json" Version="13.0.1" />
<PackageReference Include="System.CommandLine" Version="2.0.0-beta1.20071.2" />
<PackageReference Include="System.Reactive" Version="5.0.0" />
<PackageReference Include="System.Runtime.Caching" Version="6.0.0-preview.1.21102.12" />
</ItemGroup>

View file

@ -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<FileSystemEventHandler, FileSystemEventArgs>(
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