Skip to content

Instantly share code, notes, and snippets.

@lakiboy
Created November 28, 2015 12:53
Show Gist options
  • Save lakiboy/7cc805f86a3ce85a606b to your computer and use it in GitHub Desktop.
Save lakiboy/7cc805f86a3ce85a606b to your computer and use it in GitHub Desktop.

Revisions

  1. lakiboy created this gist Nov 28, 2015.
    31 changes: 31 additions & 0 deletions DelegatingProducer.php
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,31 @@
    <?php

    namespace Cinemania\CoreBundle\SimpleBus;

    use OldSound\RabbitMqBundle\RabbitMq\Fallback;
    use OldSound\RabbitMqBundle\RabbitMq\ProducerInterface;
    use Symfony\Component\DependencyInjection\ContainerInterface;

    class DelegatingProducer extends Fallback
    {
    private $container;

    public function __construct(ContainerInterface $container)
    {
    $this->container = $container;
    }

    public function publish($msg, $routingKey = '', $props = array())
    {
    if (!isset($props['producer'])) {
    throw new \RuntimeException(sprintf('No "producer" key defined in %s', __METHOD__));
    }

    /** @var ProducerInterface $producer */
    $producer = $this->container->get(sprintf('old_sound_rabbit_mq.%s_producer', $props['producer']));

    unset($props['producer']);

    return $producer->publish($msg, $routingKey, $props);
    }
    }
    51 changes: 51 additions & 0 deletions DelegatingProducerTest.php
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,51 @@
    <?php

    namespace Cinemania\CoreBundle\Tests\SimpleBus;

    use Cinemania\CoreBundle\SimpleBus\DelegatingProducer;

    class DelegatingProducerTest extends \PHPUnit_Framework_TestCase
    {
    /** @var \PHPUnit_Framework_MockObject_MockObject */
    private $container;

    /** @var DelegatingProducer */
    private $producer;

    public function setUp()
    {
    $this->container = $this->getMock('Symfony\Component\DependencyInjection\ContainerInterface');
    $this->producer = new DelegatingProducer($this->container);
    }

    /**
    * @expectedException \RuntimeException
    */
    public function testPublishFailsWithoutProducer()
    {
    $this->producer->publish('string', '');
    }

    public function testPublish()
    {
    $message = 'message';
    $routing = '';

    // Actual producer called.
    $producer = $this->getMock('OldSound\RabbitMqBundle\RabbitMq\ProducerInterface');
    $producer
    ->expects($this->once())
    ->method('publish')
    ->with($this->equalTo($message), $this->equalTo($routing), $this->equalTo([]))
    ;

    $this->container
    ->expects($this->once())
    ->method('get')
    ->with($this->equalTo('old_sound_rabbit_mq.foo_bar_producer'))
    ->willReturn($producer)
    ;

    $this->producer->publish($message, $routing, ['producer' => 'foo_bar']);
    }
    }
    33 changes: 33 additions & 0 deletions ProducerNameResolver.php
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,33 @@
    <?php

    namespace Cinemania\CoreBundle\SimpleBus;

    use SimpleBus\Asynchronous\Properties\AdditionalPropertiesResolver;

    class ProducerNameResolver implements AdditionalPropertiesResolver
    {
    public function resolveAdditionalPropertiesFor($message)
    {
    $name = self::tableize(substr(get_class($message), strrpos(get_class($message), '\\') + 1));

    if (substr($name, -8) === '_command') {
    $name = substr($name, 0, strlen($name) - 8);
    } elseif (substr($name, -6) === '_event') {
    $name = substr($name, 0, strlen($name) - 6);
    }

    return ['producer' => $name];
    }

    /**
    * Taken from Doctrine\Common\Inflector.
    *
    * @param string $word
    *
    * @return string
    */
    private static function tableize($word)
    {
    return strtolower(preg_replace('~(?<=\\w)([A-Z])~', '_$1', $word));
    }
    }
    47 changes: 47 additions & 0 deletions ProducerNameResolverTest.php
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,47 @@
    <?php

    namespace Cinemania\CoreBundle\Tests\SimpleBus;

    use Cinemania\CoreBundle\SimpleBus\ProducerNameResolver;

    class ProducerNameResolverTest extends \PHPUnit_Framework_TestCase
    {
    /**
    * @dataProvider getData
    *
    * @param object $message
    * @param string $producer
    */
    public function testResolveAdditionalPropertiesFor($message, $producer)
    {
    $props = (new ProducerNameResolver())->resolveAdditionalPropertiesFor($message);

    $this->assertEquals(['producer' => $producer], $props);
    }

    public function getData()
    {
    return [
    [new FooBar(), 'foo_bar'],
    [new FooBarCommand(), 'foo_bar'],
    [new FooBarEvent(), 'foo_bar'],
    [new FooBarCommandEvent(), 'foo_bar_command'],
    ];
    }
    }

    class FooBar
    {
    }

    class FooBarCommand
    {
    }

    class FooBarEvent
    {
    }

    class FooBarCommandEvent
    {
    }