[Testing] Make tests depending on GC less flaky#28489
[Testing] Make tests depending on GC less flaky#28489simonrozsival wants to merge 4 commits intomainfrom
Conversation
There was a problem hiding this comment.
Pull Request Overview
This PR refactors the test infrastructure to reduce flaky behavior by replacing direct GC calls with helper methods that perform multiple collections. Key changes include updating TestHelpers to provide both synchronous and async GC collection helpers, and using these helpers throughout various unit tests to improve GC reliability.
Reviewed Changes
Copilot reviewed 24 out of 24 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
| src/Controls/tests/Core.UnitTests/TestHelpers.cs | Updated GC collection methods; converted an async method to a synchronous one with an added overload for async collection and added a generic WaitForCollect. |
| src/Controls/tests/Core.UnitTests/SetterSpecificityListTests.cs | Replaced direct GC calls with TestHelpers.WaitForCollect for improved object collection assertion. |
| src/Controls/tests/Core.UnitTests/PlatformBindingTests.cs | Replaced direct GC calls with TestHelpers.Collect. |
| src/Controls/tests/Core.UnitTests/MapTests.cs | Switched from Collect to CollectAsync to align with async test behavior. |
| src/Controls/tests/Core.UnitTests/NavigationUnitTest.cs | Replaced direct GC calls with TestHelpers.Collect. |
| src/Controls/tests/Core.UnitTests/ListProxyTests.cs | Updated GC calls with TestHelpers.Collect for consistency. |
| src/Controls/tests/Core.UnitTests/BindableLayoutTests.cs | Replaced GC.Collect sequences with TestHelpers.CollectAsync. |
| src/Controls/tests/Core.UnitTests/VisualElementTests.cs | Updated GC collection calls to use TestHelpers.CollectAsync. |
| src/Controls/tests/Core.UnitTests/BindingBaseUnitTests.cs | Updated direct GC calls to use TestHelpers.Collect. |
| src/Controls/tests/Core.UnitTests/WindowsTests.cs | Replaced direct GC collection with TestHelpers.CollectAsync. |
| src/Core/tests/UnitTests/MauiContextTests.cs | Updated GC calls to use TestHelpers.Collect. |
| src/Controls/tests/Core.UnitTests/TitleBarTests.cs | Replaced GC calls with TestHelpers.CollectAsync. |
| src/Controls/tests/Core.UnitTests/MessagingCenterTests.cs | Replaced GC calls with TestHelpers.Collect. |
| src/Controls/tests/Core.UnitTests/BindingUnitTests.cs | Updated various GC calls with appropriate TestHelpers.Collect/CollectAsync. |
| src/Controls/tests/Core.UnitTests/WeakEventProxyTests.cs | Replaced direct GC calls with TestHelpers.CollectAsync. |
| src/Controls/tests/DeviceTests/Elements/Window/WindowTests.Windows.cs | Switched GC calls to TestHelpers.Collect. |
| src/Controls/tests/Core.UnitTests/TypedBindingUnitTests.cs | Replaced multiple direct GC calls with TestHelpers.Collect / CollectAsync as appropriate. |
| src/Controls/tests/Core.UnitTests/Layouts/GridLayoutTests.cs | Replaced GC calls with TestHelpers.CollectAsync. |
| src/Controls/tests/Core.UnitTests/MultiPageTests.cs | Updated GC calls to use TestHelpers.Collect. |
| src/Controls/tests/Core.UnitTests/ListViewTests.cs | Replaced direct GC calls with TestHelpers.Collect for consistency. |
Comments suppressed due to low confidence (1)
src/Controls/tests/Core.UnitTests/TestHelpers.cs:39
- [nitpick] Consider renaming WaitForCollect to more clearly communicate its semantics since it returns false when the target is collected. This could help avoid confusion among future maintainers.
public static async Task<bool> WaitForCollect<T>(this WeakReference<T> reference)
| { | ||
| for (int i = 0; i < 40; i++) | ||
| { | ||
| await Task.Yield(); |
There was a problem hiding this comment.
Is this call intentionally in the for loop? I would naively expect it to be called once.
There was a problem hiding this comment.
In this case I just modified the existing WaitForCollect for WeakReference<T> and I have not considered changing it.
|
/rebase |
fd6c79f to
fa51962
Compare
|
I'm not sure what's going on but this PR isn't making it more likely to pass, but it's making them fail every time in CI. The tests are passing just fine for me locally. I don't have time to investigate at the moment, so I'm closing the PR. |
Description of Change
This PR is motivated by frequently failing
SetterSpecificityListTests.RemovingLastValueDoesNotLeak. It is often not enough to callGC.Collect() + GC.WaitForPendingFinalizers()once to ensure that the objects are collected (for some reason). Even in tests in dotnet/runtime, we call GC multiple times to reduce the chance it does not collect what we need (for example https://github.com/dotnet/runtime/blob/367cf39652b1193d04ce3ac345a6384ecba53382/src/tests/nativeaot/SmokeTests/DynamicGenerics/dictionaries.cs#L1516-L1521)Related to #28357