Transport.php 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142
  1. <?php
  2. /*
  3. * This file is part of the Symfony package.
  4. *
  5. * (c) Fabien Potencier <fabien@symfony.com>
  6. *
  7. * For the full copyright and license information, please view the LICENSE
  8. * file that was distributed with this source code.
  9. */
  10. namespace Symfony\Component\Notifier;
  11. use Symfony\Component\Notifier\Bridge\Firebase\FirebaseTransportFactory;
  12. use Symfony\Component\Notifier\Bridge\FreeMobile\FreeMobileTransportFactory;
  13. use Symfony\Component\Notifier\Bridge\Mattermost\MattermostTransportFactory;
  14. use Symfony\Component\Notifier\Bridge\Nexmo\NexmoTransportFactory;
  15. use Symfony\Component\Notifier\Bridge\OvhCloud\OvhCloudTransportFactory;
  16. use Symfony\Component\Notifier\Bridge\RocketChat\RocketChatTransportFactory;
  17. use Symfony\Component\Notifier\Bridge\Sinch\SinchTransportFactory;
  18. use Symfony\Component\Notifier\Bridge\Slack\SlackTransportFactory;
  19. use Symfony\Component\Notifier\Bridge\Telegram\TelegramTransportFactory;
  20. use Symfony\Component\Notifier\Bridge\Twilio\TwilioTransportFactory;
  21. use Symfony\Component\Notifier\Exception\UnsupportedSchemeException;
  22. use Symfony\Component\Notifier\Transport\Dsn;
  23. use Symfony\Component\Notifier\Transport\FailoverTransport;
  24. use Symfony\Component\Notifier\Transport\NullTransportFactory;
  25. use Symfony\Component\Notifier\Transport\RoundRobinTransport;
  26. use Symfony\Component\Notifier\Transport\TransportFactoryInterface;
  27. use Symfony\Component\Notifier\Transport\TransportInterface;
  28. use Symfony\Component\Notifier\Transport\Transports;
  29. use Symfony\Contracts\EventDispatcher\EventDispatcherInterface;
  30. use Symfony\Contracts\HttpClient\HttpClientInterface;
  31. /**
  32. * @author Fabien Potencier <fabien@symfony.com>
  33. *
  34. * @experimental in 5.1
  35. */
  36. class Transport
  37. {
  38. private const FACTORY_CLASSES = [
  39. SlackTransportFactory::class,
  40. TelegramTransportFactory::class,
  41. MattermostTransportFactory::class,
  42. NexmoTransportFactory::class,
  43. RocketChatTransportFactory::class,
  44. TwilioTransportFactory::class,
  45. OvhCloudTransportFactory::class,
  46. FirebaseTransportFactory::class,
  47. SinchTransportFactory::class,
  48. FreeMobileTransportFactory::class,
  49. ];
  50. private $factories;
  51. public static function fromDsn(string $dsn, EventDispatcherInterface $dispatcher = null, HttpClientInterface $client = null): TransportInterface
  52. {
  53. $factory = new self(self::getDefaultFactories($dispatcher, $client));
  54. return $factory->fromString($dsn);
  55. }
  56. public static function fromDsns(array $dsns, EventDispatcherInterface $dispatcher = null, HttpClientInterface $client = null): TransportInterface
  57. {
  58. $factory = new self(iterator_to_array(self::getDefaultFactories($dispatcher, $client)));
  59. return $factory->fromStrings($dsns);
  60. }
  61. /**
  62. * @param TransportFactoryInterface[] $factories
  63. */
  64. public function __construct(iterable $factories)
  65. {
  66. $this->factories = $factories;
  67. }
  68. public function fromStrings(array $dsns): Transports
  69. {
  70. $transports = [];
  71. foreach ($dsns as $name => $dsn) {
  72. $transports[$name] = $this->fromString($dsn);
  73. }
  74. return new Transports($transports);
  75. }
  76. public function fromString(string $dsn): TransportInterface
  77. {
  78. $dsns = preg_split('/\s++\|\|\s++/', $dsn);
  79. if (\count($dsns) > 1) {
  80. return new FailoverTransport($this->createFromDsns($dsns));
  81. }
  82. $dsns = preg_split('/\s++&&\s++/', $dsn);
  83. if (\count($dsns) > 1) {
  84. return new RoundRobinTransport($this->createFromDsns($dsns));
  85. }
  86. return $this->fromDsnObject(Dsn::fromString($dsn));
  87. }
  88. public function fromDsnObject(Dsn $dsn): TransportInterface
  89. {
  90. foreach ($this->factories as $factory) {
  91. if ($factory->supports($dsn)) {
  92. return $factory->create($dsn);
  93. }
  94. }
  95. throw new UnsupportedSchemeException($dsn);
  96. }
  97. /**
  98. * @return TransportInterface[]
  99. */
  100. private function createFromDsns(array $dsns): array
  101. {
  102. $transports = [];
  103. foreach ($dsns as $dsn) {
  104. $transports[] = $this->fromDsnObject(Dsn::fromString($dsn));
  105. }
  106. return $transports;
  107. }
  108. /**
  109. * @return TransportFactoryInterface[]
  110. */
  111. private static function getDefaultFactories(EventDispatcherInterface $dispatcher = null, HttpClientInterface $client = null): iterable
  112. {
  113. foreach (self::FACTORY_CLASSES as $factoryClass) {
  114. if (class_exists($factoryClass)) {
  115. yield new $factoryClass($dispatcher, $client);
  116. }
  117. }
  118. yield new NullTransportFactory($dispatcher, $client);
  119. }
  120. }