Search code examples
wcftriggersconcurrent-collections

C# ConcurrentQueue - raise event when Enqueue happens?


I have a WCF service that is hosted in a Windows Service.

The WCF service is injected with a ConcurrentQueue<SomeClass>.

The Windows Service (that hosts the WCF service) is also injected with the ConcurrentQueue<SomeClass>.

The Windows Service starts the WCF service, and also spawns a worker thread.

The worker thread pushes (Enqueue) objects of SomeClass to the ConccurrentQueue.

I would like somehow for the WCF Service to be triggered when an object is enqueued to the ConcurrentQueue so that it could dequeue it (and any other object that might be in the queue), and send a message to all connected clients.

.

TWO QUESTIONS :

  1. How do I make the WCF service 'hook' on the 'Enqueue' method of the injected ConccurentQueue, so that when objects are pushed into the queue - the WCF service will do something about it ?

  2. If I do manage to somehow hook the 'Enqueue' event, and now the worker thread in the Windows Service has enqueued two objects into the queue - that means that it would also 'trigger' the WCF service's 'Enqueue hook' twice - will those two triggered events happen in different threads ? I need to somehow make sure that the WCF service pulls the objects from the queue in order. I do not want to suddenly see that for every Enqueue operation - the WCF service triggers in a seperate thread and pulls objects out ...

I hope my questions are clear enough ...

.

[Update]

After a chat with Chris, I have come to the conclusion that the best way to go at this would be to seperate the worker thread from the WCF service, and make the worker thread call the WCF service as a client. This means that I don't have to play around with the queue.


Solution

  • Wrap the ConcurrentQueue in a simple class that exposes Enqueue & Dequeue calls, then place your hook inside of this class. Whenever YourClass.Enqueue is called, trigger the WCF activity, which can call YourClass.Dequeue. YourClass.Dequeue will drain the queue & place it into an ordered enumerable that the WCF service can then process in order.