8000 [Notifier] add RocketChat bridge · symfony/symfony@4869ef6 · GitHub
[go: up one dir, main page]

Skip to content

Commit 4869ef6

Browse files
Jeroenyfabpot
authored andcommitted
[Notifier] add RocketChat bridge
1 parent 4003700 commit 4869ef6

File tree

13 files changed

+313
-0
lines changed
  • Exception
  • 13 files changed

    +313
    -0
    lines changed

    src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php

    Lines changed: 2 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -92,6 +92,7 @@
    9292
    use Symfony\Component\Mime\MimeTypes;
    9393
    use Symfony\Component\Notifier\Bridge\Mattermost\MattermostTransportFactory;
    9494
    use Symfony\Component\Notifier\Bridge\Nexmo\NexmoTransportFactory;
    95+
    use Symfony\Component\Notifier\Bridge\RocketChat\RocketChatTransportFactory;
    9596
    use Symfony\Component\Notifier\Bridge\Slack\SlackTransportFactory;
    9697
    use Symfony\Component\Notifier\Bridge\Telegram\TelegramTransportFactory;
    9798
    use Symfony\Component\Notifier\Bridge\Twilio\TwilioTransportFactory;
    @@ -2000,6 +2001,7 @@ private function registerNotifierConfiguration(array $config, ContainerBuilder $
    20002001
    TelegramTransportFactory::class => 'notifier.transport_factory.telegram',
    20012002
    MattermostTransportFactory::class => 'notifier.transport_factory.mattermost',
    20022003
    NexmoTransportFactory::class => 'notifier.transport_factory.nexmo',
    2004+
    RocketChatTransportFactory::class => 'notifier.transport_factory.rocketchat',
    20032005
    TwilioTransportFactory::class => 'notifier.transport_factory.twilio',
    20042006
    ];
    20052007

    src/Symfony/Bundle/FrameworkBundle/Resources/config/notifier_transports.xml

    Lines changed: 4 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -26,6 +26,10 @@
    2626
    <tag name="texter.transport_factory" />
    2727
    </service>
    2828

    29+
    <service id="notifier.transport_factory.rocketchat" class="Symfony\Component\Notifier\Bridge\RocketChat\RocketChatTransportFactory" parent="notifier.transport_factory.abstract">
    30+
    <tag name="chatter.transport_factory" />
    31+
    </service>
    32+
    2933
    <service id="notifier.transport_factory.twilio" class="Symfony\Component\Notifier\Bridge\Twilio\TwilioTransportFactory" parent="notifier.transport_factory.abstract">
    3034
    <tag name="texter.transport_factory" />
    3135
    </service>
    Lines changed: 2 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,2 @@
    1+
    /Tests export-ignore
    2+
    /phpunit.xml.dist export-ignore
    Lines changed: 7 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,7 @@
    1+
    CHANGELOG
    2+
    =========
    3+
    4+
    5.1.0
    5+
    -----
    6+
    7+
    * Added the bridge
    Lines changed: 19 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,19 @@
    1+
    Copyright (c) 2019 Fabien Potencier
    2+
    3+
    Permission is hereby granted, free of charge, to any person obtaining a copy
    4+
    of this software and associated documentation files (the "Software"), to deal
    5+
    in the Software without restriction, including without limitation the rights
    6+
    to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
    7+
    copies of the Software, and to permit persons to whom the Software is furnished
    8+
    to do so, subject to the following conditions:
    9+
    10+
    The above copyright notice and this permission notice shall be included in all
    11+
    copies or substantial portions of the Software.
    12+
    13+
    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    14+
    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    15+
    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
    16+
    AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    17+
    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    18+
    OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
    19+
    THE SOFTWARE.
    Lines changed: 12 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,12 @@
    1+
    RocketChat Notifier
    2+
    ===================
    3+
    4+
    Provides RocketChat integration for Symfony Notifier.
    5+
    6+
    Resources
    7+
    ---------
    8+
    9+
    * [Contributing](https://symfony.com/doc/current/contributing/index.html)
    10+
    * [Report issues](https://github.com/symfony/symfony/issues) and
    11+
    [send Pull Requests](https://github.com/symfony/symfony/pulls)
    12+
    in the [main Symfony repository](https://github.com/symfony/symfony)
    Lines changed: 60 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,60 @@
    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\Bridge\RocketChat;
    13+
    14+
    use Symfony\Component\Notifier\Message\MessageOptionsInterface;
    15+
    16+
    /**
    17+
    * @author Jeroen Spee <https://github.com/Jeroeny>
    18+
    *
    19+
    * @experimental in 5.1
    20+
    *
    21+
    * @see https://rocket.chat/docs/administrator-guides/integrations/
    22+
    */
    23+
    final class RocketChatOptions implements MessageOptionsInterface
    24+
    {
    25+
    /** @var string|null prefix with '@' for personal messages */
    26+
    private $channel;
    27+
    28+
    /** @var mixed[] */
    29+
    private $attachments;
    30+
    31+
    /**
    32+
    * @param string[] $attachments
    33+
    */
    34+
    public function __construct(array $attachments = [])
    35+
    {
    36+
    $this->attachments = $attachments;
    37+
    }
    38+
    39+
    public function toArray(): array
    40+
    {
    41+
    return [
    42+
    'attachments' => [$this->attachments],
    43+
    ];
    44+
    }
    45+
    46+
    public function getRecipientId(): ?string
    47+
    {
    48+
    return $this->channel;
    49+
    }
    50+
    51+
    /**
    52+
    * @return $this
    53+
    */
    54+
    public function channel(string $channel): self
    55+
    {
    56+
    $this->channel = $channel;
    57+
    58+
    return $this;
    59+
    }
    60+
    }
    Lines changed: 90 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,90 @@
    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\Bridge\RocketChat;
    13+
    14+
    use Symfony\Component\Notifier\Exception\LogicException;
    15+
    use Symfony\Component\Notifier\Exception\TransportException;
    16+
    use Symfony\Component\Notifier\Message\ChatMessage;
    17+
    use Symfony\Component\Notifier\Message\MessageInterface;
    18+
    use Symfony\Component\Notifier\Transport\AbstractTransport;
    19+
    use Symfony\Contracts\EventDispatcher\EventDispatcherInterface;
    20+
    use Symfony\Contracts\HttpClient\HttpClientInterface;
    21+
    22+
    /**
    23+
    * @author Jeroen Spee <https://github.com/Jeroeny>
    24+
    *
    25+
    * @internal
    26+
    *
    27+
    * @experimental in 5.1
    28+
    */
    29+
    final class RocketChatTransport extends AbstractTransport
    30+
    {
    31+
    protected const HOST = 'rocketchat.com';
    32+
    33+
    private $accessToken;
    34+
    private $chatChannel;
    35+
    36+
    public function __construct(string $accessToken, string $chatChannel = null, HttpClientInterface $client = null, EventDispatcherInterface $dispatcher = null)
    37+
    {
    38+
    $this->accessToken = $accessToken;
    39+
    $this->chatChannel = $chatChannel;
    40+
    $this->client = $client;
    41+
    42+
    parent::__construct($client, $dispatcher);
    43+
    }
    44+
    45+
    public function __toString(): string
    46+
    {
    47+
    return sprintf('rocketchat://%s?channel=%s', $this->getEndpoint(), $this->chatChannel);
    48+
    }
    49+
    50+
    public function supports(MessageInterface $message): bool
    51+
    {
    52+
    return $message instanceof ChatMessage && (null === $message->getOptions() || $message->getOptions() instanceof RocketChatOptions);
    53+
    }
    54+
    55+
    /**
    56+
    * @see https://rocket.chat/docs/administrator-guides/integrations/
    57+
    */
    58+
    protected function doSend(MessageInterface $message): void
    59+
    {
    60+
    if (!$message instanceof ChatMessage) {
    61+
    throw new LogicException(sprintf('The "%s" transport only supports instances of "%s" (instance of "%s" given).', __CLASS__, ChatMessage::class, \get_class($message)));
    62+
    }
    63+
    if ($message->getOptions() && !$message->getOptions() instanceof RocketChatOptions) {
    64+
    throw new LogicException(sprintf('The "%s" transport only supports instances of "%s" for options.', __CLASS__, RocketChatOptions::class));
    65+
    }
    66+
    67+
    $options = ($opts = $message->getOptions()) ? $opts->toArray() : [];
    68+
    if (!isset($options['channel'])) {
    69+
    $options['channel'] = $message->getRecipientId() ?: $this->chatChannel;
    70+
    }
    71+
    $options['text'] = $message->getSubject();
    72+
    73+
    $response = $this->client->request(
    74+
    'POST',
    75+
    sprintf('https://%s/hooks/%s', $this->getEndpoint(), $this->accessToken),
    76+
    [
    77+
    'json' => array_filter($options),
    78+
    ]
    79+
    );
    80+
    81+
    if (200 !== $response->getStatusCode()) {
    82+
    throw new TransportException(sprintf('Unable to post the RocketChat message: %s.', $response->getContent(false)), $response);
    83+
    }
    84+
    85+
    $result = $response->toArray(false);
    86+
    if (!$result['success']) {
    87+
    throw new TransportException(sprintf('Unable to post the RocketChat message: %s.', $result['error']), $response);
    88+
    }
    89+
    }
    90+
    }
    Lines changed: 45 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,45 @@
    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\Bridge\RocketChat;
    13+
    14+
    use Symfony\Component\Notifier\Exception\UnsupportedSchemeException;
    15+
    use Symfony\Component\Notifier\Transport\AbstractTransportFactory;
    16+
    use Symfony\Component\Notifier\Transport\Dsn;
    17+
    use Symfony\Component\Notifier\Transport\TransportInterface;
    18+
    19+
    /**
    20+
    * @author Jeroen Spee <https://github.com/Jeroeny>
    21+
    *
    22+
    * @experimental in 5.1
    23+
    */
    24+
    final class RocketChatTransportFactory extends AbstractTransportFactory
    25+
    {
    26+
    public function create(Dsn $dsn): TransportInterface
    27+
    {
    28+
    $scheme = $dsn->getScheme();
    29+
    $accessToken = $this->getUser($dsn);
    30+
    $channel = $dsn->getOption('channel');
    31+
    $host = 'default' === $dsn->getHost() ? null : $dsn->getHost();
    32+
    $port = $dsn->getPort();
    33+
    34+
    if ('rocketchat' === $scheme) {
    35+
    return (new RocketChatTransport($accessToken, $channel, $this->client, $this->dispatcher))->setHost($host)->setPort($port);
    36+
    }
    37+
    38+
    throw new UnsupportedSchemeException($dsn, 'rocketchat', $this->getSupportedSchemes());
    39+
    }
    40+
    41+
    protected function getSupportedSchemes(): array
    42+
    {
    43+
    return ['rocketchat'];
    44+
    }
    45+
    }
    Lines changed: 35 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,35 @@
    1+
    {
    2+
    "name": "symfony/rocketchat-notifier",
    3+
    "type": "symfony-bridge",
    4+
    "description": "Symfony RocketChat Notifier Bridge",
    5+
    "keywords": ["rocketchat", "notifier"],
    6+
    "homepage": "https://symfony.com",
    7+
    "license": "MIT",
    8+
    "authors": [
    9+
    {
    10+
    "name": "Jeroen Spee",
    11+
    "homepage": "https://github.com/Jeroeny"
    12+
    },
    13+
    {
    14+
    "name": "Symfony Community",
    15+
    "homepage": "https://symfony.com/contributors"
    16+
    }
    17+
    ],
    18+
    "require": {
    19+
    "php": "^7.2.5",
    20+
    "symfony/http-client": "^4.3|^5.0",
    21+
    "symfony/notifier": "^5.0"
    22+
    },
    23+
    "autoload": {
    24+
    "psr-4": { "Symfony\\Component\\Notifier\\Bridge\\RocketChat\\": "" },
    25+
    "exclude-from-classmap": [
    26+
    "/Tests/"
    27+
    ]
    28+
    },
    29+
    "minimum-stability": "dev",
    30+
    "extra": {
    31+
    "branch-alias": {
    32+
    "dev-master": "5.1-dev"
    33+
    }
    34+
    }
    35+
    }

    0 commit comments

    Comments
     (0)
    0