Skip to content

Commit 9428e32

Browse files
authored
Merge pull request #51 from dotkernel/issue-50
Issue #50: Tests to improve code coverage
2 parents 9ce572b + 57ffd34 commit 9428e32

22 files changed

+1389
-4
lines changed

.github/workflows/codecov.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ jobs:
2727
uses: shivammathur/setup-php@v2
2828
with:
2929
php-version: "${{ matrix.php }}"
30+
extensions: swoole
3031
coverage: pcov
3132
ini-values: assert.exception=1, zend.assertions=1, error_reporting=-1, log_errors_max_len=0, display_errors=On
3233
tools: composer:v2, cs2pr

.laminas-ci/pre-run.sh

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
JOB=$3
2+
PHP_VERSION=$(echo "${JOB}" | jq -r '.php')
3+
4+
apt update
5+
apt install -y "php${PHP_VERSION}-swoole"

composer.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,8 @@
6969
},
7070
"autoload-dev": {
7171
"psr-4": {
72-
"QueueTest\\Swoole\\": "test/Swoole"
72+
"QueueTest\\App\\": "test/App/",
73+
"QueueTest\\Swoole\\": "test/Swoole/"
7374
}
7475
},
7576
"scripts": {

src/Swoole/Command/GetFailedMessagesCommand.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,8 @@
2828
)]
2929
class GetFailedMessagesCommand extends Command
3030
{
31-
protected static string $defaultName = 'failed';
31+
/** @var string $defaultName */
32+
protected static $defaultName = 'failed';
3233

3334
#[Inject()]
3435
public function __construct()

src/Swoole/Command/GetProcessedMessagesCommand.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,8 @@
2828
)]
2929
class GetProcessedMessagesCommand extends Command
3030
{
31-
protected static string $defaultName = 'processed';
31+
/** @var string $defaultName */
32+
protected static $defaultName = 'processed';
3233

3334
#[Inject()]
3435
public function __construct()

src/Swoole/Command/GetQueuedMessagesCommand.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,8 @@
2525
)]
2626
class GetQueuedMessagesCommand extends Command
2727
{
28-
protected static string $defaultName = 'inventory';
28+
/** @var string $defaultName */
29+
protected static $defaultName = 'inventory';
2930

3031
private Redis $redis;
3132

test/App/AppConfigProviderTest.php

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace QueueTest\App;
6+
7+
use PHPUnit\Framework\TestCase;
8+
use Queue\App\ConfigProvider;
9+
10+
class AppConfigProviderTest extends TestCase
11+
{
12+
private array $config;
13+
14+
public function setUp(): void
15+
{
16+
$this->config = (new ConfigProvider())();
17+
}
18+
19+
public function testHasDependencies(): void
20+
{
21+
$this->assertArrayHasKey('dependencies', $this->config);
22+
}
23+
}
Lines changed: 153 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,153 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace QueueTest\App\Message;
6+
7+
use Dot\Log\Logger;
8+
use PHPUnit\Framework\MockObject\Exception;
9+
use PHPUnit\Framework\MockObject\MockObject;
10+
use PHPUnit\Framework\TestCase;
11+
use Psr\Container\ContainerExceptionInterface;
12+
use Queue\App\Message\Message;
13+
use Queue\App\Message\MessageHandler;
14+
use Symfony\Component\Messenger\Envelope;
15+
use Symfony\Component\Messenger\Exception\ExceptionInterface;
16+
use Symfony\Component\Messenger\MessageBusInterface;
17+
use Symfony\Component\Messenger\Stamp\DelayStamp;
18+
19+
class MessageHandlerTest extends TestCase
20+
{
21+
private MessageBusInterface|MockObject $bus;
22+
private Logger $logger;
23+
private array $config;
24+
private MessageHandler $handler;
25+
26+
/**
27+
* @throws Exception
28+
* @throws ContainerExceptionInterface
29+
*/
30+
protected function setUp(): void
31+
{
32+
$this->bus = $this->createMock(MessageBusInterface::class);
33+
$this->logger = new Logger([
34+
'writers' => [
35+
'FileWriter' => [
36+
'name' => 'null',
37+
'level' => Logger::ALERT,
38+
],
39+
],
40+
]);
41+
$this->config = [
42+
'fail-safe' => [
43+
'first_retry' => 1000,
44+
'second_retry' => 2000,
45+
'third_retry' => 3000,
46+
],
47+
'notification' => [
48+
'server' => [
49+
'protocol' => 'tcp',
50+
'host' => 'localhost',
51+
'port' => '8556',
52+
'eof' => "\n",
53+
],
54+
],
55+
'application' => [
56+
'name' => 'dotkernel',
57+
],
58+
];
59+
60+
$this->handler = new MessageHandler($this->bus, $this->logger, $this->config);
61+
}
62+
63+
/**
64+
* @throws Exception
65+
*/
66+
public function testInvokeSuccessfulProcessing(): void
67+
{
68+
$payload = ['foo' => 'control'];
69+
$message = $this->createMock(Message::class);
70+
$message->method('getPayload')->willReturn($payload);
71+
72+
$this->handler->__invoke($message);
73+
74+
$this->expectNotToPerformAssertions();
75+
}
76+
77+
/**
78+
* @throws Exception
79+
*/
80+
public function testInvokeFailureTriggersFirstRetry(): void
81+
{
82+
$payload = ['foo' => 'fail'];
83+
$message = $this->createMock(Message::class);
84+
$message->method('getPayload')->willReturn($payload);
85+
86+
$this->bus->expects($this->once())
87+
->method('dispatch')
88+
->with(
89+
$this->callback(function ($msg) {
90+
return $msg instanceof Message
91+
&& $msg->getPayload()['foo'] === 'fail'
92+
&& $msg->getPayload()['retry'] === 1;
93+
}),
94+
$this->callback(function ($stamps) {
95+
return isset($stamps[0]) && $stamps[0] instanceof DelayStamp
96+
&& $stamps[0]->getDelay() === 1000;
97+
})
98+
)
99+
->willReturn(new Envelope($message));
100+
101+
$this->handler->__invoke($message);
102+
}
103+
104+
/**
105+
* @throws ExceptionInterface
106+
*/
107+
public function testRetrySecondTime(): void
108+
{
109+
$payload = ['foo' => 'retry_test', 'retry' => 1];
110+
111+
$this->bus->expects($this->once())
112+
->method('dispatch')
113+
->with(
114+
$this->callback(function ($msg) {
115+
return $msg instanceof Message
116+
&& $msg->getPayload()['retry'] === 2
117+
&& $msg->getPayload()['foo'] === 'retry_test';
118+
}),
119+
$this->callback(function ($stamps) {
120+
return isset($stamps[0]) && $stamps[0] instanceof DelayStamp
121+
&& $stamps[0]->getDelay() === 2000;
122+
})
123+
)
124+
->willReturn(new Envelope(new Message($payload)));
125+
126+
$this->handler->retry($payload);
127+
}
128+
129+
/**
130+
* @throws ExceptionInterface
131+
*/
132+
public function testRetryThirdTime(): void
133+
{
134+
$payload = ['foo' => 'retry_test', 'retry' => 2];
135+
136+
$this->bus->expects($this->once())
137+
->method('dispatch')
138+
->with(
139+
$this->callback(function ($msg) {
140+
return $msg instanceof Message
141+
&& $msg->getPayload()['retry'] === 3
142+
&& $msg->getPayload()['foo'] === 'retry_test';
143+
}),
144+
$this->callback(function ($stamps) {
145+
return isset($stamps[0]) && $stamps[0] instanceof DelayStamp
146+
&& $stamps[0]->getDelay() === 3000;
147+
})
148+
)
149+
->willReturn(new Envelope(new Message($payload)));
150+
151+
$this->handler->retry($payload);
152+
}
153+
}

test/App/Message/MessageTest.php

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace QueueTest\App\Message;
6+
7+
use PHPUnit\Framework\TestCase;
8+
use Queue\App\Message\Message;
9+
10+
class MessageTest extends TestCase
11+
{
12+
public function testMessageAccessors(): void
13+
{
14+
$admin = new Message(["payload" => "test message payload"]);
15+
$this->assertSame(["payload" => "test message payload"], $admin->getPayload());
16+
}
17+
}
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace QueueTest\Swoole\Command\Factory;
6+
7+
use PHPUnit\Framework\MockObject\Exception;
8+
use PHPUnit\Framework\TestCase;
9+
use Psr\Container\ContainerInterface;
10+
use Queue\Swoole\Command\Factory\StartCommandFactory;
11+
use Queue\Swoole\Command\StartCommand;
12+
13+
class StartCommandFactoryTest extends TestCase
14+
{
15+
/**
16+
* @throws Exception
17+
*/
18+
public function testFactoryReturnsStartCommandInstance(): void
19+
{
20+
$container = $this->createMock(ContainerInterface::class);
21+
22+
$factory = new StartCommandFactory();
23+
$command = $factory($container);
24+
25+
$this->assertContainsOnlyInstancesOf(StartCommand::class, [$command]);
26+
}
27+
}

0 commit comments

Comments
 (0)