8000 [Messenger] Add auto stamp middleware · symfony/symfony@d4e67bc · GitHub
[go: up one dir, main page]

Skip to content

Commit d4e67bc

Browse files
committed
[Messenger] Add auto stamp middleware
1 parent 65fa483 commit d4e67bc

File tree

6 files changed

+138
-0
lines changed

6 files changed

+138
-0
lines changed

src/Symfony/Bundle/FrameworkBundle/Resources/config/messenger.php

+3
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
use Symfony\Component\Messenger\EventListener\StopWorkerOnSignalsListener;
2727
use Symfony\Component\Messenger\Handler\RedispatchMessageHandler;
2828
use Symfony\Component\Messenger\Middleware\AddBusNameStampMiddleware;
29+
use Symfony\Component\Messenger\Middleware\AutoStampMiddleware;
2930
use Symfony\Component\Messenger\Middleware\DispatchAfterCurrentBusMiddleware;
3031
use Symfony\Component\Messenger\Middleware\FailedMessageProcessingMiddleware;
3132
use Symfony\Component\Messenger\Middleware\HandleMessageMiddleware;
@@ -112,6 +113,8 @@
112113
service('router'),
113114
])
114115

116+
->set('messenger.middleware.auto_stamp_middleware', AutoStampMiddleware::class)
117+
115118
// Discovery
116119
->set('messenger.receiver_locator', ServiceLocator::class)
117120
->args([
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Component\Messenger\Attribute;
13+
14+
use Symfony\Component\Messenger\Stamp\StampInterface;
15+
16+
/**
17+
* Configure message stamps.
18+
*
19+
* @author Kerian Montes <kerianmontes@gmail.com>
20+
*/
21+
#[\Attribute(\Attribute::TARGET_CLASS | \Attribute::IS_REPEATABLE)]
22+
class AutoStamp
23+
{
24+
/** @var StampInterface[] $stamps */
25+
public readonly array $stamps;
26+
27+
/**
28+
* @param StampInterface|array<StampInterface> $stamps
29+
*/
30+
public function __construct(StampInterface|array $stamps)
31+
{
32+
$this->stamps = $stamps instanceof StampInterface ? [$stamps] : $stamps;
33+
}
34+
}

src/Symfony/Component/Messenger/CHANGELOG.md

+1
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ CHANGELOG
1616
SIGTERM by default
1717
* Add `RedispatchMessage` and `RedispatchMessageHandler`
1818
* Add optional parameter `$isSameDatabase` to `DoctrineTransport::configureSchema()`
19+
* Add `AutoStamp` attribute to configure stamps on message, added to envelope in `AutoStampMiddleware`
1920

2021
6.2
2122
---
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Component\Messenger\Middleware;
13+
14+
use Symfony\Component\Messenger\Attribute\AutoStamp;
15+
use Symfony\Component\Messenger\Envelope;
16+
17+
/**
18+
* Middleware that add stamps configured on message with dedicated attribute.
19+
*
20+
* @author Kerian Montes <kerianmontes@gmail.com>
21+
*/
22+
class AutoStampMiddleware implements MiddlewareInterface
23+
{
24+
public function handle(Envelope $envelope, StackInterface $stack): Envelope
25+
{
26+
$class = new \ReflectionClass($envelope->getMessage());
27+
do {
28+
foreach ($class->getAttributes(AutoStamp::class, \ReflectionAttribute::IS_INSTANCEOF) as $attribute) {
29+
$envelope = $envelope->with(...$attribute->newInstance()->stamps);
30+
}
31+
} while ($class = $class->getParentClass());
32+
33+
return $stack->next()->handle($envelope, $stack);
34+
}
35+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
<?php
2+
3+
namespace Symfony\Component\Messenger\Tests\Fixtures;
4+
5+
use Symfony\Component\Messenger\Attribute\AutoStamp;
6+
use Symfony\Component\Messenger\Stamp\DelayStamp;
7+
use Symfony\Component\Messenger\Stamp\ValidationStamp;
8+
9+
#[AutoStamp(new DelayStamp(123))]
10+
#[AutoStamp([new ValidationStamp(['Default', 'Extra'])])]
11+
class AutoStampedMessage
12+
{
13+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Component\Messenger\Tests\Middleware;
13+
14+
use Symfony\Component\Messenger\Envelope;
15+
use Symfony\Component\Messenger\Exception\ValidationFailedException;
16+
use Symfony\Component\Messenger\Middleware\AutoStampMiddleware;
17+
use Symfony\Component\Messenger\Stamp\DelayStamp;
18+
use Symfony\Component\Messenger\Stamp\ValidationStamp;
19+
use Symfony\Component\Messenger\Test\Middleware\MiddlewareTestCase;
20+
use Symfony\Component\Messenger\Tests\Fixtures\AutoStampedMessage;
21+
use Symfony\Component\Messenger\Tests\Fixtures\DummyMessage;
22+
use Symfony\Component\Validator\ConstraintViolationListInterface;
23+
use Symfony\Component\Validator\Validator\ValidatorInterface;
24+
25+
class AutoStampMiddlewareTest extends MiddlewareTestCase
26+
{
27+
public function testHandleWithoutAutoStampAndNextMiddleware()
28+
{
29+
$message = new DummyMessage('Hey');
30+
$envelope = new Envelope($message);
31+
32+
(new AutoStampMiddleware())->handle($envelope, $this->getStackMock());
33+
$this->assertCount(0, $envelope->all());
34+
}
35+
36+
public function testHandleWithAutoStampAndNextMiddleware()
37+
{
38+
$message = new AutoStampedMessage();
39+
$envelope = new Envelope($message);
40+
41+
$handledEnvelope = (new AutoStampMiddleware())->handle($envelope, $this->getStackMock());
42+
$this->assertCount(2, $handledEnvelope->all());
43+
44+
$delayStamp = $handledEnvelope->last(DelayStamp::class);
45+
$this->assertInstanceOf(DelayStamp::class, $delayStamp);
46+
$this->assertSame(123, $delayStamp->getDelay());
47+
48+
$validationStamp = $handledEnvelope->last(ValidationStamp::class);
49+
$this->assertInstanceOf(ValidationStamp::class, $validationStamp);
50+
$this->assertSame(['Default', 'Extra'], $validationStamp->getGroups());
51+
}
52+
}

0 commit comments

Comments
 (0)
0