I don't like the bad docs here, which are wrongly claiming that "serialize(): This method acts as the destructor of the object. The __destruct() method will not be called after this method.".
They are simply meaning that serialize() will NOT call __destruct(). That is the ONLY thing they mean.
Your object that is being serialized will continue to live as a normal object. So you should NOT treat serialize() as your destructor! Treat your object as a still-living copy that the user may be using!
The destructor will always run as normal, later, when your object goes out of scope (or is forcibly unset() by you)).
Example with proof:
<?php
class A implements Serializable
{
public $data = [];
public function __destruct()
{
echo "Destruct of A called.\n";
}
public function serialize()
{
printf("- Serialize of %s called.\n", static::class);
return serialize($this->data);
}
public function unserialize($serialized)
{
printf("- Unserialize of %s called.\n", static::class);
$this->data = unserialize($serialized);
}
}
class B extends A
{
public function __destruct()
{
echo "Destruct of B called.\n";
}
}
$a = new A();
$a->data['inner_b'] = new B();
var_dump($a);
echo "-----------------\n";
echo "Calling serialize($a):\n";
$str = serialize($a);
echo "-----------------\n";
echo "End of script shutdown from here on:...\n";
?>
Result:
```
object(A)#1 (1) {
["data"]=>
array(1) {
["inner_b"]=>
object(B)#2 (1) {
["data"]=>
array(0) {
}
}
}
}
-----------------
Calling serialize($a):
- Serialize of A called.
- Serialize of B called.
-----------------
End of script shutdown from here on:...
Destruct of A called.
Destruct of B called.
```