Как протестировать семафоры с помощью PHPUnit

#php #symfony #phpunit #pthreads

#php #symfony #phpunit #pthreads

Вопрос:

Я использую пакет Symfony Lock, чтобы проверить, может ли быть выполнен метод класса

 if ($this->lock->acquire()) {
    $this->execute();
    $this->lock->release();
}
  

Важно: я не использую фреймворк Symfony, только компонент Lock

Я хочу сделать тест, который утверждает, что выполнение заблокировано при запуске в нескольких потоках, но я не нашел никакой документации о том, как этого добиться.

Хорошая ли идея использовать pthreads? Если нет, то какой лучший способ выполнить этот тест?

Большое вам спасибо.

Ответ №1:

Ссылаясь на документацию по компоненту блокировки:https://symfony.com/doc/current/components/lock.html#usage

Информация о CommandTester:https://symfony.com/doc/current/console.html#testing-commands

Решение для тестирования PHPUnit :

 use SymfonyComponentLockFactory;
use SymfonyComponentLockStoreSemaphoreStore;

public function testLockIsSet()
{     
    // Create a new Semaphore lock with the same ID as the one that would be
    // created if you were running the command / class / process etc.
    $store = new SemaphoreStore();
    $factory = new Factory($store);
    $lock = $factory->createLock('lock-name-used-eg-generate-pdf');

    if ($lock->acquire()) {
        // In my use case I was running multiple commands to see if the lock
        // was working properly
        $commandTester = new CommandTester($this->command);

        // Try and run the command. The lock should already be set.
        $commandTester->execute(
            [
                'command'  => $this->command->getName()
            ]
        );

        // You could also use expectException() here for LogicException    
        $this->assertContains(
            'The command is already running in locked mode.',
            $commandTester->getDisplay()
        );

        $lock->release();
    }
}
  

Комментарии:

1. Для информации, я пробовал что-то подобное, но, похоже, блокировка не может быть снята во время модульного тестирования, мне пришлось удалить *.lock файлы в /tmp каталоге, чтобы заставить его работать.