1--TEST--
2Lazy objects: setRawValueWithoutLazyInitialization() leaves property as lazy if exception prevents update
3--FILE--
4<?php
5
6class C {
7    public function __construct() {
8        printf("%s\n", __METHOD__);
9    }
10    public int $a;
11    public $b;
12}
13
14function test(string $name, object $obj) {
15    printf("# %s\n", $name);
16
17    $reflector = new ReflectionClass(C::class);
18    try {
19        $reflector->getProperty('a')->setRawValueWithoutLazyInitialization($obj, new stdClass);
20    } catch (Error $e) {
21        printf("%s: %s\n", $e::class, $e->getMessage());
22    }
23
24    // Prop is still lazy: This triggers initialization
25    $obj->a = 1;
26    var_dump(!$reflector->isUninitializedLazyObject($obj));
27    var_dump($obj);
28}
29
30$reflector = new ReflectionClass(C::class);
31$obj = $reflector->newLazyGhost(function ($obj) {
32    $obj->__construct();
33});
34
35test('Ghost', $obj);
36
37$obj = $reflector->newLazyProxy(function () {
38    return new C();
39});
40
41test('Proxy', $obj);
42
43?>
44--EXPECTF--
45# Ghost
46TypeError: Cannot assign stdClass to property C::$a of type int
47C::__construct
48bool(true)
49object(C)#%d (2) {
50  ["a"]=>
51  int(1)
52  ["b"]=>
53  NULL
54}
55# Proxy
56TypeError: Cannot assign stdClass to property C::$a of type int
57C::__construct
58bool(true)
59lazy proxy object(C)#%d (1) {
60  ["instance"]=>
61  object(C)#%d (2) {
62    ["a"]=>
63    int(1)
64    ["b"]=>
65    NULL
66  }
67}
68