Skip to content

Commit 356e312

Browse files
committed
add NotifierAssertionTrait
1 parent 25c2bb1 commit 356e312

18 files changed

+630
-0
lines changed

src/Symfony/Bundle/FrameworkBundle/CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ CHANGELOG
44
6.2
55
---
66

7+
* Add `NotificationAssertionsTrait`
78
* Add option `framework.catch_all_throwables` to allow `Symfony\Component\HttpKernel\HttpKernel` to catch all kinds of `Throwable`
89
* Make `AbstractController::render()` able to deal with forms and deprecate `renderForm()`
910
* Deprecate the `Symfony\Component\Serializer\Normalizer\ObjectNormalizer` and

src/Symfony/Bundle/FrameworkBundle/Test/KernelTestCase.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
abstract class KernelTestCase extends TestCase
2727
{
2828
use MailerAssertionsTrait;
29+
use NotificationAssertionsTrait;
2930

3031
protected static $class;
3132

Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
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\Bundle\FrameworkBundle\Test;
13+
14+
use PHPUnit\Framework\Constraint\LogicalNot;
15+
use Symfony\Component\Notifier\Event\MessageEvent;
16+
use Symfony\Component\Notifier\Event\NotificationEvents;
17+
use Symfony\Component\Notifier\Message\MessageInterface;
18+
use Symfony\Component\Notifier\Test\Constraint as NotifierConstraint;
19+
20+
/*
21+
* @author Smaïne Milianni <smaine.milianni@gmail.com>
22+
*/
23+
trait NotificationAssertionsTrait
24+
{
25+
public static function assertNotificationCount(int $count, string $transport = null, string $message = ''): void
26+
{
27+
self::assertThat(self::getNotificationEvents(), new NotifierConstraint\NotificationCount($count, $transport), $message);
28+
}
29+
30+
public static function assertQueuedNotificationCount(int $count, string $transport = null, string $message = ''): void
31+
{
32+
self::assertThat(self::getMessageMailerEvents(), new NotifierConstraint\NotificationCount($count, $transport, true), $message);
33+
}
34+
35+
public static function assertNotificationIsQueued(MessageEvent $event, string $message = ''): void
36+
{
37+
self::assertThat($event, new NotifierConstraint\NotificationIsQueued(), $message);
38+
}
39+
40+
public static function assertNotificationIsNotQueued(MessageEvent $event, string $message = ''): void
41+
{
42+
self::assertThat($event, new LogicalNot(new NotifierConstraint\NotificationIsQueued()), $message);
43+
}
44+
45+
public static function assertNotificationSubjectContains(MessageInterface $messageObject, string $text, string $message = ''): void
46+
{
47+
self::assertThat($messageObject, new NotifierConstraint\NotificationSubjectContains($text), $message);
48+
}
49+
50+
public static function assertNotificationSubjectNotContains(MessageInterface $messageObject, string $text, string $message = ''): void
51+
{
52+
self::assertThat($messageObject, new LogicalNot(new NotifierConstraint\NotificationSubjectContains($text)), $message);
53+
}
54+
55+
public static function assertNotificationContentContains(MessageInterface $messageObject, string $text, string $message = ''): void
56+
{
57+
self::assertThat($messageObject, new NotifierConstraint\NotificationContentContains($text), $message);
58+
}
59+
60+
public static function assertNotificationContentNotContains(MessageInterface $messageObject, string $text, string $message = ''): void
61+
{
62+
self::assertThat($messageObject, new LogicalNot(new NotifierConstraint\NotificationContentContains($text)), $message);
63+
}
64+
65+
public static function assertNotificationTransportIsEqual(MessageInterface $messageObject, string $text, string $message = ''): void
66+
{
67+
self::assertThat($messageObject, new NotifierConstraint\NotificationTransportIsEqual($text), $message);
68+
}
69+
70+
public static function assertNotificationTransportIsNotEqual(MessageInterface $messageObject, string $text, string $message = ''): void
71+
{
72+
self::assertThat($messageObject, new LogicalNot(new NotifierConstraint\NotificationTransportIsEqual($text)), $message);
73+
}
74+
75+
public static function assertNotificationImportanceIsEqual(MessageInterface $messageObject, string $text, string $message = ''): void
76+
{
77+
self::assertThat($messageObject, new NotifierConstraint\NotificationImportanceIsEqual($text), $message);
78+
}
79+
80+
public static function assertNotificationImportanceIsNotEqual(MessageInterface $messageObject, string $text, string $message = ''): void
81+
{
82+
self::assertThat($messageObject, new LogicalNot(new NotifierConstraint\NotificationImportanceIsEqual($text)), $message);
83+
}
84+
85+
/**
86+
* @return MessageEvent[]
87+
*/
88+
public static function getNotifierEvents(string $transport = null): array
89+
{
90+
return self::getNotificationEvents()->getEvents($transport);
91+
}
92+
93+
public static function getNotifierEvent(int $index = 0, string $transport = null): ?MessageEvent
94+
{
95+
return self::getNotifierEvents($transport)[$index] ?? null;
96+
}
97+
98+
/**
99+
* @return MessageInterface[]
100+
*/
101+
public static function getNotifierMessages(string $transport = null): array
102+
{
103+
return self::getNotificationEvents()->getMessages($transport);
104+
}
105+
106+
public static function getNotifierMessage(int $index = 0, string $transport = null): ?MessageInterface
107+
{
108+
return self::getNotifierMessages($transport)[$index] ?? null;
109+
}
110+
111+
public static function getNotificationEvents(): NotificationEvents
112+
{
113+
$container = static::getContainer();
114+
if ($container->has('notifier.logger_notification_listener')) {
115+
return $container->get('notifier.logger_notification_listener')->getEvents();
116+
}
117+
118+
static::fail('A client must have Notifier enabled to make notifications assertions. Did you forget to require symfony/notifier?');
119+
}
120+
}
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\Bundle\FrameworkBundle\Tests\Functional\Bundle\TestBundle\Controller;
13+
14+
use Symfony\Component\HttpFoundation\Response;
15+
use Symfony\Component\Notifier\Notification\Notification;
16+
use Symfony\Component\Notifier\NotifierInterface;
17+
18+
final class NotificationController
19+
{
20+
public function indexAction(NotifierInterface $notifier)
21+
{
22+
$firstNotification = new Notification('Hello World!', ['chat/slack']);
23+
$firstNotification->content("Symfony is awesome!");
24+
25+
$notifier->send($firstNotification);
26+
27+
$secondNotification = (new Notification('New urgent notification'))
28+
->importance(Notification::IMPORTANCE_URGENT)
29+
;
30+
$notifier->send($secondNotification);
31+
32+
return new Response();
33+
}
34+
}

src/Symfony/Bundle/FrameworkBundle/Tests/Functional/Bundle/TestBundle/Resources/config/routing.yml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,3 +64,7 @@ send_email:
6464
uid:
6565
resource: "../../Controller/UidController.php"
6666
type: "annotation"
67+
68+
send_notification:
69+
path: /send_notification
70+
defaults: { _controller: Symfony\Bundle\FrameworkBundle\Tests\Functional\Bundle\TestBundle\Controller\NotificationController::indexAction }
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
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\Bundle\FrameworkBundle\Tests\Functional;
13+
14+
use Symfony\Component\Notifier\Notification\Notification;
15+
16+
final class NotificationTest extends AbstractWebTestCase
17+
{
18+
public function testNotifierAssertion()
19+
{
20+
$client = $this->createClient(['test_case' => 'Notifier', 'root_config' => 'config.yml', 'debug' => true]);
21+
$client->request('GET', '/send_notification');
22+
23+
$this->assertNotificationCount(2);
24+
$first = 0;
25+
$second = 1;
26+
$this->assertNotificationIsNotQueued($this->getNotifierEvent($first));
27+
$this->assertNotificationIsNotQueued($this->getNotifierEvent($second));
28+
29+
$notification = $this->getNotifierMessage($first);
30+
$this->assertNotificationSubjectContains($notification, 'Hello World!');
31+
$this->assertNotificationSubjectNotContains($notification, 'New urgent notification');
32+
$this->assertNotificationTransportIsEqual($notification,'slack');
33+
$this->assertNotificationTransportIsNotEqual($notification,'mercure');
34+
$this->assertNotificationContentContains($notification,'Symfony is awesome!');
35+
$this->assertNotificationContentNotContains($notification,'mercure');
36+
$this->assertNotificationImportanceIsEqual($notification,Notification::IMPORTANCE_HIGH);
37+
$this->assertNotificationImportanceIsNotEqual($notification,Notification::IMPORTANCE_URGENT);
38+
39+
$notification = $this->getNotifierMessage($second);
40+
$this->assertNotificationSubjectContains($notification, 'New urgent notification');
41+
$this->assertNotificationSubjectNotContains($notification, 'Hello World!');
42+
$this->assertNotificationTransportIsEqual($notification,'mercure');
43+
$this->assertNotificationTransportIsNotEqual($notification,'slack');
44+
$this->assertNotificationContentNotContains($notification,'mercure');
45+
$this->assertNotificationImportanceIsEqual($notification,Notification::IMPORTANCE_URGENT);
46+
}
47+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
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+
use Symfony\Bundle\FrameworkBundle\FrameworkBundle;
13+
use Symfony\Bundle\FrameworkBundle\Tests\Functional\Bundle\TestBundle\TestBundle;
14+
use Symfony\Bundle\MercureBundle\MercureBundle;
15+
16+
return [
17+
new FrameworkBundle(),
18+
new TestBundle(),
19+
new MercureBundle(),
20+
];
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
imports:
2+
- { resource: ../config/default.yml }
3+
- { resource: services.yml }
4+
5+
framework:
6+
mailer:
7+
dsn: 'null://null'
8+
notifier:
9+
chatter_transports:
10+
slack: 'null://null'
11+
mercure: 'null://null'
12+
channel_policy:
13+
urgent: ['chat/mercure']
14+
admin_recipients:
15+
- { email: admin@example.com }
16+
profiler: ~
17+
18+
mercure:
19+
hubs:
20+
default:
21+
url: 'null://null'
22+
jwt:
23+
secret: '!ChangeMe!'
24+
publish: [ 'foo', 'https://example.com/foo' ]
25+
subscribe: [ 'bar', 'https://example.com/bar' ]
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
_notifiertest_bundle:
2+
resource: '@TestBundle/Resources/config/routing.yml'
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
services:
2+
_defaults:
3+
public: true
4+
5+
Symfony\Bundle\FrameworkBundle\Tests\Functional\Bundle\TestBundle\Controller\NotificationController:
6+
tags: ['controller.service_arguments']
7+

src/Symfony/Component/Notifier/CHANGELOG.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,11 @@
11
CHANGELOG
22
=========
33

4+
6.2
5+
---
6+
7+
* Add PHPUnit constraints
8+
49
6.1
510
---
611

src/Symfony/Component/Notifier/Message/NullMessage.php

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@
1111

1212
namespace Symfony\Component\Notifier\Message;
1313

14+
use Symfony\Component\Notifier\Notification\Notification;
15+
1416
/**
1517
* @author Jan Schädlich <jan.schaedlich@sensiolabs.de>
1618
*/
@@ -42,4 +44,13 @@ public function getTransport(): ?string
4244
{
4345
return $this->decoratedMessage->getTransport() ?? 'null';
4446
}
47+
48+
public function getNotification(): ?Notification
49+
{
50+
if (true === method_exists($this->decoratedMessage, 'getNotification')) {
51+
return $this->decoratedMessage->getNotification();
52+
}
53+
54+
return null;
55+
}
4556
}
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
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\Notifier\Test\Constraint;
13+
14+
use PHPUnit\Framework\Constraint\Constraint;
15+
use Symfony\Component\Notifier\Message\MessageInterface;
16+
use Symfony\Component\Notifier\Notification\Notification;
17+
18+
/**
19+
* @author Smaïne Milianni <smaine.milianni@gmail.com>
20+
*/
21+
final class NotificationContentContains extends Constraint
22+
{
23+
private $expectedText;
24+
25+
public function __construct(string $expectedText)
26+
{
27+
$this->expectedText = $expectedText;
28+
}
29+
30+
/**
31+
* {@inheritdoc}
32+
*/
33+
public function toString(): string
34+
{
35+
return sprintf('contains "%s"', $this->expectedText);
36+
}
37+
38+
/**
39+
* {@inheritdoc}
40+
*
41+
* @param MessageInterface $message
42+
*/
43+
protected function matches($message): bool
44+
{
45+
if (true === method_exists($message, 'getNotification')) {
46+
/** @var Notification $notification */
47+
$notification = $message->getNotification();
48+
49+
return false !== mb_strpos($notification->getContent(), $this->expectedText);
50+
}
51+
52+
return false;
53+
}
54+
55+
/**
56+
* {@inheritdoc}
57+
*
58+
* @param MessageInterface $message
59+
*/
60+
protected function failureDescription($message): string
61+
{
62+
return 'the Notification content '.$this->toString();
63+
}
64+
}

0 commit comments

Comments
 (0)