Skip to content

Commit 6344cc1

Browse files
committed
test property hooks
1 parent 4842d2b commit 6344cc1

File tree

3 files changed

+44
-2
lines changed

3 files changed

+44
-2
lines changed

src/Analyser/MutatingScope.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3350,7 +3350,7 @@ public function enterFunction(
33503350

33513351
private function enterFunctionLike(
33523352
PhpFunctionFromParserNodeReflection $functionReflection,
3353-
bool $preserveConstructorScope,
3353+
bool $preserveConstructorScope,
33543354
): self
33553355
{
33563356
$parametersByName = [];

src/Analyser/NodeScopeResolver.php

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -930,9 +930,16 @@ private function processStmtNode(
930930
$classStatementsGatherer = new ClassStatementsGatherer($classReflection, $nodeCallback);
931931
$this->processAttributeGroups($stmt, $stmt->attrGroups, $classScope, $classStatementsGatherer);
932932

933-
// analyze static methods first, constructor next and instance methods last so we can carry over the scope
933+
// analyze static methods first; constructor next; instance methods and property hooks last so we can carry over the scope
934934
$classLikeStatements = $stmt->stmts;
935935
usort($classLikeStatements, static function ($a, $b) {
936+
if ($a instanceof Node\Stmt\Property) {
937+
return 1;
938+
}
939+
if ($b instanceof Node\Stmt\Property) {
940+
return -1;
941+
}
942+
936943
if (!$a instanceof Node\Stmt\ClassMethod || !$b instanceof Node\Stmt\ClassMethod) {
937944
return 0;
938945
}
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
<?php // lint >= 8.4
2+
3+
namespace RememberReadOnlyConstructorInPropertyHookBodies;
4+
5+
use function PHPStan\Testing\assertType;
6+
7+
class User
8+
{
9+
public string $name {
10+
get {
11+
assertType('1|2', $this->type);
12+
return $this->name ;
13+
}
14+
set {
15+
if (strlen($value) === 0) {
16+
throw new ValueError("Name must be non-empty");
17+
}
18+
assertType('1|2', $this->type);
19+
$this->name = $value;
20+
}
21+
}
22+
23+
private readonly int $type;
24+
25+
public function __construct(
26+
string $name
27+
) {
28+
$this->name = $name;
29+
if (rand(0,1)) {
30+
$this->type = 1;
31+
} else {
32+
$this->type = 2;
33+
}
34+
}
35+
}

0 commit comments

Comments
 (0)