-
Notifications
You must be signed in to change notification settings - Fork 555
Fix phpstan/phpstan#14352: "Cannot re-assign $this." false-positive #5281
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
staabm
merged 11 commits into
phpstan:2.1.x
from
phpstan-bot:create-pull-request/patch-t6vskzw
Mar 23, 2026
+112
−0
Merged
Changes from 6 commits
Commits
Show all changes
11 commits
Select commit
Hold shift + click to select a range
4f11780
"Cannot re-assign $this." false-positive
staabm 6dfeac6
Update InvalidVariableAssignRuleTest.php
staabm bbf04d1
test $this=$value when $value is ArrayAccess
staabm 97e4965
fix lint
staabm 8d2b7d4
Use dimFetch flag instead of checking assigned expression type for $t…
phpstan-bot 2e8875d
Revert "Use dimFetch flag instead of checking assigned expression typ…
staabm 5c5e3c7
Use dimFetch flag and check $this type with !->no() for ArrayAccess r…
phpstan-bot ff7af6b
Revert "Use dimFetch flag and check $this type with !->no() for Array…
staabm 12e4ef5
fix
staabm 272e2a9
Update InvalidVariableAssignRule.php
staabm 5f16ff1
Update InvalidVariableAssignRule.php
staabm File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,47 @@ | ||
| <?php declare(strict_types = 1); | ||
|
|
||
| namespace Bug14352; | ||
|
|
||
| use ArrayAccess; | ||
|
|
||
| class TestArrayAccess implements ArrayAccess | ||
| { | ||
| public function doFoo(string $key, string $value): void | ||
| { | ||
| $this[$key] = $value; // fine because ArrayAccess | ||
|
|
||
| $this = $value; // should still fail | ||
| } | ||
|
|
||
| public function offsetExists(mixed $offset): bool | ||
| { | ||
| } | ||
|
|
||
| public function offsetGet(mixed $offset): mixed | ||
| { | ||
| } | ||
|
|
||
| public function offsetSet(mixed $offset, mixed $value): void | ||
| { | ||
| } | ||
|
|
||
| public function offsetUnset(mixed $offset): void | ||
| { | ||
| } | ||
| } | ||
|
|
||
| final class FinalTestPlain | ||
| { | ||
| public function doFoo(string $key, string $value): void | ||
| { | ||
| $this[$key] = $value; | ||
| } | ||
| } | ||
|
|
||
| class TestPlain | ||
| { | ||
| public function doFoo(string $key, string $value): void | ||
| { | ||
| $this[$key] = $value; | ||
| } | ||
| } | ||
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I know the case
might sometimes works if we extends this class and implement ArrayAccess.
But on the opposide, the code
will crash.
IMHO
->yes()should be!->no()and we will have a behavior similar to https://phpstan.org/r/ae445bd2-da35-4b9f-b0cb-a44c0d1b71e8
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pushed. Here's a summary of the changes:
Problem: The reviewer pointed out that for non-final classes like
TestPlain,$this[$key] = $valueshould not error because a subclass might implementArrayAccess. The check should use!->no()instead of->yes().Changes:
VariableAssignNode— AddeddimFetchflag to distinguish$this[$key] = $value(dim-fetch) from$this = $value(direct assignment)AssignHandler— PassdimFetch: truewhen creatingVariableAssignNodefrom dim-fetch assignment pathsInvalidVariableAssignRule— Changed the check to:$node->isDimFetch()to only suppress errors for dim-fetch assignments$scope->getType($variable)(the type of$this) instead of the assigned expression type!->no()instead of->yes()— this allows the "maybe" case for non-final classes (line 614 ofObjectType::isSuperTypeOfreturnsMaybewhen checking an interface against a non-final class)Test data — Added
TestArrayAccessReassigncase to verify$this = $otherstill errors even when$otherimplementsArrayAccessBehavior:
TestArrayAccess(implements ArrayAccess):$this[$key] = $value→ no error,$this = $value→ errorTestArrayAccessReassign:$this = $other→ error (even though$otheris ArrayAccess)FinalTestPlain(final, no ArrayAccess):$this[$key] = $value→ errorTestPlain(non-final, no ArrayAccess):$this[$key] = $value→ no error (subclass might implement ArrayAccess)