RabbitMQ in WCF Web Service, Using Model and Performance

I need to call the RabbitMQ RPC service from a C # WCF web service hosted in IIS. We are working fine, but as a good little soldier, I read the RabbitMQ client documentation and it states the following "IModel should not be shared between threads . "

I understand that in RabbitMQ, the IModel is actually a socket connection. this means that for each call, the WCF service forces it to create an IModel and delete it after completion.

It seems to me that I'm somewhat excessive in performance and use of sockets, and I'm wondering if my understanding is really correct or if there are other options available, such as using the connection pool for IModels between threads.

Any suggestions would be greatly appreciated. Here is the sample code that I use below, the rabbitMQ connection is actually initialized in Global.asax, I just see it there, you can see the usage.

var connectionFactory = new ConnectionFactory(); connectionFactory.HostName = "SampleHostName"; connectionFactory.UserName = "SampleUserName"; connectionFactory.Password = "SamplePassword"; IConnection connection = connectionFactory.CreateConnection(); // Code below is what we actually have in the service method. var model = connection.CreateModel(); using (model) { model.ExchangeDeclare("SampleExchangeName", ExchangeType.Direct, false); model.QueueDeclare("SampleQueueName", false, false, false, null); model.QueueBind("SampleQueueName", "SampleExchangeName", "routingKey" , null); // Do stuff, like post messages to queues } 
+4
source share
2 answers

IModel is actually a socket connection

This is not true. IConnection is a connection :) A model has been introduced to allow multiple clients to use the same tcp connection. Thus, the model is a “logical” connection in the “physical”.

One of the tasks the Model does is to split and reassemble large messages. If the message exceeds a certain size, it is divided into frames, frames are marked and collected back by the recipient. Now imagine that 2 threads are sending large messages ... Frame numbers will be corrupted, and you will get a Frankenstein message consisting of random parts of 2 messages.

You are right in believing that creating a model has some value. The client sends a request to the server to create the model, the server creates a structure in memory for this model and sends the model identifier back to the client. This is done by connecting tcp, which is already open, so there is no overhead due to the connection being established. But still there is overhead due to the trip in both directions.

I'm not sure about the WCF binding, but the rabbit.net base library does not provide any association for models. If this is a problem in your case, you will have to come up with something.

+3
source

For each session, you need one IModel object. This is pretty normal for network APIs. For example, the Azure Table Storage client is exactly the same. Why, well, you cannot have a single channel with several parallel communication flows passing through them.

I expect a certain level of caching (like DNS) to happen, which will reduce the overhead of creating subsequent IModel instances.

Performance is good when you do the same with Azure tables, so it should be great with IModel. Just try to optimize this when you can prove that you have a real need.

+1
source

All Articles