using ScadaLink.SiteRuntime; using ScadaLink.SiteRuntime.Scripts; namespace ScadaLink.SiteRuntime.Tests.Scripts; /// /// SiteRuntime-009: the dedicated script-execution scheduler must run script bodies on /// its own dedicated threads, not on the shared .NET thread pool, so blocking script /// I/O cannot starve the global pool. /// public class ScriptExecutionSchedulerTests { [Fact] public async Task Scheduler_RunsWork_OffTheThreadPool() { using var scheduler = new ScriptExecutionScheduler(2); bool wasThreadPoolThread = true; string? threadName = null; await Task.Factory.StartNew(() => { wasThreadPoolThread = Thread.CurrentThread.IsThreadPoolThread; threadName = Thread.CurrentThread.Name; }, CancellationToken.None, TaskCreationOptions.DenyChildAttach, scheduler); Assert.False(wasThreadPoolThread, "Script work must not run on a shared thread-pool thread."); Assert.StartsWith("script-execution-", threadName); } [Fact] public void Scheduler_RespectsConfiguredThreadCount() { using var scheduler = new ScriptExecutionScheduler(4); Assert.Equal(4, scheduler.MaximumConcurrencyLevel); } [Fact] public void Scheduler_Shared_ReturnsSameInstanceForOptions() { var options = new SiteRuntimeOptions { ScriptExecutionThreadCount = 3 }; var a = ScriptExecutionScheduler.Shared(options); var b = ScriptExecutionScheduler.Shared(options); Assert.Same(a, b); } }