CoversClass does not transitively target traits used by enumerations#1145
CoversClass does not transitively target traits used by enumerations#1145no-simpler wants to merge 1 commit intosebastianbergmann:mainfrom
CoversClass does not transitively target traits used by enumerations#1145Conversation
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #1145 +/- ##
=========================================
Coverage 96.97% 96.97%
- Complexity 1480 1482 +2
=========================================
Files 110 110
Lines 5057 5057
=========================================
Hits 4904 4904
Misses 153 153 ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
|
As a bug fix, this should target the |
CoversClass does not transitively target traits used by enumerations
|
This branch cannot be rebased due to conflicts, likely because something went wrong when changing the target branch. Might be easier to close this and send a fresh pull request against |
|
I switched target branch in UI and immediately felt stupid. I will re-create the change on correct branch when I get back to my desk. |
No worries :) Thank you for working on this. |
|
Superseded by !1147. |
Problem
When a class uses a trait,
#[CoversClass(TheClass::class)]transitively whitelists the trait's lines for coverage. When an enum uses the same trait, the trait's lines are not whitelisted — PHPUnit flags the test as risky:This forces authors to add
#[UsesTrait]or#[CoversTrait]to enum tests, which is inconsistent with the class behavior and creates friction with static analysis tools that don't accept those attributes.A minimal reproduction is available at https://github.com/no-simpler/phpunit-psalm-trit-catch22 (rows 1 vs 4 in its test matrix).
Root cause
CodeUnitFindingVisitor::leaveNode()resolves trait usages only forClass_andTrait_nodes.Enum_extendsClassLike(notClass_), so it is excluded by the early-return gate. Enums are correctly discovered inenterNode()viaprocessClass(), but their trait lists are never populated.Changes
Three one-line fixes in
CodeUnitFindingVisitor:leaveNode()— includeEnum_in the gate so enums proceed to trait resolutionpostProcessClassOrTrait()signature — widen the type union to acceptEnum_postProcessClassOrTrait()body — routeEnum_into the class branch (enums are stored in$this->classes)Plus a regression test (
testHandlesEnumUsingTrait) and fixture file mirroring the existingtestHandlesTraitUsingTraitpattern.