I have this issue where I wonder if it is a PHP bug or intentional behaviour. If I assign in the child class a MySQL resource to a parent member then the value gets lost when running as a thread.
This code does not run - the MySQL resource should be displayed twice:
<?php
class MyFileAbstract extends Threaded
{
protected static $m_Connection;
public static function init() {
static::openFile();
echo "<br>Member accessed from parent: ";
print_r(self::$m_Connection); # the resource is empty
}
}
class MyFile extends MyFileAbstract
{
public static function openFile() {
self::$m_Connection = fopen("/etc/php.ini", "r");
echo "<br>Member accessed from child: ";
print_r(self::$m_Connection)."<br>"; # the resource has value
}
}
class MyThread extends Thread
{
public function run() {
MyFile::init();
}
}
$myThread = new MyThread();
$myThread->start();
echo "<br>Correct output:";
MyFile::init();
?>
This is the result - expected output for "Member accessed from parent:" should be something like "Resource id#2":
Member accessed from child: Resource id #2
Member accessed from parent:
Correct output:
Member accessed from child: Resource id #3
Member accessed from parent: Resource id #3
I have to change it and then the member $m_Connection
receives/keeps the resource from fopen()
. Note: It is working in the thread!
<?php
class MyFileAbstract extends Threaded
{
protected static $m_Connection;
public static function openFile()
{
$sFileName = static::getFileName();
self::$m_Connection = fopen($sFileName, "r");
echo "Member accessed from parent: ";
print_r(self::$m_Connection); # the resource has value
}
}
class MyFile extends MyFileAbstract
{
public static function getFileName()
{
return "/etc/php.ini";
}
}
class MyThread extends Thread
{
public function run()
{
MyFile::openFile();
}
}
$myThread = new MyThread();
$myThread->start();
?>
Output:
Member accessed from parent: Resource id #2
Requirements to run the examples:
I have to connect to MySql in the thread according to this article: http://php.net/manual/en/intro.pthreads.php
UPDATE:
I changed the code: it is opening /etc/php.ini
instead of connecting to MySql database. Same result --> the resource gets lost when returning it from the extended class. The examples are now running 1:1 without changing/adapting anything.
I still think it is a bug. I found now a workaround, when the resource is explicitly assigned to the class member in the openFile()
function as parent::
and not as self::
:
<?php
class MyFileAbstract extends Threaded
{
protected static $m_Connection;
public static function init() {
static::openFile();
echo "<br>Member accessed from parent: ";
print_r(self::$m_Connection); # the resource is empty
}
}
class MyFile extends MyFileAbstract
{
public static function openFile() {
# the resource keeps now the value when using parent:: instead of self::
parent::$m_Connection = fopen("/etc/php.ini", "r");
echo "<br>Member accessed from child: ";
print_r(parent::$m_Connection)."<br>";
}
}
class MyThread extends Thread
{
public function run() {
MyFile::init();
}
}
$myThread = new MyThread();
$myThread->start();
echo "<br>Correct output:";
MyFile::init();
?>
The result is now correct:
Member accessed from child: Resource id #2
Member accessed from parent: Resource id #2
Correct output:
Member accessed from child: Resource id #3
Member accessed from parent: Resource id #3