Skip to content

fix: run-tests timeout can cancel in-flight Test Runner jobs#1743

Merged
hatayama merged 2 commits into
v3-betafrom
feat/run-tests-cancel-testrun-reflection
Jul 13, 2026
Merged

fix: run-tests timeout can cancel in-flight Test Runner jobs#1743
hatayama merged 2 commits into
v3-betafrom
feat/run-tests-cancel-testrun-reflection

Conversation

@hatayama

@hatayama hatayama commented Jul 13, 2026

Copy link
Copy Markdown
Owner

Summary

  • After a run-tests timeout or cancel, Unity can now request Test Runner to stop the in-flight job (EditMode included), not only exit Play Mode.
  • On Test Framework versions where cancel helpers are unavailable or changed, behavior automatically falls back to the existing bounded Play Mode exit path.

User Impact

  • Before: Cancel/timeout relied on Play Mode exit only; EditMode jobs and some PlayMode cases could keep running until they finished on their own.
  • After: When Unity Test Framework exposes CancelTestRun, uloop uses it with the run id from Execute. If IsRunActive() is missing (e.g. TF 2.0 guid overload), cancel still proceeds via the public Play Mode exit + capped wait without retrying reflection.

Changes

  • Keep and pass the Execute run GUID into cancel stop/restore.
  • Resolve CancelTestRun(string) with Public | NonPublic once; cache success and failure.
  • Resolve parameterless IsRunActive() only; miss → Option B fallback.
  • Pure unit tests for TF 1.3.9 / 1.4 / 2.0 shaped lookup.

Verification

  • dotnet test tests/RunTestsExecutionTimeout.UnitTests/RunTestsExecutionTimeout.UnitTests.csproj
  • dist/darwin-arm64/uloop compile --project-path "$(git rev-parse --show-toplevel)" (0 errors / 0 warnings)
  • CI on this PR

Made with Cursor

Review in cubic

Keep the Execute runGuid and call CancelTestRun when available so timeouts
can stop EditMode jobs as well as Play Mode. Lookup uses Public|NonPublic
once and caches misses so TF 2.0 IsRunActive(string) falls back to the
bounded Play Mode exit path without retrying reflection.

Co-authored-by: Cursor <cursoragent@cursor.com>
@coderabbitai

coderabbitai Bot commented Jul 13, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Warning

Review limit reached

@hatayama, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 5 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 39b41ecb-1a46-4d0a-ae2f-bd83182c72d5

📥 Commits

Reviewing files that changed from the base of the PR and between 67427ea and 26869df.

⛔ Files ignored due to path filters (1)
  • Assets/Tests/Editor/TestRunnerApiCancelMethodLookupEditModeTests.cs.meta is excluded by none and included by none
📒 Files selected for processing (2)
  • Assets/Tests/Editor/TestRunnerApiCancelMethodLookupEditModeTests.cs
  • Packages/src/Editor/FirstPartyTools/RunTests/TestFramework/TestRunnerApiCancelBridge.cs
📝 Walkthrough

Walkthrough

Changes

Test cancellation flow

Layer / File(s) Summary
Resolve cancellation API methods
Packages/src/Editor/FirstPartyTools/RunTests/TestFramework/TestRunnerApiCancelMethodLookup.cs, tests/RunTestsExecutionTimeout.UnitTests/TestRunnerApiCancelMethodLookupTests.cs
Reflection resolves CancelTestRun(string) and parameterless IsRunActive(), with tests covering supported, public, mismatched, and missing method shapes.
Cache and invoke cancellation methods
Packages/src/Editor/FirstPartyTools/RunTests/TestFramework/TestRunnerApiCancelBridge.cs
The bridge caches resolved methods, reports fallback logs, exposes capability checks, and safely invokes cancellation and active-run polling.
Propagate run identifiers during cancellation
Packages/src/Editor/FirstPartyTools/RunTests/TestFramework/PlayModeTestExecuter.cs, Packages/src/Editor/FirstPartyTools/RunTests/TestFramework/RunTestsCancelStopRestoreUnityHooks.cs
Test execution returns and captures runGuid, passes it to stop/restore cancellation, and conditionally wires the reflected Unity hooks.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Possibly related PRs

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 21.74% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly matches the main change: improving run-tests timeout/cancel behavior for in-flight Test Runner jobs.
Description check ✅ Passed The description accurately describes the cancellation, fallback behavior, and added tests in this changeset.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/run-tests-cancel-testrun-reflection

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

Assert CancelTestRun and parameterless IsRunActive resolve against the
installed Test Framework so Option A cannot silently degrade on this repo.
Also mark the resolve cache flag volatile for double-checked locking clarity.

Co-authored-by: Cursor <cursoragent@cursor.com>
@hatayama

Copy link
Copy Markdown
Owner Author

LGTM (reviewer: Fable). Follow-up verified at 26869df: the EditMode test asserts the lookup resolves CancelTestRun(string) and parameterless IsRunActive() against the real TF 1.3.9 TestRunnerApi (so a future TF upgrade in this repo fails loudly instead of silently degrading), and _resolved is now volatile. The merge-gate device verification also passed: an intentional EditMode infinite-yield hang with --timeout-seconds 8 timed out with a message showing the CancelTestRun path succeeded, the immediate follow-up EditMode run passed without an Editor restart, and IsRunActive reported false afterward. Option A wiring is complete and version-compatible from TF 1.3.9 through the 2.0 previews.

@hatayama hatayama merged commit b348ad5 into v3-beta Jul 13, 2026
10 checks passed
@hatayama hatayama deleted the feat/run-tests-cancel-testrun-reflection branch July 13, 2026 06:42
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant