1--TEST-- 2Lazy objects: Initializer effects are reverted after exception (properties hashtable) 3--FILE-- 4<?php 5 6class C { 7 public $a = 1; 8 public int $b = 2; 9 public int $c; 10} 11 12function test(string $name, object $obj) { 13 $reflector = new ReflectionClass(C::class); 14 15 printf("# %s:\n", $name); 16 17 (new ReflectionProperty(C::class, 'c'))->setRawValueWithoutLazyInitialization($obj, 0); 18 19 // Builds properties hashtable 20 var_dump(get_mangled_object_vars($obj)); 21 22 try { 23 $reflector->initializeLazyObject($obj); 24 } catch (Exception $e) { 25 printf("%s\n", $e->getMessage()); 26 } 27 28 var_dump($obj); 29 printf("Is lazy: %d\n", $reflector->isUninitializedLazyObject($obj)); 30} 31 32$reflector = new ReflectionClass(C::class); 33 34$obj = $reflector->newLazyGhost(function ($obj) { 35 var_dump("initializer"); 36 $obj->a = 3; 37 $obj->b = 4; 38 $obj->c = 5; 39 throw new Exception('initializer exception'); 40}); 41 42test('Ghost', $obj); 43 44$obj = $reflector->newLazyProxy(function ($obj) { 45 var_dump("initializer"); 46 $obj->a = 3; 47 $obj->b = 4; 48 $obj->c = 5; 49 throw new Exception('initializer exception'); 50}); 51 52// Initializer effects on the proxy are not reverted 53test('Proxy', $obj); 54 55--EXPECTF-- 56# Ghost: 57array(1) { 58 ["c"]=> 59 int(0) 60} 61string(11) "initializer" 62initializer exception 63lazy ghost object(C)#%d (1) { 64 ["b"]=> 65 uninitialized(int) 66 ["c"]=> 67 int(0) 68} 69Is lazy: 1 70# Proxy: 71array(1) { 72 ["c"]=> 73 int(0) 74} 75string(11) "initializer" 76initializer exception 77lazy proxy object(C)#%d (3) { 78 ["a"]=> 79 int(3) 80 ["b"]=> 81 int(4) 82 ["c"]=> 83 int(5) 84} 85Is lazy: 1 86