RabbitMQ Flashcards
What are the alternatives to RabbitMQ
ActiveMQ
Kafka
zeroMQ
Qpid
Why RabbitMQ
- RabbitMQ Supports AMQP, STOMP and MQTT protocols.
- Clustering is very simple because of Erlang
- Far more reliable and crash resistant than its competitors
- Very easy to install and use
How do producers/consumers connect to RabbitMQ?
They connect to RabbitMQ by creating a TCP connection. An AMQP channel is created once the TCP connection is open. This channel is virtual connection inside real TCP connection, and all AMQP commands are sent over this channel. Each channel is assigned a unique ID. Multiple channels can be opened on a single TCP connection.
How message is routed between consumers and producers?
There are three parts to any successful routing of AMQP messages – exchange, queue and binding.
Exchanges are where producers publish their message, queues are where messages end up & received by consumers and bindings are how messages are routed from exchange to queues.
How rabbitMQ queue works?
Queues are like named mail-box. They are where messages end up and wait to be consumed. Consumers receive messages from a queue in one of two ways –
• Push model: Consumers automatically receive messages as they arrive in the queue. (Basic.Consume)
• Pull model: Consumers requests a single message from queue. Once that is processed, the next message is requested by the consumer. (Basic.Get)
If multiple consumers have subscribed to the queue, they are served in round-robin fashion. Each message is sent to only one consumer subscribed to the queue. A message is removed from queue on successful acknowledgement from the consumer. Consumer can acknowledge using basic.ack command or by setting auto_ack parameter to true when it subscribes to the queue. If acknowledgement is not received, then RabbitMQ sends the message to next subscriber. The consumer can reject a message either by disconnecting from RabbitMQ server without acknowledging the message or call basic.reject command. If requeue parameter of reject command is set to true, RabbitMQ will redeliver the message to next subscribed consumer. You can also discard a message by simply acknowledging it.
What are important properties of a queue
Important properties of queue are
• Name – name used by consumer to subscribe to it. If not specified RabbitMQ will generate some random name.
• Exclusive – Private queue that can only be consumed by your application
• Auto-delete – automatically deleted when the last consumer unsubscribes. If you need a temporay queue used by only one consumer, combine auto-delete with exclusive. When consumer disconnects, the queue will be deleted
• x-expires: Queue is removed after specified number of miliseconds
• x-max-length: Maximum message count for a queue
• x-message-ttl: Message expiration in milliseconds.
What happens if message is published into an exchange but queue is not declared at that time?
Message that get published into exchange but have no queue to be routed to are discarded by rabbit. So, if you cannot afford your messages to be black holed, both producer and consumer should attempt to create the queue.
How can you load balance message processing in multiple consumers
Queues are fundamental block of AMQP messaging. They are perfect for load balancing. Just attach a bunch of consumers and let RabbitMQ round-robin incoming messages evenly among them.
What are different types of queues
- Temporary queues – Queues are deleted when the last consumer disconnect. (auto_delete = True)
- Exclusive – Only a single consumer can access the queue. Automatically deleted when the channel that queue was created on is closed.
- Expiring – Automatically expiring queues means queues are deleted if it is unused for some length of time. ‘x-expires’ argument used while declaring the queue.
- Permanent - Permanent queues persist across server restart. Queue durability is different than message durability. The messages can be auto expired using “expires” attributes set in the message properties. ‘x-message-ttl’ setting of queue enforces maximum age for all the messages in the queue. ‘x-max-length’ argument specifies maximum length of the queue. If this capacity is reached, RabbitMQ will drop messages from front of queue as new messages are added.
How does a message reach a queue
A message is sent to exchange by publisher. Message has payload and routing key. A queue when created is bound to an exchange by routing keys. Message routing key is matched against the queue binding (i.e. routing key specified by the queue) and message is delivered to the queue whose binding matches. So, the broker routes messages from exchange to queues based on routing keys.
What is direct exchange
Direct exchange is used to deliver messages to specific targets. It uses string equality when checking the bindings with routing keys, no pattern matching (like regular expressions) are supported. Multiple queues can be bound to the direct exchange. There is a default direct exchange which has empty string as its name. When a queue is declared, it will bind to this default exchange.
Send a message to the default exchange
Channel.basic_publish($msg, ‘’, ‘queue_name’)
Declare your own exchange if default is not enough. It’s a good choice for routing RPC reply messages.
What is fanout exchange
Message sent to fanout exchange will be delivered to all the queues attached to it. RabbitMQ does not evaluate routing keys associated with messages as all are delivered to all the queues.
What is topic exchange
Route Message to any queue bound with matching routing key. A message can be sent to multiple queues.
Channel.basic_publish($msg, ‘logs_exchange’, ‘error.msg-inbox’)
Channel.queue_bind(‘msg-inbox-errors’, ‘logs_exchange’, ‘error.msg-inbox)
In above example, message is published to ‘logs_exchange’ with routing key as ‘error.msg-inbox’. It will get delivered to the queue ‘msg-inbox-errors’ since this queue is bound to the same ‘logs_exchange’ and the queue binding ‘error.msg-inbox’ matches the routing key of the published message.
This behavior is so far like direct exchange. But if you declare additional queue like
Channel.queue_bind(‘all-logs’, ‘logs_exchange’, ‘#’)
Then all the messages sent to logs_exchange will be sent to ‘all-logs’ queue. # indicates match-all. You can use wild cards in the queue binding. For example
Channel.queue_bind(‘inbox-logs’, ‘logs_exchange’, ‘*.msg-inbox)
All the messages whose routing key matches ‘*.msg-inbox’ would be sent to ‘inbox-logs’ queue. Here * means all characters and . acts as a separator.
Namespaced (combinations of dots in the name of the key) routing key is a good choice for future proofing an application. Topic exchange can emulate behavior of both direct and fanout exchange. Direct using full routing keys instead of pattern matching and fanout using # routing keys.
If an exchange is declared with ‘auto-delete’ set to true, then that exchange would be automatically deleted when the last consumer connected to it is disconnected.
what is exchange to exchange routing
This is supported using Exchange.Bind rpc command.
What is consistent hashing exchange
Distribute messages to queues on different physical servers