From 2aa0fd7c21c3e093784d2f2b4e81668569554bc0 Mon Sep 17 00:00:00 2001 From: Tom Longhurst <30480171+thomhurst@users.noreply.github.com> Date: Fri, 9 May 2025 18:12:38 +0100 Subject: [PATCH] Fix KeyNotFoundException when comparing dictionaries --- .../DictionaryAssertionTests.cs | 10 +++++++ TUnit.Assertions/Compare.cs | 26 +++++++++++++++++++ 2 files changed, 36 insertions(+) diff --git a/TUnit.Assertions.UnitTests/DictionaryAssertionTests.cs b/TUnit.Assertions.UnitTests/DictionaryAssertionTests.cs index c8a9521c80..ea1032427b 100644 --- a/TUnit.Assertions.UnitTests/DictionaryAssertionTests.cs +++ b/TUnit.Assertions.UnitTests/DictionaryAssertionTests.cs @@ -1,3 +1,4 @@ +using System.Collections.Immutable; using TUnit.Assertions.Extensions; namespace TUnit.Assertions.UnitTests; @@ -36,4 +37,13 @@ public async Task String_Dictionary_Contains_Key_IgnoreCase() await TUnitAssert.That(dictionary).ContainsKey("blah", StringComparer.InvariantCultureIgnoreCase); } + + [Test] + public async Task Immutable_Dictionary_Does_Not_Contain_Key() + { + await TUnitAssert.ThrowsAsync(async () => + await TUnitAssert.That(ImmutableDictionary.Empty.Add("Hello", 1)) + .IsEquivalentTo(ImmutableDictionary.Empty.Add("Hello2", 1)) + ); + } } \ No newline at end of file diff --git a/TUnit.Assertions/Compare.cs b/TUnit.Assertions/Compare.cs index 4396b0fe43..687953c05b 100644 --- a/TUnit.Assertions/Compare.cs +++ b/TUnit.Assertions/Compare.cs @@ -91,6 +91,32 @@ private static IEnumerable CheckEquivalent< foreach (var key in keys) { + if (!actualDictionary.Contains(key)) + { + yield return new ComparisonFailure + { + Type = MemberType.DictionaryItem, + Actual = $"No entry with key: {key}", + Expected = $"[{key}] = {expectedDictionary[key]}", + NestedMemberNames = [..memberNames, $"[{key}]"] + }; + + yield break; + } + + if (!expectedDictionary.Contains(key)) + { + yield return new ComparisonFailure + { + Type = MemberType.DictionaryItem, + Actual = $"[{key}] = {actualDictionary[key]}", + Expected = $"No entry with key: {key}", + NestedMemberNames = [..memberNames, $"[{key}]"] + }; + + yield break; + } + var actualObject = actualDictionary[key]; var expectedObject = expectedDictionary[key];