I am wondering how to create my own SOA style messaging system, similar to JMS (Java Messaging System).
The MOM (Messaging Oriented Middleware) needs to store messages in a single database, but may be processed by more than one service for scalability and failover.
I have defined a rudimentary Messages table as follows:
- MessageId int
- CreateTimeStamp datetime
- DeliveredTimeStamp datetime
- Payload varchar(max)
- Expiration datetime
- RetryCount int
- CorrelationId int
- State int (1-Waiting, 2-Processing, 3-Sent, 4-Retry, 5-failed)
- *ProcessIdLock int - This is the process id of the messaging service that is processing the message
The problem is, idemptency issues aside, how to I ensure that one service processes each message at a time?
I was thinking about a scheme like this:
Perform record locking: UPDATE Messages SET ProcessIdLock = MessageProcessorId, SET State = 2 -- Processing WHERE MessageId IN ( SELECT TOP 10 MessageId FROM Messages WHERE Expiration < GETTIME() + CreateTimeStamp AND State = 1 -- Waiting OR State = 3 -- Retry )
The above step will get up to 10 messages to process by a single service at a time
Get the locked records: SELECT Payload FROM Messages WHERE State = 2 -- Processing AND ProcessIdLock = MessageProcessorId
Update the status for each message processed: UPDATE Messages
SET State = (Pass, Fail, or Retry), SET DeliveredTimeStamp = GETDATE() -- Pass only WHERE MessageId = ProcessedMessageId
Note: Another problem I have is that some messaged are broadcast to several clients grouped by id (such that, there may be 100 total clients, but each client group will consist of 10 or less).
For example, what happens if there are 5 clients in a group, but 2 clients are currently disconnected? I would like to sent that message to those clients as they come back up.
One client may reconnect (and should get the message), while the other client may not reconnect (so the message will be dropped after message Expiration).
Thank you for reading this. Seems like a typical enterprise problem to me. Would MSMQ be the best solution? I am new to MSMQ, are MSMQ messages persisted in storage or kept in memory?