Skip to content

Wait for the cancelled tasks to stop before asserting how they ended - #2119

Merged
Rafael-SOWNet merged 1 commit into
masterfrom
wait-for-the-cancelled-tasks-before-asserting
Oct 25, 2026
Merged

Rafael-SOWNet merged 1 commit into
masterfrom
wait-for-the-cancelled-tasks-before-asserting

Conversation

@Rafael-SOWNet

Copy link
Copy Markdown
Member

MultithreadingCancel.TestThoseOnlyCancel asserted two times, and each was wrong on some machine:

  • A stopping time. It cancelled a task at 750 ms and asserted at about 1,500 ms that the task had ended as cancelled. On ubuntu-latest the task was sometimes still Running. That is the failure in 12 of the last 40 failed C# Test runs, 8 on master. On a desktop a cancelled task stops within 195 ms, under coverlet within 182 ms, and on one shared core within 129 ms.
  • A minimum workload. Every row first checked that 30 solves take at least 3 s. On a desktop they take 2.3 s cold, so all 26 rows failed locally, and they will on CI once the library is fast enough there.

Now each task solves until it is cancelled. The test waits for the cancelled tasks to stop, up to a 30 s budget, then waits as long again in case a task that was not meant to be cancelled shows up. Then it asserts:

  • the cancelled tasks are Canceled;
  • the rest are still Running, which is stronger than "not cancelled".

A solve that starts with its token already cancelled has to throw. If it returns instead, the task ends as RanToCompletion and the assertion fails, so a library that ignores the token fails the test rather than hanging it.

The test still catches what it is for, checked by breaking the library on purpose:

the library, broken this test master's test
ignores the token 20 of 26 rows fail, every row that cancels something, all RanToCompletion; the run ends in 76 s
one token shared by every thread 18 fail, Faulted and RanToCompletion; the 8 that pass are the 6 rows that cancel nothing and the 2 one-task rows
notices a cancel a second late passes, 26 of 26 3 fail on one core, with the CI message Status: Running; unbroken, it passes there, 26 of 26

The second clock is why master's test was run on one core: on all eight, its 30 solves finish inside 3 s and every row fails before anything is cancelled.

The full unit suite passes on this branch, 17,039 tests, and again pinned to four cores under coverlet.

Fixes #2118.

🤖 Generated with Claude Code

https://claude.ai/code/session_012sonx8iAspMiwRwokT1Ura

TestThoseOnlyCancel cancelled a task at 750 ms and asserted at about 1,500 ms that it had ended
as cancelled, so it asserted a stopping time. On ubuntu-latest the task was sometimes still
Running, which is the failure in 12 of the last 40 failed C# Test runs, 8 of them on master.
On a desktop the worst stop is 195 ms, 182 ms under coverlet, and 359 ms inside the full suite
on four cores under coverlet.

It also required 30 solves to take at least 3 s, and failed every row when they did not. They
take 2.3 s cold on a desktop, so all 26 rows failed there.

Each task now solves until it is cancelled. The test waits for the cancelled tasks to stop
under a 30 s budget, then asserts that they are Canceled and that the rest are still Running.
A solve that starts with its token already cancelled has to throw; if it returns, the task ends
as RanToCompletion and the assertion fails, so a library that ignores the token fails the test
rather than hanging it.

Checked by breaking the library on purpose: ignoring the token fails every row that cancels
something (20 of 26, all RanToCompletion); one token shared by every thread fails 18 (Faulted
and RanToCompletion); noticing a cancel a second late passes, where master's version of the
test fails with the CI message, Status: Running.

Fixes #2118

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012sonx8iAspMiwRwokT1Ura
@Rafael-SOWNet Rafael-SOWNet added this to the 2.7.0 milestone Oct 25, 2026
@Rafael-SOWNet
Rafael-SOWNet merged commit 3c6e879 into master Oct 25, 2026
27 checks passed
@github-project-automation github-project-automation Bot moved this from Todo to Done in AngouriMath Oct 25, 2026
@Rafael-SOWNet
Rafael-SOWNet deleted the wait-for-the-cancelled-tasks-before-asserting branch October 25, 2026 08:52
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: Done

Development

Successfully merging this pull request may close these issues.

Flaky test: MultithreadingCancel.TestThoseOnlyCancel asserts how fast a cancelled task stops

1 participant