Our connectivity to EMS code was initially ill-designed and created one TopicConnection object per topic that we listened to. So, in effect, whenever we subscribed to a topic, we create a new connection, a new session and, lastly, a new listener.
We would like to switch to a single connection model. Although I am able to do this easily in our code by sharing one connection object and creating a new session object per topic, we are unsure whether this is going to cause any issues without code.
My understanding is that the Tibco EMS client library is thread safe with regards to sharing a connection. In effect, a connection is just a pipe and the sessions can resuse the this pipe in a thread safe manner.
Is this assumption correct or is there more to this?
The .NET EMS API is based on JMS. In JMS, the Connection and Session objects are specified to be thread-safe and can be reused within the program. You are quite correct in that the Connection object simply represent a network pipe to the EMS server. The EMS User's Guide states:
A connection is a fairly heavyweight object, so most clients will create a connection once and keep it open until the client exits. Your application can create multiple connections, if necessary.
And regarding sessions:
A Session is a single-threaded context for producing or consuming messages. You create Message Producers or Message Consumers using Session objects.
Essentially, unless you need very large volumes and are bumping into performance limitations, it's perfectly safe to use just one connection in your application. The session controls the transaction/acknowledgement semantics of any producers or consumers created within, but is again safe to reuse. I would probably use separate sessions for modules exist within the application with distinct life cycles (think separate deployment units within an application server).
Your EMS server installation will contain a samples directory with various code (something like C:\tibco\ems\5.0\samples\cs). The code in csTopicSubscriber.cs shows how to write a single-threaded topic consumer. There is no multi-threaded topic consumer example but csMsgConsumerPerf.cs demonstrates how to do it with queues.
Be sure to clean up any objects you create after you're done with them - e.g. close the topic consumer object, the session, and the connection when you're finished. Leaking handles without closing them can result in unpredictable behaviour when combined with prefetch and fault-tolerant reconnect settings.
I think yes as long as sharing is within the same application (exe, binary).
We have shared same connection object, and used it as a singleton in our code.
Agree with an earlier answer: the JMS Session must not be shared between threads, but the Connection can/should be. So one connection per application is ok (make sure you start/close it only once - best before/after the individual threads creation).
And then create and use one Session per thread. Remember that when you close() a Session, it will block until all receive callbacks have really returned. So do NOT call close() from within a callback's onMessage().
Related
I have a SQL server database with 200 concurrent users limitation. I want to keep the first connection created by any user opened and use it with all other users through my C# Web API. Is that possible?
SqlConnection is not intended to be used concurrently, so to do what you want would mean synchronizing all access, especially if there are transactions involved, or anything involving temporary tables that live longer than a single command. It can be done, but it isn't a good idea.
Note that SqlConnection is disposable, and when disposed: the underlying connection (that you never see) usually goes back to a pool. If you use consecutively (not concurrently) 200 SqlConnection instances, you might have only used a single underlying connection.
If you must put a hard limit on your concurrent connections, you'll have to create your own pool (which might be a pool of one), with your own synchronization code while you lease and release connections. But: it won't be trivial.
I'm writing code that will be publishing messages from multiple threads to an Azure Event Hub in C# using the EventHubClient. The documentation for EventHubClient contains the fairly standard boiler plate.
"Any public static (Shared in Visual Basic) members of this type are
thread safe. Any instance members are not guaranteed to be thread
safe."
There is no additional documentation as to thread safety in any of the four send
methods I would most expect to be thread safe. Were I to believe that the send methods are not threadsafe then I would end up creating a new EventHubClient instance each time I wished to send to a message. Since the underlying tcp connection is apparently reused unless steps are taken this may not have too much overhead. Similar issues arise with partitioned senders though given that there is an async method to create one, they might well have their own AMQP connection.
Are some, if not all, instance methods of EventHubClient thread safe despite the documentation?
And for any Azure folks would it be possible to have this clarified in the documentation? This sort of documentation issue (assuming it is wrong as seems likely) appears to affect Azure Table as well and is generally common within the MSDN docs. With regards to EventHub this is in contrast to the clear thread safety statement of Kafka and AWS Kinesis at least does not explicitly label everything as unsafe. I did not find EventHubs in the open source portion of the SDK so could not check myself.
TLDR:
All critical runtime operations (aka data-plane) in the .NET SDK are thread-safe.
Create EventHubClient object once and re-use
The Story
ServiceBus SDK exposes two patterns to create senders:
Basic
Advanced
For Basic version - developer will directly use EventHubClient.CreateFromConnectionString() API and doesn't worry about managing MessagingFactory objects (connection gu's). SDK will handle reusing the MessagingFactory across all EventHubClient instances as long as the connection string is same - a literal match of all keys and values - is done in the SDK for this reuse.
For an Advanced developer who will need a bit more control at connection level, SB SDK provides MessagingFactory.CreateFromConnectionString() and from this developer can create the EventHubClient instance.
All instance methods of EventHubClient - to send to EventHubs are strictly thread-safe. In general, all data-plane operations are...
However, while reading from EventHubs, API is optimized for, this pattern.
while(true) {
var events = eventHubPartitionReceiver.receive(100);
processMyEvents(events);
}
So, for ex: properties like, EventHubReceiver.RuntimeInformation - is populated after every receive call without any synchronization. So, even though the actual receive API is thread-safe - the subsequent call to RuntimeInformation isn't - as it is rare for anyone to park multiple receive calls on an instance of PartitionReceiver.
Creating a new instance of EventHubClient in each component to start send messages is the default pattern - and the ServiceBus SDK will take care of reusing the underlying MessagingFactory - which reuses the same physical socket (if the connection string is same).
If you are looking for real high throughput scenarios then you should design a strategy to create multiple MessagingFactory objects and then Create an EventHubClient each. However - make sure that you have already increased the Thruput units for your EventHub on the Portal before trying this as the default is just 1 MBPS - cumulative of all 16 partitions.
Also, if the Send pattern you are using is Partitioned Senders - they all will also use the same underlying MessagingFactory - if you create all Senders from the same eventHubClient(.CreatePartitionedSender()) instance.
This question is related to my old question .
1) I have a vb.net application which requires connections to some databases.So now if i open multiple instance of same application(exe files) then it uses different connection or uses multiple connection. So can i make it to use single connection?
2) I heard about Appdomain(An AppDomain provides a layer of isolation within a process) . Does it help in making the connection to be drawn from same pool and make optimal use of resources?
This article has something related to it.
Different processes (your case #1) do not (and cannot) share database connections, each connection is unique to the process.
I do not know whether connection pools are per process or per-appdomain.1 But it is unlikely to make much difference. The model that you should be aiming for is to create, use and then close connections around each functional database operation. Do not try and keep them open, rather try and keep them closed. This maximises the re-use opportunities for re-use.
Unless you have a particular will a few excess connections over what is theoretically needed the default pooling while avoiding holding connections open will just work.
1 As connections are reset before being returned from the pool it would be rather hard to determine which of these is the case. Perhaps a test program that had one app domain open, use and close one connection before another app domain repeated the process and see if one or two connections to the database were established.
Each AppDomain would have its own Connection Pool, so no I don't think using AppDomains would help in your case.
We have a 3rd party piece of software that uses a bunch of internal middleware and services to connect to outside databases. Through this API I only have a bit of information on the connection object it uses when contacting an Oracle DB.
Update: This isn't a pooling to connect to Oracle. This is a pool of objects/connections to a piece of software that deal with massive amounts of statistical data which in turn has it's own connections to Oracle. The reason we need pooling is this software can be accessed 50-200 times a second, and it can takes over 20 seconds to instantiate the Initiate object.
What I'm wondering is if .NET has any classes I can inherit / use to help me build a better object pooling system than what is currently written. I have no problem writing my own, but I'd rather not re-invent the wheel if I could inherit from one.
Note, this is pretty much object pooling, but the objects have the ability to connect.
Update:
The current system works once the pool is created. It has a worker thread that ensures the pool is clean and working. The problem comes in when the Application gets no activity for a long time. When a request comes in, the system looks for a connection and they're all cleaned up (I believe because the cache is gone). So it regenerates them, but this can take upwards of 1 minute to do the 100+ connections, and the request can time out due to this being accessed through SOA.
You can implement your own using Object Pool Design pattern:
http://sourcemaking.com/design_patterns/object_pool
or use this one:
C# Object Pooling Pattern implementation
I have a multi-threaded application which communicates with a server over a TCP connection. The application would be deployed as a windows service.
The way it has been implemeted is, there is Controller which creates Communicator objects, assigns the port number, message count etc. properties to the Communicator and invokes its StartClient method to commence the dialog with the server.
Within the StartClient method, each Communicator object creates a connection to the server, using the port number and url specified by the Controller. After establishing the connection, it internally creates a thread and calls the ReadMessages method which keeps reading from the server till the message count is met and then gets closed down.
Based on the runtime conditions, there might be a need to reuse the Communicator object to talk with the server again and hence, the ReadMessages method woudl be called again.
Initially, we had been calling Dispose() method for the NetworkStream, StreamReader and StreamWriter objects when the ReadMessages method completed, but with the reconnecting scenario, it used to throw "Cannot access a disposed object" error. So, we commented out the Dispose method call for testing.
As of now, it works fine, but I am concerned that, this isnt the best way to achieve this functionlity as I am not disposing the objects ever.
I was thinking in terms of object pooling, If it is possible to have a pool of Stream objects which could be reused by different threads?
One way to tackle this can be to create a new instance of Stream objects each time the Communicator connects with the server, but I think that would be an expensive operation.
Can you please help me identify a better approach to handle the situation here so that I can reuse the Communicator object without a performance hit?
The approach will be based on how frequently you need to read messages - if its occasional the n, I would recommend that you re-factor your communicator object to make "ReadMessages" operation atomic - i.e. it would connect to the server, create network stream, read messages and then dispose every thing.