From 5f16e3cd759952f7dada3c481569159e443c0d52 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Przemys=C5=82aw=20K=C5=82ys?= Date: Tue, 1 Sep 2026 10:05:12 +0200 Subject: [PATCH] Fix breadcrumbs in process-isolated hosts --- FileInspectorX.Tests/SettingsBehaviorTests.cs | 58 ++++++++++++++++--- FileInspectorX/FileInspectorX.csproj | 2 +- FileInspectorX/Logging/Breadcrumbs.cs | 5 +- 3 files changed, 56 insertions(+), 9 deletions(-) diff --git a/FileInspectorX.Tests/SettingsBehaviorTests.cs b/FileInspectorX.Tests/SettingsBehaviorTests.cs index c5b23370..fbf1aa91 100644 --- a/FileInspectorX.Tests/SettingsBehaviorTests.cs +++ b/FileInspectorX.Tests/SettingsBehaviorTests.cs @@ -1,13 +1,44 @@ -using System.Collections.Generic; -using System.Diagnostics; -using System.Threading; -using FileInspectorX; +using System.Collections.Generic; +using System.Diagnostics; +#if NET8_0_OR_GREATER +using System.Reflection; +using System.Runtime.Loader; +#endif +using System.Threading; +using FileInspectorX; namespace FileInspectorX.Tests; [Xunit.Collection(nameof(DetectionSettingsCollection))] public class SettingsBehaviorTests -{ +{ +#if NET8_0_OR_GREATER + [Xunit.Fact] + public void Breadcrumbs_DoNotRequireProcessAssembly() + { + var logPath = Path.Combine(Path.GetTempPath(), $"FileInspectorX.Breadcrumbs.{Guid.NewGuid():N}.log"); + var loadContext = new ProcessRejectingLoadContext(); + try + { + var assembly = loadContext.LoadFromAssemblyPath(typeof(FileInspector).Assembly.Location); + var settings = assembly.GetType("FileInspectorX.Settings", throwOnError: true)!; + settings.GetProperty("BreadcrumbsEnabled")!.SetValue(null, true); + settings.GetProperty("BreadcrumbsPath")!.SetValue(null, logPath); + var breadcrumbs = assembly.GetType("FileInspectorX.Breadcrumbs", throwOnError: true)!; + var write = breadcrumbs.GetMethod("Write", BindingFlags.Static | BindingFlags.NonPublic)!; + + write.Invoke(null, new object?[] { "ISOLATED_TEST", null, null }); + + Xunit.Assert.Contains($"PID={Environment.ProcessId}", File.ReadAllText(logPath), StringComparison.Ordinal); + } + finally + { + loadContext.Unload(); + File.Delete(logPath); + } + } +#endif + [Xunit.Fact] public void JsonValidationCore_TimesOut_When_StopwatchExpired() { @@ -93,5 +124,18 @@ public void DangerousExtensionsOverrideMode_Merge_Keeps_Defaults() Settings.DangerousExtensionsOverride = prevOverride; Settings.DangerousExtensionsOverrideMode = prevMode; } - } -} + } + +#if NET8_0_OR_GREATER + private sealed class ProcessRejectingLoadContext() : AssemblyLoadContext(isCollectible: true) + { + protected override Assembly? Load(AssemblyName assemblyName) + { + if (string.Equals(assemblyName.Name, "System.Diagnostics.Process", StringComparison.Ordinal)) + throw new FileNotFoundException("Process assembly is unavailable in the isolated test context.", assemblyName.Name); + + return null; + } + } +#endif +} diff --git a/FileInspectorX/FileInspectorX.csproj b/FileInspectorX/FileInspectorX.csproj index ceaf6b31..6e46a7ee 100644 --- a/FileInspectorX/FileInspectorX.csproj +++ b/FileInspectorX/FileInspectorX.csproj @@ -8,7 +8,7 @@ true FileInspectorX: dependency-free content type detection (magic bytes + heuristics) FileInspectorX - 1.1.1 + 1.1.2 true README.MD https://github.com/EvotecIT/FileInspectorX diff --git a/FileInspectorX/Logging/Breadcrumbs.cs b/FileInspectorX/Logging/Breadcrumbs.cs index 220e91b4..2402efaa 100644 --- a/FileInspectorX/Logging/Breadcrumbs.cs +++ b/FileInspectorX/Logging/Breadcrumbs.cs @@ -43,7 +43,11 @@ internal static void Write(string tag, string? message = null, string? path = nu } } catch { } var now = DateTime.UtcNow.ToString("yyyy-MM-dd HH:mm:ss.fffZ"); +#if NET8_0_OR_GREATER + var pid = Environment.ProcessId; +#else var pid = Process.GetCurrentProcess().Id; +#endif var tid = Environment.CurrentManagedThreadId; var line = $"{now} PID={pid} TID={tid} TAG={tag}{(path!=null?" PATH="+path:"")}{(message!=null?" MSG="+message:"")}"; File.AppendAllText(file, line + Environment.NewLine); @@ -51,4 +55,3 @@ internal static void Write(string tag, string? message = null, string? path = nu catch { /* never throw from breadcrumbs */ } } } -