mainLogger = new MainLogger(null, false, "Main", new \DateTimeZone('UTC')); $this->pool = new AsyncPool(2, 1024, new ThreadSafeClassLoader(), $this->mainLogger, new SleeperHandler()); } public function tearDown() : void{ $this->pool->shutdown(); } public function testTaskLeak() : void{ $start = microtime(true); $this->pool->submitTask(new LeakTestAsyncTask()); while(!LeakTestAsyncTask::$destroyed && microtime(true) < $start + 30){ usleep(50 * 1000); $this->pool->collectTasks(); } self::assertTrue(LeakTestAsyncTask::$destroyed, "Task was not destroyed after 30 seconds"); } public function testThreadSafeSetResult() : void{ $resolver = new PromiseResolver(); $resolver->getPromise()->onCompletion( function(ThreadSafeArray $result) : void{ self::assertCount(1, $result); self::assertSame(["foo"], (array) $result); }, function() : void{ self::fail("Promise failed"); } ); $this->pool->submitTask(new ThreadSafeResultAsyncTask($resolver)); while($this->pool->collectTasks()){ usleep(50 * 1000); } } /** * This test ensures that the fix for an exotic AsyncTask::__destruct() reentrancy bug has not regressed. * * Due to an unset() in the function body, other AsyncTask::__destruct() calls could be triggered during * an AsyncTask's destruction. If done in the wrong way, this could lead to a crash. * * @doesNotPerformAssertions This test is checking for a crash condition, not a specific output. */ public function testTaskDestructorReentrancy() : void{ $this->pool->submitTask(new class extends AsyncTask{ public function __construct(){ $this->storeLocal("task", new class extends AsyncTask{ public function __construct(){ $this->storeLocal("dummy", 1); } public function onRun() : void{ //dummy } }); } public function onRun() : void{ //dummy } }); while($this->pool->collectTasks()){ usleep(50 * 1000); } } public function testNullComplexDataFetch() : void{ $this->pool->submitTask(new class extends AsyncTask{ public function __construct(){ $this->storeLocal("null", null); } public function onRun() : void{ //dummy } public function onCompletion() : void{ AsyncPoolTest::assertNull($this->fetchLocal("null")); } }); while($this->pool->collectTasks()){ usleep(50 * 1000); } } }