Using Rabbitmq DefaultConsumer channel to publish - rabbitmq

DefaultConsumer has a channel that it binds to and can be acquired with getChannel(). Can I use this channel in handleDelivery to publish something to another queue or should I create a new factory+connection+channel trifecta and use that to publish? I want to publish an event to another queue when consumer consumes an event from it's queue, just not sure if the consumer channel can be re-used for publishing and if it is safe to do.

The best practice is to use different channels
you should no use the same channel to consume and publish

Related

Publish same message to different queues in RabbitMQ using Masstransit

any body can help me finding how can I send the message to differents queues (depending on business logic) to differents queues in RabbitMQ, using Masstransit
I have read the documentation I didn't found how I can specify the queue destination name
thank you
You might want to read the documentation again. If you want to send to a specific queue, you actually have to send to the exchange for that queue created by MassTransit.
Use the ISendEndpointProvider (or ConsumeContext):
Call await GetSendEndpoint(new Uri("exchange:name")) or await GetSendEndpoint(new Uri("queue:name")) to get the ISendEndpoint.
Call Send(...) to send the message to the exchange or queue.

spring-RabbitMQ manually listen to queue

I'm new in rabbitmq.I'm using spring-amqp to implement the feature.
As we know spring provide #RabbitListener to register a listener to queue when the app initialization.
I want to design a function when I click some button, a new consumer will be created and listen to a specified queue.
Java base provide channel.basicConsume() method to consume a queue.
Is spring provide such function ?
I want to implement like :
producer keep sending messages to a fanout exchange.
when a consume wants to join, call function1 -> create queue and binding to exchange -> consume messages.
when a consume wants leave, call function2 -> disconnect
There are a few options.
Use one of the RabbitTemplate.receive() or convertAndReceive() methods to get messages one-at-a-time, you can set a receiveTimeout in case there are no messages.
RabbitTemplate.execute() with a callback that gets a channel that you can call basicConsume() on. This is a lower-level option and won't do any conversion for you.
Create a SimpleMessageListenerContainer (or DirectMessageListenerContainer) dynamically and start/stop it as needed.
...
In all cases, you can use a RabbitAdmin to create/bind the queue, for all except option 1, it would probably an auto-delete queue that will be removed when the consumer is cancelled. With option 1, you would have to use a non-auto-delete queue and remove it with the RabbitAdmin.
I would suggest that #3 is the most efficient using pure Spring AMQP.
You could also use Spring Integration with an inbound channel adapter and a publish-subscribe channel; that way you only need one queue (per application instance) and then subscribe a new MessageHandler to the channel for each user.

API design around RabbitMQ for publisher/subscriber

TL;DR - Whats the best way to expose RabbitMQ to a consumer via REST API?
I'm creating an API to publish and consume message from RabbitMQ. In my current design, the publisher is going to make a POST request. My API will route the POST request to the exchange. In this way, the publisher doesn't have to know the server address, exchange name etc. while publishing.
Now the consumer part is where I'm not sure how to proceed.
At the beginning there will be no queues. When a new consumer wants to subscribe to a TOPIC, then I will create a queue and bind it to the exchange. I need help with answers to few questions -
Once I create a queue for the consumer, what's the next step to let the consumer get messages from that queue?
I make the consumer ask for a batch of messages(say 50 messages) from the queue. Then once I receive an ack from the consumer I will send the next 50 messages from queue. If I don't receive an ack I will requeue the 50 messages back into the queue. Isn't this expensive in terms of opening and closing connection between the consumer and my API?
If there is a better approach then please suggest
In general, your idea of putting RMQ behind a REST API is a good one. You don't want to expose RMQ to the world, directly.
For the specific questions:
Once I create a queue for the consumer, what's the next step to let the consumer get messages from that queue?
Have you read the tutorials? I would start there, for the language you are working with: http://www.rabbitmq.com/getstarted.html
Isn't this expensive in terms of opening and closing connection between the consumer and my API?
Don't open and close connections for each batch of messages.
Your application instance (the "consumer" app) should have a single connection. That connection stays open as long as you need it - across as many calls to RabbitMQ as you want.
I typically open my RMQ connection as soon as the app starts, and I leave it open until the app shuts down.
Within the consumer app, using that one single connection, you will create multiple channels through the connection. A channel is where the actual work is done.
Depending on your language, you will have a single channel per thread; a single channel per queue being consumed; etc
You can create and destroy channels very quickly, unlike connections.
More specifically with your idea of batch processing, this will be handled by putting a consumer prefetch limit on your consumer and then requiring messages to be acknowledged after processing it.

Invoking publish inside a deliver handler rabbitmq

Suppose I have a queue 'Q1' and there is are multiple producers publishing to this queue and multiple consumers reading from this queue.
Now, each consumer will process the message from 'Q1' and again put it in some other queue say 'Q2'/'Q3'.
How should be the channels assocaited with it? I have created a single producer channel which will publish to any queue(Q1 and Q2/Q3) and multiple consumer channels. Is it ok to work with a single producer channel or there would be some synchronization issues?
Generally the best practice is to have a channel for thread.
In case you use the same channel with more threads you should synchronize the access, there are client implementation that do it for you.
Now, if you use a single channel to publish to more queues is fine, but it should be serialized.
if you are looking for performance is better to have multi-threading publishers where each thread has his own channel.
The channel creation is very "cheap" in term of resource, so don't be afraid to use more channels.
The question is a bit generic, I hope it helps

NServiceBus queue concept

Just started learning NServiceBus and trying to understand the concept.
When it talks about queues, are we talking about MSMQs on both publisher and subscriber?
So, if I have an application that generates a list of something (say, name of animals), then it dumps the list into publisher’s queue. The publisher polls the queue every minute and if there is something in the queue, it will publish to subscriber’s queue for further processing. Does this make sense?
Thanks.
The sequence of events for a publish is as follows:
The Publisher will start up(Windows Service)
A Subscriber will start up and place a message into the Publisher's input queue(MSMQ)
The Publisher will take that message, read the address of the Subscriber and place that into storage(subscription storage: memory, MSMQ, or RDBMS)
When it is time to publish and event, the Publisher will inspect the type of message and then read subscription storage to find Subscribers interested in that message
The Publisher will then send a message to each of the Subscribers found in subscription storage
The Subscriber receives the message in its input queue(MSMQ) and processes it
You can leverage other messaging platforms instead of MSMQ, but MSMQ is the default. There really is no polling done, all the endpoints are signaled when a message hits the queues.
MSMQ is a transport layer. It passes the messages around.
The application will publish something using a NServiceBus queue. If you configured it to use MSMQ, that's what it will use for its transport layer and this is what the subscribers will be looking at.
NServiceBus follows the publisher/subscriber model as you have correctly stated. However your confusion is based on the use of two queues. This is incorrect. The server (publisher) will maintain the queue which is interfaced via the MSMQ protocol and so your application would communicate directly with this possibly remotely or locally.
You would typically use a WCF service which would raise an event upon a new message being pushed onto the queue. Your application can then make use of this new message as desired. See the NServiceBus documentation for examples: http://www.nservicebus.com/ArchitecturalPrinciples.aspx