SlideShare a Scribd company logo
1 of 144
Download to read offline
There's a Rabbit
                          on my Symfony
                            RabbitMQ and Symfony2 Integration




                                   Álvaro Videla



                            Symfony Live 2011

Thursday, March 3, 2011
Who?


Thursday, March 3, 2011
About Me


                    •     Development Manager at TheNetCircle.com

                    •     Blog: http://videlalvaro.github.com/

                    •     Twitter: @old_sound




Thursday, March 3, 2011
About Me


                    •     Developer at Liip

                    •     Blog: http://videlalvaro.github.com/

                    •     Twitter: @old_sound




Thursday, March 3, 2011
About Me
                          Co-authoring

               RabbitMQ in Action
              http://bit.ly/rabbitmq




Thursday, March 3, 2011
Why Do I need
                           RabbitMQ?


Thursday, March 3, 2011
Or



Thursday, March 3, 2011
Why Do I need
                           Messaging?


Thursday, March 3, 2011
An Upload Picture
                           Form as seen by:


Thursday, March 3, 2011
The User



Thursday, March 3, 2011
I don’t want to wait
                          till your app resizes
                                my image!


Thursday, March 3, 2011
The Product Owner



Thursday, March 3, 2011
Can we also notify the
                    user friends when she
                    uploads a new image?


Thursday, March 3, 2011
Can we also notify the
                    user friends when she
                    uploads a new image?
       I forgot to mention we need it for tomorrow…

Thursday, March 3, 2011
The Sysadmin



Thursday, March 3, 2011
Dumb! You’re delivering
                    full size images!
                 The bandwidth bill has
                         tripled!

Thursday, March 3, 2011
Dumb! You’re delivering
                    full size images!
                 The bandwidth bill has
                         tripled!
                          We need this fixed for yesterday!
Thursday, March 3, 2011
The Developer in the
                              other team


Thursday, March 3, 2011
I need to call your PHP
                   stuff but from Python


Thursday, March 3, 2011
I need to call your PHP
                   stuff but from Python

                          And also Java starting next week
Thursday, March 3, 2011
You



Thursday, March 3, 2011
FML!

Thursday, March 3, 2011
Is there a solution?



Thursday, March 3, 2011
RabbitMQ & AMQP



Thursday, March 3, 2011
AMQP



Thursday, March 3, 2011
AMQP
                    • Advanced Message Queuing Protocol
                    • Suits Interoperability
                    • Completely Open Protocol
                    • Binary Protocol
                    • AMQP Model
                    • AMQP Wire Format
Thursday, March 3, 2011
AMQP Model

                    • Exchanges
                    • Message Queues
                    • Bindings
                    • Rules for binding them

Thursday, March 3, 2011
AMQP Wire Protocol


                    • Functional Layer
                    • Transport Layer


Thursday, March 3, 2011
Message Flow




                  http://www.redhat.com/docs/en-US/Red_Hat_Enterprise_MRG/1.0/html/Messaging_Tutorial/chap-Messaging_Tutorial-Initial_Concepts.html



Thursday, March 3, 2011
Exchange Types

                    • Fanout
                    • Direct
                    • Topic


Thursday, March 3, 2011
http://www.redhat.com/docs/en-US/Red_Hat_Enterprise_MRG/1.0/html/Messaging_Tutorial/sect-Messaging_Tutorial-Initial_Concepts-
                                                                       Fanout_Exchange.html




Thursday, March 3, 2011
http://www.redhat.com/docs/en-US/Red_Hat_Enterprise_MRG/1.0/html/Messaging_Tutorial/sect-Messaging_Tutorial-Initial_Concepts-
                                                                        Direct_Exchange.html




Thursday, March 3, 2011
http://www.redhat.com/docs/en-US/Red_Hat_Enterprise_MRG/1.0/html/Messaging_Tutorial/sect-Messaging_Tutorial-Initial_Concepts-
                                                                        Topic_Exchange.html




Thursday, March 3, 2011
Usage Scenarios




Thursday, March 3, 2011
Usage Scenarios

                    • Batch Processing




Thursday, March 3, 2011
Usage Scenarios

                    • Batch Processing
                    • Image Uploading




Thursday, March 3, 2011
Usage Scenarios

                    • Batch Processing
                    • Image Uploading
                    • Distributed Logging



Thursday, March 3, 2011
Scenario


                          Batch Processing



Thursday, March 3, 2011
Requirements




Thursday, March 3, 2011
Requirements

                    • Generate XML




Thursday, March 3, 2011
Requirements

                    • Generate XML
                    • Distribution Over a Cluster



Thursday, March 3, 2011
Requirements

                    • Generate XML
                    • Distribution Over a Cluster
                    • Elasticity - Add/Remove new workers


Thursday, March 3, 2011
Requirements

                    • Generate XML
                    • Distribution Over a Cluster
                    • Elasticity - Add/Remove new workers
                    • No Code Changes

Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Publisher Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);

                 $msg = new AMQPMessage($video_info,
                            array('content_type' => 'text/plain',
                                   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'video-desc-ex');

                 $channel->close();
                 $conn->close();




Thursday, March 3, 2011
Publisher Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);

                 $msg = new AMQPMessage($video_info,
                            array('content_type' => 'text/plain',
                                   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'video-desc-ex');

                 $channel->close();
                 $conn->close();




Thursday, March 3, 2011
Publisher Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);

                 $msg = new AMQPMessage($video_info,
                            array('content_type' => 'text/plain',
                                   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'video-desc-ex');

                 $channel->close();
                 $conn->close();




Thursday, March 3, 2011
Publisher Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);

                 $msg = new AMQPMessage($video_info,
                            array('content_type' => 'text/plain',
                                   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'video-desc-ex');

                 $channel->close();
                 $conn->close();




Thursday, March 3, 2011
Publisher Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);

                 $msg = new AMQPMessage($video_info,
                            array('content_type' => 'text/plain',
                                   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'video-desc-ex');

                 $channel->close();
                 $conn->close();




Thursday, March 3, 2011
Publisher Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);

                 $msg = new AMQPMessage($video_info,
                            array('content_type' => 'text/plain',
                                   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'video-desc-ex');

                 $channel->close();
                 $conn->close();




Thursday, March 3, 2011
Consumer Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);
                 $channel->queue_declare('video-desc-queue', false, true,
                              false, false);
                 $channel->queue_bind('video-desc-queue', 'video-desc-ex');

                 $channel->basic_consume('video-desc-queue', $consumer_tag,
                              false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                     $channel->wait();
                 }



Thursday, March 3, 2011
Consumer Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);
                 $channel->queue_declare('video-desc-queue', false, true,
                              false, false);
                 $channel->queue_bind('video-desc-queue', 'video-desc-ex');

                 $channel->basic_consume('video-desc-queue', $consumer_tag,
                              false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                     $channel->wait();
                 }



Thursday, March 3, 2011
Consumer Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);
                 $channel->queue_declare('video-desc-queue', false, true,
                              false, false);
                 $channel->queue_bind('video-desc-queue', 'video-desc-ex');

                 $channel->basic_consume('video-desc-queue', $consumer_tag,
                              false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                     $channel->wait();
                 }



Thursday, March 3, 2011
Consumer Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);
                 $channel->queue_declare('video-desc-queue', false, true,
                              false, false);
                 $channel->queue_bind('video-desc-queue', 'video-desc-ex');

                 $channel->basic_consume('video-desc-queue', $consumer_tag,
                              false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                     $channel->wait();
                 }



Thursday, March 3, 2011
Consumer Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);
                 $channel->queue_declare('video-desc-queue', false, true,
                              false, false);
                 $channel->queue_bind('video-desc-queue', 'video-desc-ex');

                 $channel->basic_consume('video-desc-queue', $consumer_tag,
                              false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                     $channel->wait();
                 }



Thursday, March 3, 2011
Consumer Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);
                 $channel->queue_declare('video-desc-queue', false, true,
                              false, false);
                 $channel->queue_bind('video-desc-queue', 'video-desc-ex');

                 $channel->basic_consume('video-desc-queue', $consumer_tag,
                              false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                     $channel->wait();
                 }



Thursday, March 3, 2011
Consumer Code
                 $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST);
                 $channel = $conn->channel();

                 $channel->exchange_declare('video-desc-ex', 'direct', false,
                              true, false);
                 $channel->queue_declare('video-desc-queue', false, true,
                              false, false);
                 $channel->queue_bind('video-desc-queue', 'video-desc-ex');

                 $channel->basic_consume('video-desc-queue', $consumer_tag,
                              false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                     $channel->wait();
                 }



Thursday, March 3, 2011
Scenario


                          Upload Pictures



Thursday, March 3, 2011
Requirements




Thursday, March 3, 2011
Requirements
                    • Upload Picture




Thursday, March 3, 2011
Requirements
                    • Upload Picture
                    • Reward User




Thursday, March 3, 2011
Requirements
                    • Upload Picture
                    • Reward User
                    • Notify User Friends



Thursday, March 3, 2011
Requirements
                    • Upload Picture
                    • Reward User
                    • Notify User Friends
                    • Resize Picture


Thursday, March 3, 2011
Requirements
                    • Upload Picture
                    • Reward User
                    • Notify User Friends
                    • Resize Picture
                    • No Code Changes

Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('upload-pictures', 'fanout', false,
                 true, false);

                 $metadata = json_encode(array(
                   'image_id' => $image_id,
                   'user_id' => $user_id,
                   ‘image_path' => $image_path));

                 $msg = new AMQPMessage($metadata, array('content_type' =>
                 'application/json',   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'upload-pictures');




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('upload-pictures', 'fanout', false,
                 true, false);

                 $metadata = json_encode(array(
                   'image_id' => $image_id,
                   'user_id' => $user_id,
                   ‘image_path' => $image_path));

                 $msg = new AMQPMessage($metadata, array('content_type' =>
                 'application/json',   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'upload-pictures');




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('upload-pictures', 'fanout', false,
                 true, false);

                 $metadata = json_encode(array(
                   'image_id' => $image_id,
                   'user_id' => $user_id,
                   ‘image_path' => $image_path));

                 $msg = new AMQPMessage($metadata, array('content_type' =>
                 'application/json',   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'upload-pictures');




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('upload-pictures', 'fanout', false,
                 true, false);

                 $metadata = json_encode(array(
                   'image_id' => $image_id,
                   'user_id' => $user_id,
                   ‘image_path' => $image_path));

                 $msg = new AMQPMessage($metadata, array('content_type' =>
                 'application/json',   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'upload-pictures');




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('upload-pictures', 'fanout', false,
                 true, false);

                 $metadata = json_encode(array(
                   'image_id' => $image_id,
                   'user_id' => $user_id,
                   ‘image_path' => $image_path));

                 $msg = new AMQPMessage($metadata, array('content_type' =>
                 'application/json',   'delivery_mode' => 2));

                 $channel->basic_publish($msg, 'upload-pictures');




Thursday, March 3, 2011
Consumer Code
                 $channel->exchange_declare('upload-pictures', 'fanout',
                             false, true, false);

                 $channel->queue_declare('resize-picture', false, true,
                             false, false);

                 $channel->queue_bind('resize-picture', 'upload-pictures');

                 $channel->basic_consume('resize-picture', $consumer_tag,
                             false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                   $channel->wait();
                 }




Thursday, March 3, 2011
Consumer Code
                 $channel->exchange_declare('upload-pictures', 'fanout',
                             false, true, false);

                 $channel->queue_declare('resize-picture', false, true,
                             false, false);

                 $channel->queue_bind('resize-picture', 'upload-pictures');

                 $channel->basic_consume('resize-picture', $consumer_tag,
                             false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                   $channel->wait();
                 }




Thursday, March 3, 2011
Consumer Code
                 $channel->exchange_declare('upload-pictures', 'fanout',
                             false, true, false);

                 $channel->queue_declare('resize-picture', false, true,
                             false, false);

                 $channel->queue_bind('resize-picture', 'upload-pictures');

                 $channel->basic_consume('resize-picture', $consumer_tag,
                             false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                   $channel->wait();
                 }




Thursday, March 3, 2011
Consumer Code
                 $channel->exchange_declare('upload-pictures', 'fanout',
                             false, true, false);

                 $channel->queue_declare('resize-picture', false, true,
                             false, false);

                 $channel->queue_bind('resize-picture', 'upload-pictures');

                 $channel->basic_consume('resize-picture', $consumer_tag,
                             false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                   $channel->wait();
                 }




Thursday, March 3, 2011
Consumer Code
                 $channel->exchange_declare('upload-pictures', 'fanout',
                             false, true, false);

                 $channel->queue_declare('resize-picture', false, true,
                             false, false);

                 $channel->queue_bind('resize-picture', 'upload-pictures');

                 $channel->basic_consume('resize-picture', $consumer_tag,
                             false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                   $channel->wait();
                 }




Thursday, March 3, 2011
Consumer Code
                 $channel->exchange_declare('upload-pictures', 'fanout',
                             false, true, false);

                 $channel->queue_declare('resize-picture', false, true,
                             false, false);

                 $channel->queue_bind('resize-picture', 'upload-pictures');

                 $channel->basic_consume('resize-picture', $consumer_tag,
                             false, false, false, false, $consumer);

                 while(count($channel->callbacks)) {
                   $channel->wait();
                 }




Thursday, March 3, 2011
Consumer Code
                 $consumer = function($msg){

                      $meta = json_decode($msg->body, true);
                 	
                      resize_picture($meta['image_id'], $meta['image_path']);
                 	
                      $msg->delivery_info['channel']->
                        basic_ack($msg->delivery_info['delivery_tag']);
                 };




Thursday, March 3, 2011
Consumer Code
                 $consumer = function($msg){

                      $meta = json_decode($msg->body, true);
                 	
                      resize_picture($meta['image_id'], $meta['image_path']);
                 	
                      $msg->delivery_info['channel']->
                        basic_ack($msg->delivery_info['delivery_tag']);
                 };




Thursday, March 3, 2011
Consumer Code
                 $consumer = function($msg){

                      $meta = json_decode($msg->body, true);
                 	
                      resize_picture($meta['image_id'], $meta['image_path']);
                 	
                      $msg->delivery_info['channel']->
                        basic_ack($msg->delivery_info['delivery_tag']);
                 };




Thursday, March 3, 2011
Consumer Code
                 $consumer = function($msg){

                      $meta = json_decode($msg->body, true);
                 	
                      resize_picture($meta['image_id'], $meta['image_path']);
                 	
                      $msg->delivery_info['channel']->
                        basic_ack($msg->delivery_info['delivery_tag']);
                 };




Thursday, March 3, 2011
Consumer Code
                 $consumer = function($msg){

                      $meta = json_decode($msg->body, true);
                 	
                      resize_picture($meta['image_id'], $meta['image_path']);
                 	
                      $msg->delivery_info['channel']->
                        basic_ack($msg->delivery_info['delivery_tag']);
                 };




Thursday, March 3, 2011
Scenario


                          Distributed Logging



Thursday, March 3, 2011
Requirements




Thursday, March 3, 2011
Requirements
                    • Several Web Servers




Thursday, March 3, 2011
Requirements
                    • Several Web Servers
                    • Logic Separated by Module/Action




Thursday, March 3, 2011
Requirements
                    • Several Web Servers
                    • Logic Separated by Module/Action
                    • Several Log Levels:



Thursday, March 3, 2011
Requirements
                    • Several Web Servers
                    • Logic Separated by Module/Action
                    • Several Log Levels:
                     • Info, Warning, Error


Thursday, March 3, 2011
Requirements
                    • Several Web Servers
                    • Logic Separated by Module/Action
                    • Several Log Levels:
                     • Info, Warning, Error
                    • Add/Remove log listeners at will

Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Design




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $msg = new AMQPMessage('some log message',
                               array('content_type' => 'text/plain'));

                 $channel->basic_publish($msg, 'logs',
                               server1.user.profile.info');




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $msg = new AMQPMessage('some log message',
                               array('content_type' => 'text/plain'));

                 $channel->basic_publish($msg, 'logs',
                               server1.user.profile.info');




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $msg = new AMQPMessage('some log message',
                               array('content_type' => 'text/plain'));

                 $channel->basic_publish($msg, 'logs',
                               server1.user.profile.info');




Thursday, March 3, 2011
Publisher Code
                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $msg = new AMQPMessage('some log message',
                               array('content_type' => 'text/plain'));

                 $channel->basic_publish($msg, 'logs',
                               server1.user.profile.info');




Thursday, March 3, 2011
Consumer Code

                           Get messages sent by host:

                                   server1




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('server1-logs', false, true,
                               false, false);

                 $channel->queue_bind('server1-logs', 'logs', 'server1.#');




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('server1-logs', false, true,
                               false, false);

                 $channel->queue_bind('server1-logs', 'logs', 'server1.#');




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('server1-logs', false, true,
                               false, false);

                 $channel->queue_bind('server1-logs', 'logs', 'server1.#');




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('server1-logs', false, true,
                               false, false);

                 $channel->queue_bind('server1-logs', 'logs', 'server1.#');




Thursday, March 3, 2011
Consumer Code


                           Get all error messages




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('error-logs', false, true,
                               false, false);

                 $channel->queue_bind('error-logs', 'logs', '#.error');




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('error-logs', false, true,
                               false, false);

                 $channel->queue_bind('error-logs', 'logs', '#.error');




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('error-logs', false, true,
                               false, false);

                 $channel->queue_bind('error-logs', 'logs', '#.error');




Thursday, March 3, 2011
Consumer Code

                 $channel->exchange_declare('logs', 'topic', false,
                               true, false);

                 $channel->queue_declare('error-logs', false, true,
                               false, false);

                 $channel->queue_bind('error-logs', 'logs', '#.error');




Thursday, March 3, 2011
Symfony Integration



Thursday, March 3, 2011
RabbitMQ Bundle




Thursday, March 3, 2011
RabbitMQ Bundle

                                  Goal:


                            To be easy to use



Thursday, March 3, 2011
RabbitMQ Bundle
                                        Publish a Message:

                          $msg = array('user_id' => 1235,
                                   'image_path' => '/path/to/new/
                                   pic.png');

                          $this->get('rabbitmq.upload_picture_producer')->
                                    publish(serialize($msg));




Thursday, March 3, 2011
RabbitMQ Bundle
                             Consume a Message:

           $ ./app/console_dev rabbitmq:consumer -m 1 upload_picture




Thursday, March 3, 2011
RabbitMQ Bundle
                            Consume 50 Messages:

           $ ./app/console_dev rabbitmq:consumer -m 50 upload_picture




Thursday, March 3, 2011
RabbitMQ Bundle
                           Consume infinite* Messages:

           $ ./app/console_dev rabbitmq:consumer -m -1 upload_picture




                                    *messages may not be infinite




Thursday, March 3, 2011
RabbitMQ Bundle
                                 Configuration:
           # app/config/config.yml
           rabbitmq.config:
               connections:
                   default:
                       host:       'localhost'
                       port:       5672
                       user:       'guest'
                       password: 'guest'
                       vhost:      '/'




Thursday, March 3, 2011
RabbitMQ Bundle
                                 Configuration:
           # app/config/config.yml
           rabbitmq.config:
               connections:
                   ...
               producers:
                    upload_picture:
                        connection: default
                        exchange_options: {name: 'upload-picture',
                                             type: direct}




Thursday, March 3, 2011
RabbitMQ Bundle
                                Configuration:
           # app/config/config.yml
           rabbitmq.config:
               connections:
                  ...
              consumers:
                   upload_picture:
                       connection: default
                       exchange_options: {name: 'upload-picture',
                                            type: direct}
                       queue_options:    {name: 'upload-picture'}
                       callback:         upload_picture_service




Thursday, March 3, 2011
RabbitMQ Bundle
                                    Using a Producer:
           public function indexAction($name)
           {
               ...
               $msg = array('user_id' => 1235,
                       'image_path' => '/path/to/new/pic.png');

                     $this->get('rabbitmq.upload_picture_producer')->
                           publish(serialize($msg));
                     ...
           }




Thursday, March 3, 2011
RabbitMQ Bundle
                               Consumer Class:
           class UploadPictureConsumer extends ContainerAware
           implements ConsumerInterface
           {
               public function execute($msg)
               {
                   // Process picture upload.
                   // $msg will be what was published
                  // from the Controller.
               }
           }




Thursday, March 3, 2011
RabbitMQ Bundle
                                Recap:




Thursday, March 3, 2011
RabbitMQ Bundle
                                              Recap:

                • Add an entry for the consumer/producer in
                          the configuration.




Thursday, March 3, 2011
RabbitMQ Bundle
                                              Recap:

                • Add an entry for the consumer/producer in
                          the configuration.
                • Implement your Callback.


Thursday, March 3, 2011
RabbitMQ Bundle
                                              Recap:

                • Add an entry for the consumer/producer in
                          the configuration.
                • Implement your Callback.
                • Start the consumer from the CLI.

Thursday, March 3, 2011
RabbitMQ Bundle
                                              Recap:

                • Add an entry for the consumer/producer in
                          the configuration.
                • Implement your Callback.
                • Start the consumer from the CLI.
                • Add code to publish messages.
Thursday, March 3, 2011
RabbitMQ Bundle
                              There’s more:




Thursday, March 3, 2011
RabbitMQ Bundle
                                There’s more:

                • RPC clients and servers




Thursday, March 3, 2011
RabbitMQ Bundle
                                There’s more:

                • RPC clients and servers
                • Anonymous consumers



Thursday, March 3, 2011
RabbitMQ Bundle
                                There’s more:

                • RPC clients and servers
                • Anonymous consumers
                • Parallel RPC


Thursday, March 3, 2011
RabbitMQ Bundle
                                           Fork it at


                          http://github.com/videlalvaro/RabbitMqBundle




Thursday, March 3, 2011
Why RabbitMQ?



Thursday, March 3, 2011
RabbitMQ

                    • Enterprise Messaging System
                    • Open Source MPL
                    • Written in Erlang/OTP
                    • Commercial Support

Thursday, March 3, 2011
Features

                    • Reliable and High Scalable
                    • Easy To install
                    • Easy To Cluster
                    • Runs on: Windows, Solaris, Linux, OSX
                    • AMQP 0.8 - 0.9.1

Thursday, March 3, 2011
Client Libraries

                    • Java
                    • .NET/C#
                    • Erlang
                    • Ruby, Python, PHP, Perl, AS3, Lisp, Scala,
                          Clojure, Haskell



Thursday, March 3, 2011
Docs/Support

                    •     http://www.rabbitmq.com/documentation.html

                    •     http://dev.rabbitmq.com/wiki/

                    •     #rabbitmq at irc.freenode.net

                    •     http://www.rabbitmq.com/email-archive.html




Thursday, March 3, 2011
One Setup for HA




Thursday, March 3, 2011
Conclusion




Thursday, March 3, 2011
Conclusion

                    • Flexibility




Thursday, March 3, 2011
Conclusion

                    • Flexibility
                    • Scalability



Thursday, March 3, 2011
Conclusion

                    • Flexibility
                    • Scalability
                    • Interoperability


Thursday, March 3, 2011
Conclusion

                    • Flexibility
                    • Scalability
                    • Interoperability
                    • Reduce Ops

Thursday, March 3, 2011
Questions?



Thursday, March 3, 2011
Thanks!
                                   Álvaro Videla
                             http://twitter.com/old_sound
                             http://github.com/videlalvaro
                                 http://github.com/tnc
                          http://www.slideshare.net/old_sound




Thursday, March 3, 2011

More Related Content

What's hot

Introducing Drools
Introducing DroolsIntroducing Drools
Introducing Drools
Mario Fusco
 

What's hot (20)

Owl: The New Odoo UI Framework
Owl: The New Odoo UI FrameworkOwl: The New Odoo UI Framework
Owl: The New Odoo UI Framework
 
Country State City Dropdown in PHP
Country State City Dropdown in PHPCountry State City Dropdown in PHP
Country State City Dropdown in PHP
 
Models for hierarchical data
Models for hierarchical dataModels for hierarchical data
Models for hierarchical data
 
Flask
FlaskFlask
Flask
 
React Native Firebase
React Native FirebaseReact Native Firebase
React Native Firebase
 
Teach a Dog to REST
Teach a Dog to RESTTeach a Dog to REST
Teach a Dog to REST
 
Railway Oriented Programming
Railway Oriented ProgrammingRailway Oriented Programming
Railway Oriented Programming
 
Jboss Tutorial Basics
Jboss Tutorial BasicsJboss Tutorial Basics
Jboss Tutorial Basics
 
Cloud + Docker - La arquitectura MELI usando AWS en la nube.
Cloud + Docker - La arquitectura MELI usando AWS en la nube.Cloud + Docker - La arquitectura MELI usando AWS en la nube.
Cloud + Docker - La arquitectura MELI usando AWS en la nube.
 
Why The Free Monad isn't Free
Why The Free Monad isn't FreeWhy The Free Monad isn't Free
Why The Free Monad isn't Free
 
Doctrine ORM Internals. UnitOfWork
Doctrine ORM Internals. UnitOfWorkDoctrine ORM Internals. UnitOfWork
Doctrine ORM Internals. UnitOfWork
 
Why Vue.js?
Why Vue.js?Why Vue.js?
Why Vue.js?
 
Spring Boot
Spring BootSpring Boot
Spring Boot
 
Introducing Drools
Introducing DroolsIntroducing Drools
Introducing Drools
 
The Odoo JS Framework
The Odoo JS FrameworkThe Odoo JS Framework
The Odoo JS Framework
 
Task parallel library presentation
Task parallel library presentationTask parallel library presentation
Task parallel library presentation
 
JavaScript Event Loop
JavaScript Event LoopJavaScript Event Loop
JavaScript Event Loop
 
Security: Odoo Code Hardening
Security: Odoo Code HardeningSecurity: Odoo Code Hardening
Security: Odoo Code Hardening
 
Introduction Django
Introduction DjangoIntroduction Django
Introduction Django
 
XPages Workshop: Concepts And Exercises
XPages Workshop:   Concepts And ExercisesXPages Workshop:   Concepts And Exercises
XPages Workshop: Concepts And Exercises
 

Viewers also liked

Telephony with OpenShift Twilio and MongoDB
Telephony with OpenShift Twilio and MongoDBTelephony with OpenShift Twilio and MongoDB
Telephony with OpenShift Twilio and MongoDB
Mark Atwood
 

Viewers also liked (16)

Scaling Symfony2 apps with RabbitMQ - Symfony UK Meetup
Scaling Symfony2 apps with RabbitMQ - Symfony UK MeetupScaling Symfony2 apps with RabbitMQ - Symfony UK Meetup
Scaling Symfony2 apps with RabbitMQ - Symfony UK Meetup
 
Speed up your Symfony2 application and build awesome features with Redis
Speed up your Symfony2 application and build awesome features with RedisSpeed up your Symfony2 application and build awesome features with Redis
Speed up your Symfony2 application and build awesome features with Redis
 
Building real time applications with Symfony2
Building real time applications with Symfony2Building real time applications with Symfony2
Building real time applications with Symfony2
 
Intro to Angular.js & Zend2 for Front-End Web Applications
Intro to Angular.js & Zend2  for Front-End Web ApplicationsIntro to Angular.js & Zend2  for Front-End Web Applications
Intro to Angular.js & Zend2 for Front-End Web Applications
 
Juc boston2014.pptx
Juc boston2014.pptxJuc boston2014.pptx
Juc boston2014.pptx
 
PHP, RabbitMQ, and You
PHP, RabbitMQ, and YouPHP, RabbitMQ, and You
PHP, RabbitMQ, and You
 
Telephony with OpenShift Twilio and MongoDB
Telephony with OpenShift Twilio and MongoDBTelephony with OpenShift Twilio and MongoDB
Telephony with OpenShift Twilio and MongoDB
 
What RabbitMQ Can Do For You (Nomad PHP May 2014)
What RabbitMQ Can Do For You (Nomad PHP May 2014)What RabbitMQ Can Do For You (Nomad PHP May 2014)
What RabbitMQ Can Do For You (Nomad PHP May 2014)
 
Working with Asynchronous Events
Working with Asynchronous EventsWorking with Asynchronous Events
Working with Asynchronous Events
 
Asynchronous processing with PHP and Symfony2. Do it simple
Asynchronous processing with PHP and Symfony2. Do it simpleAsynchronous processing with PHP and Symfony2. Do it simple
Asynchronous processing with PHP and Symfony2. Do it simple
 
Scaling applications with RabbitMQ at SunshinePHP
Scaling applications with RabbitMQ   at SunshinePHPScaling applications with RabbitMQ   at SunshinePHP
Scaling applications with RabbitMQ at SunshinePHP
 
Interoperability With RabbitMq
Interoperability With RabbitMqInteroperability With RabbitMq
Interoperability With RabbitMq
 
Rationally boost your symfony2 application with caching tips and monitoring
Rationally boost your symfony2 application with caching tips and monitoringRationally boost your symfony2 application with caching tips and monitoring
Rationally boost your symfony2 application with caching tips and monitoring
 
Integrating RabbitMQ with PHP
Integrating RabbitMQ with PHPIntegrating RabbitMQ with PHP
Integrating RabbitMQ with PHP
 
2016 Digital predictions for marketing, tech, pop culture and everything in b...
2016 Digital predictions for marketing, tech, pop culture and everything in b...2016 Digital predictions for marketing, tech, pop culture and everything in b...
2016 Digital predictions for marketing, tech, pop culture and everything in b...
 
Build Features, Not Apps
Build Features, Not AppsBuild Features, Not Apps
Build Features, Not Apps
 

Similar to Theres a rabbit on my symfony

Visualizations of Spatial and Social Data
Visualizations of Spatial and Social DataVisualizations of Spatial and Social Data
Visualizations of Spatial and Social Data
interface2011
 
Applying operations culture to everything
Applying operations culture to everythingApplying operations culture to everything
Applying operations culture to everything
Theo Schlossnagle
 
Deployment presentation
Deployment presentationDeployment presentation
Deployment presentation
Corey Purcell
 

Similar to Theres a rabbit on my symfony (20)

How Lanyrd uses Twitter
How Lanyrd uses TwitterHow Lanyrd uses Twitter
How Lanyrd uses Twitter
 
Introducing Sencha Touch 2
Introducing Sencha Touch 2Introducing Sencha Touch 2
Introducing Sencha Touch 2
 
A importância dos dados em sua arquitetura... uma visão muito além do SQL Ser...
A importância dos dados em sua arquitetura... uma visão muito além do SQL Ser...A importância dos dados em sua arquitetura... uma visão muito além do SQL Ser...
A importância dos dados em sua arquitetura... uma visão muito além do SQL Ser...
 
High Availability Server Apps
High Availability Server AppsHigh Availability Server Apps
High Availability Server Apps
 
ActiveRain Univerity Link Class
ActiveRain Univerity Link ClassActiveRain Univerity Link Class
ActiveRain Univerity Link Class
 
The State of Web Typography
The State of Web TypographyThe State of Web Typography
The State of Web Typography
 
Testing distributed, complex web applications
Testing distributed, complex web applicationsTesting distributed, complex web applications
Testing distributed, complex web applications
 
Minegems
MinegemsMinegems
Minegems
 
Visualizations of Spatial and Social Data
Visualizations of Spatial and Social DataVisualizations of Spatial and Social Data
Visualizations of Spatial and Social Data
 
Node js techtalksto
Node js techtalkstoNode js techtalksto
Node js techtalksto
 
Interact - How to create an App?
Interact - How to create an App?Interact - How to create an App?
Interact - How to create an App?
 
Applying operations culture to everything
Applying operations culture to everythingApplying operations culture to everything
Applying operations culture to everything
 
Sandro Zaccarini, Achive escape velocity
Sandro Zaccarini, Achive escape velocitySandro Zaccarini, Achive escape velocity
Sandro Zaccarini, Achive escape velocity
 
Introducing Ext GWT 3.0
Introducing Ext GWT 3.0Introducing Ext GWT 3.0
Introducing Ext GWT 3.0
 
City Camp - Wolverhampton presentation
City Camp - Wolverhampton presentationCity Camp - Wolverhampton presentation
City Camp - Wolverhampton presentation
 
Deployment presentation
Deployment presentationDeployment presentation
Deployment presentation
 
Blogs micro
Blogs microBlogs micro
Blogs micro
 
Pronk like you mean it
Pronk like you mean itPronk like you mean it
Pronk like you mean it
 
Re/wiring Brains · Andres Colmenares
Re/wiring Brains · Andres ColmenaresRe/wiring Brains · Andres Colmenares
Re/wiring Brains · Andres Colmenares
 
Evolution of the Mobile Experience
Evolution of the Mobile Experience Evolution of the Mobile Experience
Evolution of the Mobile Experience
 

More from Alvaro Videla

Rabbitmq Boot System
Rabbitmq Boot SystemRabbitmq Boot System
Rabbitmq Boot System
Alvaro Videla
 

More from Alvaro Videla (20)

Improvements in RabbitMQ
Improvements in RabbitMQImprovements in RabbitMQ
Improvements in RabbitMQ
 
Data Migration at Scale with RabbitMQ and Spring Integration
Data Migration at Scale with RabbitMQ and Spring IntegrationData Migration at Scale with RabbitMQ and Spring Integration
Data Migration at Scale with RabbitMQ and Spring Integration
 
RabbitMQ Data Ingestion at Craft Conf
RabbitMQ Data Ingestion at Craft ConfRabbitMQ Data Ingestion at Craft Conf
RabbitMQ Data Ingestion at Craft Conf
 
Unit Test + Functional Programming = Love
Unit Test + Functional Programming = LoveUnit Test + Functional Programming = Love
Unit Test + Functional Programming = Love
 
RabbitMQ Data Ingestion
RabbitMQ Data IngestionRabbitMQ Data Ingestion
RabbitMQ Data Ingestion
 
Dissecting the rabbit: RabbitMQ Internal Architecture
Dissecting the rabbit: RabbitMQ Internal ArchitectureDissecting the rabbit: RabbitMQ Internal Architecture
Dissecting the rabbit: RabbitMQ Internal Architecture
 
Introduction to RabbitMQ | Meetup at Pivotal Labs
Introduction to RabbitMQ | Meetup at Pivotal LabsIntroduction to RabbitMQ | Meetup at Pivotal Labs
Introduction to RabbitMQ | Meetup at Pivotal Labs
 
Writing testable code
Writing testable codeWriting testable code
Writing testable code
 
RabbitMQ Hands On
RabbitMQ Hands OnRabbitMQ Hands On
RabbitMQ Hands On
 
Rabbitmq Boot System
Rabbitmq Boot SystemRabbitmq Boot System
Rabbitmq Boot System
 
Cloud Foundry Bootcamp
Cloud Foundry BootcampCloud Foundry Bootcamp
Cloud Foundry Bootcamp
 
Cloud Messaging With Cloud Foundry
Cloud Messaging With Cloud FoundryCloud Messaging With Cloud Foundry
Cloud Messaging With Cloud Foundry
 
Taming the rabbit
Taming the rabbitTaming the rabbit
Taming the rabbit
 
Vertx
VertxVertx
Vertx
 
Código Fácil De Testear
Código Fácil De TestearCódigo Fácil De Testear
Código Fácil De Testear
 
Desacoplando aplicaciones
Desacoplando aplicacionesDesacoplando aplicaciones
Desacoplando aplicaciones
 
Messaging patterns
Messaging patternsMessaging patterns
Messaging patterns
 
Scaling Web Apps With RabbitMQ - Erlang Factory Lite
Scaling Web Apps With RabbitMQ - Erlang Factory LiteScaling Web Apps With RabbitMQ - Erlang Factory Lite
Scaling Web Apps With RabbitMQ - Erlang Factory Lite
 
Integrating php withrabbitmq_zendcon
Integrating php withrabbitmq_zendconIntegrating php withrabbitmq_zendcon
Integrating php withrabbitmq_zendcon
 
Scaling webappswithrabbitmq
Scaling webappswithrabbitmqScaling webappswithrabbitmq
Scaling webappswithrabbitmq
 

Recently uploaded

Recently uploaded (20)

How to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerHow to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected Worker
 
What Are The Drone Anti-jamming Systems Technology?
What Are The Drone Anti-jamming Systems Technology?What Are The Drone Anti-jamming Systems Technology?
What Are The Drone Anti-jamming Systems Technology?
 
Strategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a FresherStrategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a Fresher
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
 
GenAI Risks & Security Meetup 01052024.pdf
GenAI Risks & Security Meetup 01052024.pdfGenAI Risks & Security Meetup 01052024.pdf
GenAI Risks & Security Meetup 01052024.pdf
 
Automating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps ScriptAutomating Google Workspace (GWS) & more with Apps Script
Automating Google Workspace (GWS) & more with Apps Script
 
Partners Life - Insurer Innovation Award 2024
Partners Life - Insurer Innovation Award 2024Partners Life - Insurer Innovation Award 2024
Partners Life - Insurer Innovation Award 2024
 
Driving Behavioral Change for Information Management through Data-Driven Gree...
Driving Behavioral Change for Information Management through Data-Driven Gree...Driving Behavioral Change for Information Management through Data-Driven Gree...
Driving Behavioral Change for Information Management through Data-Driven Gree...
 
Exploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone ProcessorsExploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone Processors
 
Developing An App To Navigate The Roads of Brazil
Developing An App To Navigate The Roads of BrazilDeveloping An App To Navigate The Roads of Brazil
Developing An App To Navigate The Roads of Brazil
 
AWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of TerraformAWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of Terraform
 
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
 
A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?
 
Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024
 
How to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerHow to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected Worker
 
Understanding Discord NSFW Servers A Guide for Responsible Users.pdf
Understanding Discord NSFW Servers A Guide for Responsible Users.pdfUnderstanding Discord NSFW Servers A Guide for Responsible Users.pdf
Understanding Discord NSFW Servers A Guide for Responsible Users.pdf
 
Advantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your BusinessAdvantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your Business
 
Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)
 
Strategize a Smooth Tenant-to-tenant Migration and Copilot Takeoff
Strategize a Smooth Tenant-to-tenant Migration and Copilot TakeoffStrategize a Smooth Tenant-to-tenant Migration and Copilot Takeoff
Strategize a Smooth Tenant-to-tenant Migration and Copilot Takeoff
 
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
 

Theres a rabbit on my symfony

  • 1. There's a Rabbit on my Symfony RabbitMQ and Symfony2 Integration Álvaro Videla Symfony Live 2011 Thursday, March 3, 2011
  • 3. About Me • Development Manager at TheNetCircle.com • Blog: http://videlalvaro.github.com/ • Twitter: @old_sound Thursday, March 3, 2011
  • 4. About Me • Developer at Liip • Blog: http://videlalvaro.github.com/ • Twitter: @old_sound Thursday, March 3, 2011
  • 5. About Me Co-authoring RabbitMQ in Action http://bit.ly/rabbitmq Thursday, March 3, 2011
  • 6. Why Do I need RabbitMQ? Thursday, March 3, 2011
  • 8. Why Do I need Messaging? Thursday, March 3, 2011
  • 9. An Upload Picture Form as seen by: Thursday, March 3, 2011
  • 11. I don’t want to wait till your app resizes my image! Thursday, March 3, 2011
  • 13. Can we also notify the user friends when she uploads a new image? Thursday, March 3, 2011
  • 14. Can we also notify the user friends when she uploads a new image? I forgot to mention we need it for tomorrow… Thursday, March 3, 2011
  • 16. Dumb! You’re delivering full size images! The bandwidth bill has tripled! Thursday, March 3, 2011
  • 17. Dumb! You’re delivering full size images! The bandwidth bill has tripled! We need this fixed for yesterday! Thursday, March 3, 2011
  • 18. The Developer in the other team Thursday, March 3, 2011
  • 19. I need to call your PHP stuff but from Python Thursday, March 3, 2011
  • 20. I need to call your PHP stuff but from Python And also Java starting next week Thursday, March 3, 2011
  • 23. Is there a solution? Thursday, March 3, 2011
  • 24. RabbitMQ & AMQP Thursday, March 3, 2011
  • 26. AMQP • Advanced Message Queuing Protocol • Suits Interoperability • Completely Open Protocol • Binary Protocol • AMQP Model • AMQP Wire Format Thursday, March 3, 2011
  • 27. AMQP Model • Exchanges • Message Queues • Bindings • Rules for binding them Thursday, March 3, 2011
  • 28. AMQP Wire Protocol • Functional Layer • Transport Layer Thursday, March 3, 2011
  • 29. Message Flow http://www.redhat.com/docs/en-US/Red_Hat_Enterprise_MRG/1.0/html/Messaging_Tutorial/chap-Messaging_Tutorial-Initial_Concepts.html Thursday, March 3, 2011
  • 30. Exchange Types • Fanout • Direct • Topic Thursday, March 3, 2011
  • 35. Usage Scenarios • Batch Processing Thursday, March 3, 2011
  • 36. Usage Scenarios • Batch Processing • Image Uploading Thursday, March 3, 2011
  • 37. Usage Scenarios • Batch Processing • Image Uploading • Distributed Logging Thursday, March 3, 2011
  • 38. Scenario Batch Processing Thursday, March 3, 2011
  • 40. Requirements • Generate XML Thursday, March 3, 2011
  • 41. Requirements • Generate XML • Distribution Over a Cluster Thursday, March 3, 2011
  • 42. Requirements • Generate XML • Distribution Over a Cluster • Elasticity - Add/Remove new workers Thursday, March 3, 2011
  • 43. Requirements • Generate XML • Distribution Over a Cluster • Elasticity - Add/Remove new workers • No Code Changes Thursday, March 3, 2011
  • 45. Publisher Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $msg = new AMQPMessage($video_info, array('content_type' => 'text/plain', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'video-desc-ex'); $channel->close(); $conn->close(); Thursday, March 3, 2011
  • 46. Publisher Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $msg = new AMQPMessage($video_info, array('content_type' => 'text/plain', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'video-desc-ex'); $channel->close(); $conn->close(); Thursday, March 3, 2011
  • 47. Publisher Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $msg = new AMQPMessage($video_info, array('content_type' => 'text/plain', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'video-desc-ex'); $channel->close(); $conn->close(); Thursday, March 3, 2011
  • 48. Publisher Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $msg = new AMQPMessage($video_info, array('content_type' => 'text/plain', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'video-desc-ex'); $channel->close(); $conn->close(); Thursday, March 3, 2011
  • 49. Publisher Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $msg = new AMQPMessage($video_info, array('content_type' => 'text/plain', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'video-desc-ex'); $channel->close(); $conn->close(); Thursday, March 3, 2011
  • 50. Publisher Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $msg = new AMQPMessage($video_info, array('content_type' => 'text/plain', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'video-desc-ex'); $channel->close(); $conn->close(); Thursday, March 3, 2011
  • 51. Consumer Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $channel->queue_declare('video-desc-queue', false, true, false, false); $channel->queue_bind('video-desc-queue', 'video-desc-ex'); $channel->basic_consume('video-desc-queue', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 52. Consumer Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $channel->queue_declare('video-desc-queue', false, true, false, false); $channel->queue_bind('video-desc-queue', 'video-desc-ex'); $channel->basic_consume('video-desc-queue', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 53. Consumer Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $channel->queue_declare('video-desc-queue', false, true, false, false); $channel->queue_bind('video-desc-queue', 'video-desc-ex'); $channel->basic_consume('video-desc-queue', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 54. Consumer Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $channel->queue_declare('video-desc-queue', false, true, false, false); $channel->queue_bind('video-desc-queue', 'video-desc-ex'); $channel->basic_consume('video-desc-queue', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 55. Consumer Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $channel->queue_declare('video-desc-queue', false, true, false, false); $channel->queue_bind('video-desc-queue', 'video-desc-ex'); $channel->basic_consume('video-desc-queue', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 56. Consumer Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $channel->queue_declare('video-desc-queue', false, true, false, false); $channel->queue_bind('video-desc-queue', 'video-desc-ex'); $channel->basic_consume('video-desc-queue', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 57. Consumer Code $conn = new AMQPConnection(HOST, PORT, USER, PASS, VHOST); $channel = $conn->channel(); $channel->exchange_declare('video-desc-ex', 'direct', false, true, false); $channel->queue_declare('video-desc-queue', false, true, false, false); $channel->queue_bind('video-desc-queue', 'video-desc-ex'); $channel->basic_consume('video-desc-queue', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 58. Scenario Upload Pictures Thursday, March 3, 2011
  • 60. Requirements • Upload Picture Thursday, March 3, 2011
  • 61. Requirements • Upload Picture • Reward User Thursday, March 3, 2011
  • 62. Requirements • Upload Picture • Reward User • Notify User Friends Thursday, March 3, 2011
  • 63. Requirements • Upload Picture • Reward User • Notify User Friends • Resize Picture Thursday, March 3, 2011
  • 64. Requirements • Upload Picture • Reward User • Notify User Friends • Resize Picture • No Code Changes Thursday, March 3, 2011
  • 68. Publisher Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $metadata = json_encode(array( 'image_id' => $image_id, 'user_id' => $user_id, ‘image_path' => $image_path)); $msg = new AMQPMessage($metadata, array('content_type' => 'application/json', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'upload-pictures'); Thursday, March 3, 2011
  • 69. Publisher Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $metadata = json_encode(array( 'image_id' => $image_id, 'user_id' => $user_id, ‘image_path' => $image_path)); $msg = new AMQPMessage($metadata, array('content_type' => 'application/json', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'upload-pictures'); Thursday, March 3, 2011
  • 70. Publisher Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $metadata = json_encode(array( 'image_id' => $image_id, 'user_id' => $user_id, ‘image_path' => $image_path)); $msg = new AMQPMessage($metadata, array('content_type' => 'application/json', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'upload-pictures'); Thursday, March 3, 2011
  • 71. Publisher Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $metadata = json_encode(array( 'image_id' => $image_id, 'user_id' => $user_id, ‘image_path' => $image_path)); $msg = new AMQPMessage($metadata, array('content_type' => 'application/json', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'upload-pictures'); Thursday, March 3, 2011
  • 72. Publisher Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $metadata = json_encode(array( 'image_id' => $image_id, 'user_id' => $user_id, ‘image_path' => $image_path)); $msg = new AMQPMessage($metadata, array('content_type' => 'application/json', 'delivery_mode' => 2)); $channel->basic_publish($msg, 'upload-pictures'); Thursday, March 3, 2011
  • 73. Consumer Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $channel->queue_declare('resize-picture', false, true, false, false); $channel->queue_bind('resize-picture', 'upload-pictures'); $channel->basic_consume('resize-picture', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 74. Consumer Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $channel->queue_declare('resize-picture', false, true, false, false); $channel->queue_bind('resize-picture', 'upload-pictures'); $channel->basic_consume('resize-picture', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 75. Consumer Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $channel->queue_declare('resize-picture', false, true, false, false); $channel->queue_bind('resize-picture', 'upload-pictures'); $channel->basic_consume('resize-picture', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 76. Consumer Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $channel->queue_declare('resize-picture', false, true, false, false); $channel->queue_bind('resize-picture', 'upload-pictures'); $channel->basic_consume('resize-picture', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 77. Consumer Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $channel->queue_declare('resize-picture', false, true, false, false); $channel->queue_bind('resize-picture', 'upload-pictures'); $channel->basic_consume('resize-picture', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 78. Consumer Code $channel->exchange_declare('upload-pictures', 'fanout', false, true, false); $channel->queue_declare('resize-picture', false, true, false, false); $channel->queue_bind('resize-picture', 'upload-pictures'); $channel->basic_consume('resize-picture', $consumer_tag, false, false, false, false, $consumer); while(count($channel->callbacks)) { $channel->wait(); } Thursday, March 3, 2011
  • 79. Consumer Code $consumer = function($msg){ $meta = json_decode($msg->body, true); resize_picture($meta['image_id'], $meta['image_path']); $msg->delivery_info['channel']-> basic_ack($msg->delivery_info['delivery_tag']); }; Thursday, March 3, 2011
  • 80. Consumer Code $consumer = function($msg){ $meta = json_decode($msg->body, true); resize_picture($meta['image_id'], $meta['image_path']); $msg->delivery_info['channel']-> basic_ack($msg->delivery_info['delivery_tag']); }; Thursday, March 3, 2011
  • 81. Consumer Code $consumer = function($msg){ $meta = json_decode($msg->body, true); resize_picture($meta['image_id'], $meta['image_path']); $msg->delivery_info['channel']-> basic_ack($msg->delivery_info['delivery_tag']); }; Thursday, March 3, 2011
  • 82. Consumer Code $consumer = function($msg){ $meta = json_decode($msg->body, true); resize_picture($meta['image_id'], $meta['image_path']); $msg->delivery_info['channel']-> basic_ack($msg->delivery_info['delivery_tag']); }; Thursday, March 3, 2011
  • 83. Consumer Code $consumer = function($msg){ $meta = json_decode($msg->body, true); resize_picture($meta['image_id'], $meta['image_path']); $msg->delivery_info['channel']-> basic_ack($msg->delivery_info['delivery_tag']); }; Thursday, March 3, 2011
  • 84. Scenario Distributed Logging Thursday, March 3, 2011
  • 86. Requirements • Several Web Servers Thursday, March 3, 2011
  • 87. Requirements • Several Web Servers • Logic Separated by Module/Action Thursday, March 3, 2011
  • 88. Requirements • Several Web Servers • Logic Separated by Module/Action • Several Log Levels: Thursday, March 3, 2011
  • 89. Requirements • Several Web Servers • Logic Separated by Module/Action • Several Log Levels: • Info, Warning, Error Thursday, March 3, 2011
  • 90. Requirements • Several Web Servers • Logic Separated by Module/Action • Several Log Levels: • Info, Warning, Error • Add/Remove log listeners at will Thursday, March 3, 2011
  • 96. Publisher Code $channel->exchange_declare('logs', 'topic', false, true, false); $msg = new AMQPMessage('some log message', array('content_type' => 'text/plain')); $channel->basic_publish($msg, 'logs', server1.user.profile.info'); Thursday, March 3, 2011
  • 97. Publisher Code $channel->exchange_declare('logs', 'topic', false, true, false); $msg = new AMQPMessage('some log message', array('content_type' => 'text/plain')); $channel->basic_publish($msg, 'logs', server1.user.profile.info'); Thursday, March 3, 2011
  • 98. Publisher Code $channel->exchange_declare('logs', 'topic', false, true, false); $msg = new AMQPMessage('some log message', array('content_type' => 'text/plain')); $channel->basic_publish($msg, 'logs', server1.user.profile.info'); Thursday, March 3, 2011
  • 99. Publisher Code $channel->exchange_declare('logs', 'topic', false, true, false); $msg = new AMQPMessage('some log message', array('content_type' => 'text/plain')); $channel->basic_publish($msg, 'logs', server1.user.profile.info'); Thursday, March 3, 2011
  • 100. Consumer Code Get messages sent by host: server1 Thursday, March 3, 2011
  • 101. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('server1-logs', false, true, false, false); $channel->queue_bind('server1-logs', 'logs', 'server1.#'); Thursday, March 3, 2011
  • 102. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('server1-logs', false, true, false, false); $channel->queue_bind('server1-logs', 'logs', 'server1.#'); Thursday, March 3, 2011
  • 103. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('server1-logs', false, true, false, false); $channel->queue_bind('server1-logs', 'logs', 'server1.#'); Thursday, March 3, 2011
  • 104. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('server1-logs', false, true, false, false); $channel->queue_bind('server1-logs', 'logs', 'server1.#'); Thursday, March 3, 2011
  • 105. Consumer Code Get all error messages Thursday, March 3, 2011
  • 106. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('error-logs', false, true, false, false); $channel->queue_bind('error-logs', 'logs', '#.error'); Thursday, March 3, 2011
  • 107. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('error-logs', false, true, false, false); $channel->queue_bind('error-logs', 'logs', '#.error'); Thursday, March 3, 2011
  • 108. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('error-logs', false, true, false, false); $channel->queue_bind('error-logs', 'logs', '#.error'); Thursday, March 3, 2011
  • 109. Consumer Code $channel->exchange_declare('logs', 'topic', false, true, false); $channel->queue_declare('error-logs', false, true, false, false); $channel->queue_bind('error-logs', 'logs', '#.error'); Thursday, March 3, 2011
  • 112. RabbitMQ Bundle Goal: To be easy to use Thursday, March 3, 2011
  • 113. RabbitMQ Bundle Publish a Message: $msg = array('user_id' => 1235, 'image_path' => '/path/to/new/ pic.png'); $this->get('rabbitmq.upload_picture_producer')-> publish(serialize($msg)); Thursday, March 3, 2011
  • 114. RabbitMQ Bundle Consume a Message: $ ./app/console_dev rabbitmq:consumer -m 1 upload_picture Thursday, March 3, 2011
  • 115. RabbitMQ Bundle Consume 50 Messages: $ ./app/console_dev rabbitmq:consumer -m 50 upload_picture Thursday, March 3, 2011
  • 116. RabbitMQ Bundle Consume infinite* Messages: $ ./app/console_dev rabbitmq:consumer -m -1 upload_picture *messages may not be infinite Thursday, March 3, 2011
  • 117. RabbitMQ Bundle Configuration: # app/config/config.yml rabbitmq.config: connections: default: host: 'localhost' port: 5672 user: 'guest' password: 'guest' vhost: '/' Thursday, March 3, 2011
  • 118. RabbitMQ Bundle Configuration: # app/config/config.yml rabbitmq.config: connections: ... producers: upload_picture: connection: default exchange_options: {name: 'upload-picture', type: direct} Thursday, March 3, 2011
  • 119. RabbitMQ Bundle Configuration: # app/config/config.yml rabbitmq.config: connections: ... consumers: upload_picture: connection: default exchange_options: {name: 'upload-picture', type: direct} queue_options: {name: 'upload-picture'} callback: upload_picture_service Thursday, March 3, 2011
  • 120. RabbitMQ Bundle Using a Producer: public function indexAction($name) { ... $msg = array('user_id' => 1235, 'image_path' => '/path/to/new/pic.png'); $this->get('rabbitmq.upload_picture_producer')-> publish(serialize($msg)); ... } Thursday, March 3, 2011
  • 121. RabbitMQ Bundle Consumer Class: class UploadPictureConsumer extends ContainerAware implements ConsumerInterface { public function execute($msg) { // Process picture upload. // $msg will be what was published // from the Controller. } } Thursday, March 3, 2011
  • 122. RabbitMQ Bundle Recap: Thursday, March 3, 2011
  • 123. RabbitMQ Bundle Recap: • Add an entry for the consumer/producer in the configuration. Thursday, March 3, 2011
  • 124. RabbitMQ Bundle Recap: • Add an entry for the consumer/producer in the configuration. • Implement your Callback. Thursday, March 3, 2011
  • 125. RabbitMQ Bundle Recap: • Add an entry for the consumer/producer in the configuration. • Implement your Callback. • Start the consumer from the CLI. Thursday, March 3, 2011
  • 126. RabbitMQ Bundle Recap: • Add an entry for the consumer/producer in the configuration. • Implement your Callback. • Start the consumer from the CLI. • Add code to publish messages. Thursday, March 3, 2011
  • 127. RabbitMQ Bundle There’s more: Thursday, March 3, 2011
  • 128. RabbitMQ Bundle There’s more: • RPC clients and servers Thursday, March 3, 2011
  • 129. RabbitMQ Bundle There’s more: • RPC clients and servers • Anonymous consumers Thursday, March 3, 2011
  • 130. RabbitMQ Bundle There’s more: • RPC clients and servers • Anonymous consumers • Parallel RPC Thursday, March 3, 2011
  • 131. RabbitMQ Bundle Fork it at http://github.com/videlalvaro/RabbitMqBundle Thursday, March 3, 2011
  • 133. RabbitMQ • Enterprise Messaging System • Open Source MPL • Written in Erlang/OTP • Commercial Support Thursday, March 3, 2011
  • 134. Features • Reliable and High Scalable • Easy To install • Easy To Cluster • Runs on: Windows, Solaris, Linux, OSX • AMQP 0.8 - 0.9.1 Thursday, March 3, 2011
  • 135. Client Libraries • Java • .NET/C# • Erlang • Ruby, Python, PHP, Perl, AS3, Lisp, Scala, Clojure, Haskell Thursday, March 3, 2011
  • 136. Docs/Support • http://www.rabbitmq.com/documentation.html • http://dev.rabbitmq.com/wiki/ • #rabbitmq at irc.freenode.net • http://www.rabbitmq.com/email-archive.html Thursday, March 3, 2011
  • 137. One Setup for HA Thursday, March 3, 2011
  • 139. Conclusion • Flexibility Thursday, March 3, 2011
  • 140. Conclusion • Flexibility • Scalability Thursday, March 3, 2011
  • 141. Conclusion • Flexibility • Scalability • Interoperability Thursday, March 3, 2011
  • 142. Conclusion • Flexibility • Scalability • Interoperability • Reduce Ops Thursday, March 3, 2011
  • 144. Thanks! Álvaro Videla http://twitter.com/old_sound http://github.com/videlalvaro http://github.com/tnc http://www.slideshare.net/old_sound Thursday, March 3, 2011