Skip to content

Commit

Permalink
Add test for worker (#123)
Browse files Browse the repository at this point in the history
Add test for worker
  • Loading branch information
romkatsu authored Jun 17, 2022
2 parents 6fa7bcd + b9bf62c commit f10b2f3
Show file tree
Hide file tree
Showing 2 changed files with 212 additions and 20 deletions.
38 changes: 38 additions & 0 deletions tests/App/FakeHandler.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
<?php

declare(strict_types=1);

namespace Yiisoft\Yii\Queue\Tests\App;

use Yiisoft\Yii\Queue\Message\MessageInterface;
use RuntimeException;

final class FakeHandler
{
public static array $processedMessages = [];

public function __construct()
{
self::$processedMessages = [];
}

public function __invoke(MessageInterface $message)
{
self::$processedMessages[] = $message;
}

public function execute(MessageInterface $message): void
{
self::$processedMessages[] = $message;
}

public static function staticExecute(MessageInterface $message): void
{
self::$processedMessages[] = $message;
}

public function executeWithException(MessageInterface $message): void
{
throw new RuntimeException('Test exception');
}
}
194 changes: 174 additions & 20 deletions tests/Unit/WorkerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,39 +4,193 @@

namespace Yiisoft\Yii\Queue\Tests\Unit;

use RuntimeException;
use Psr\Container\ContainerInterface;
use Psr\Log\LoggerInterface;
use Psr\Log\Test\TestLogger;
use Yiisoft\Injector\Injector;
use Yiisoft\Test\Support\Container\SimpleContainer;
use Yiisoft\Yii\Queue\Exception\JobFailureException;
use Yiisoft\Yii\Queue\Message\Message;
use Yiisoft\Yii\Queue\Message\MessageInterface;
use Yiisoft\Yii\Queue\QueueInterface;
use Yiisoft\Yii\Queue\Tests\App\FakeHandler;
use Yiisoft\Yii\Queue\Tests\TestCase;
use Yiisoft\Yii\Queue\Worker\Worker;

final class WorkerTest extends TestCase
{
/**
* Check normal job execution
*/
public function testJobExecuted(): void
public function testJobExecutedWithCallableHandler(): void
{
$this->executionTimes = 0;
$message = new Message('simple', '', []);
$handleMessage = null;
$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$container = new SimpleContainer();
$handlers = [
'simple' => function (MessageInterface $message) use (&$handleMessage) {
$handleMessage = $message;
},
];

$queue = $this->createMock(QueueInterface::class);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

$worker->process($message, $queue);
$this->assertSame($message, $handleMessage);

$this->assertTrue(
$logger->hasInfoThatContains('Processing message #{message}.')
);
}

public function testJobExecutedWithDefinitionHandler(): void
{
$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$handler = new FakeHandler();
$container = new SimpleContainer([FakeHandler::class => $handler]);
$handlers = ['simple' => FakeHandler::class];

$queue = $this->createMock(QueueInterface::class);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

$worker->process($message, $queue);
$this->assertSame([$message], $handler::$processedMessages);
}

public function testJobExecutedWithDefinitionClassHandler(): void
{
$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$handler = new FakeHandler();
$container = new SimpleContainer([FakeHandler::class => $handler]);
$handlers = ['simple' => [FakeHandler::class, 'execute']];

$queue = $this->createMock(QueueInterface::class);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

$worker->process($message, $queue);
$this->assertSame([$message], $handler::$processedMessages);
}

public function testJobFailWithDefinitionNotFoundClassButExistInContainerHandler(): void
{
$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$handler = new FakeHandler();
$container = new SimpleContainer(['not-found-class-name' => $handler]);
$handlers = ['simple' => ['not-found-class-name', 'execute']];

$queue = $this->createMock(QueueInterface::class);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

$worker->process($message, $queue);
$this->assertSame([$message], $handler::$processedMessages);
}

public function testJobExecutedWithStaticDefinitionHandler(): void
{
$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$handler = new FakeHandler();
$container = new SimpleContainer([FakeHandler::class => $handler]);
$handlers = ['simple' => [FakeHandler::class, 'staticExecute']];

$queue = $this->createMock(QueueInterface::class);
$this
->getWorker()
->process($message, $queue);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

self::assertEquals(1, $this->executionTimes);
$worker->process($message, $queue);
$this->assertSame([$message], $handler::$processedMessages);
}

/**
* Check job throws exception
*/
public function testThrowException(): void
public function testJobFailWithDefinitionUndefinedMethodHandler(): void
{
$this->expectException(RuntimeException::class);
$this->expectExceptionMessage("Queue handler with name simple doesn't exist");

$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$handler = new FakeHandler();
$container = new SimpleContainer([FakeHandler::class => $handler]);
$handlers = ['simple' => [FakeHandler::class, 'undefinedMethod']];

$message = new Message('exceptional', '', []);
$queue = $this->createMock(QueueInterface::class);
$this
->getWorker()
->process($message, $queue);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

$worker->process($message, $queue);
}

public function testJobFailWithDefinitionUndefinedClassHandler(): void
{
$this->expectExceptionMessage("Queue handler with name simple doesn't exist");

$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$handler = new FakeHandler();
$container = new SimpleContainer([FakeHandler::class => $handler]);
$handlers = ['simple' => ['UndefinedClass', 'handle']];

$queue = $this->createMock(QueueInterface::class);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

try {
$worker->process($message, $queue);
} finally {
$this->assertTrue(
$logger->hasErrorThatContains("UndefinedClass doesn't exist.")
);
}
}

public function testJobFailWithDefinitionClassNotFoundInContainerHandler(): void
{
$this->expectExceptionMessage("Queue handler with name simple doesn't exist");
$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$container = new SimpleContainer();
$handlers = ['simple' => [FakeHandler::class, 'execute']];

$queue = $this->createMock(QueueInterface::class);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

$worker->process($message, $queue);
}

public function testJobFailWithDefinitionHandlerException(): void
{
$this->expectException(JobFailureException::class);
$this->expectExceptionMessage(
"Processing of message #null is stopped because of an exception:\nTest exception."
);

$message = new Message('simple', ['test-data']);
$logger = new TestLogger();
$handler = new FakeHandler();
$container = new SimpleContainer([FakeHandler::class => $handler]);
$handlers = ['simple' => [FakeHandler::class, 'executeWithException']];

$queue = $this->createMock(QueueInterface::class);
$worker = $this->createWorkerByParams($handlers, $logger, $container);

try {
$worker->process($message, $queue);
} finally {
$this->assertTrue(
$logger->hasErrorThatContains(
"Processing of message #null is stopped because of an exception:\nTest exception."
)
);
}
}

private function createWorkerByParams(
array $handlers,
LoggerInterface $logger,
ContainerInterface $container
): Worker {
return new Worker(
$handlers,
$logger,
new Injector($container),
$container
);
}
}

0 comments on commit f10b2f3

Please sign in to comment.