Transactional BatchQueue?

Transactional BatchQueue?

Old forum URL: forums.lhotka.net/forums/t/566.aspx


DavidG posted on Friday, July 07, 2006

Hello,

I understand that the BatchQueue has not been brought forward into CSLA 2.0, but I'm wondering if I can still get some help with it?

Basically, I am combining some database updates with adding jobs to the queue and would like to know if (or how to make) the queue transactional. Or am I just going to have to talk to MSMQ directly?

My (pseudo)code is something like this:

[Transactional()]
protected override void DataPortal_Update()
{
    foreach(Child item in BusinessCollectionBase)
    {
          item.property = value;

          BatchQueue.Submit(BatchJob);
    }

    BusinessCollectionBase.Save();
}

Therefore if the BusinessCollectionBase.Save() fails for some reason, I want the BatchJobs to be rolled back as well. I know that MSMQ is transactional, but it doesn't look like the BatchQueue would support that, or does it? If not, does anybody have an idea how to implement it?

Thanks,

David

RockfordLhotka replied on Friday, July 07, 2006

To do this you'll have to alter the batchqueue code itself so it starts the transaction before reading the work item from the queue. In general, this should work, as long as the transaction type you use when reading from the queue is the same as what your object uses - and that has to be EnterpriseServices, because that's the only transaction monitor that supports MSMQ.

The deeper problem is what to do in the case of failure? Just putting the item back in the queue almost certainly means it will be retried immediately, and will fail - blocking your queue processor into an infinite loop. Ugly.

So what you need to do instead, is what COM+ does with Queued Messaging; which means that in the case of failure you move the queued item to another queue that has a different retry schedule. Look at Microsoft's docs for Queued Messaging for more details on what they do.

DavidG replied on Friday, July 07, 2006

Thanks for the quick reply Rocky!

I agree with the points you make in the reply, however they seem to be in the context of processing (receiving) the items from the queue. What my question really is though it how to rollback the submitting of items to the queue. I'm thinking it's not possible using the BatchQueue and will need talk to MSMQ directly. If I understand how it works correctly, the messages won't be sent to the queue until my distributed transaction commits, which is exactly what I want.

RockfordLhotka replied on Friday, July 07, 2006

Ahh, I see.
 
You'll still need to do some work. The queue has to be transactional for this to work - and the code currently creates simple queues. You'll have to change the code to create a transactional queue instead (I don't know how much work that is, sorry...)
 
Once the queue is transactional, then it should be the case that, as long as your code that submits the job is in a COM+ transaction, the submission will be done transactionally. In other words, the _client_ can't submit the job - the job has to be submitted on the app server within a DataPortal_XYZ method that is transactional. That way your code is running in a COM+ transaction, and the submission will get rolled into that same transaction.
 
Rocky


From: DavidG [mailto:cslanet@lhotka.net]
Sent: Friday, July 07, 2006 1:19 PM
To: rocky@lhotka.net
Subject: Re: [CSLA .NET] Transactional BatchQueue?

Thanks for the quick reply Rocky!

I agree with the points you make in the reply, however they seem to be in the context of processing (receiving) the items from the queue. What my question really is though it how to rollback the submitting of items to the queue. I'm thinking it's not possible using the BatchQueue and will need talk to MSMQ directly. If I understand how it works correctly, the messages won't be sent to the queue until my distributed transaction commits, which is exactly what I want.



Copyright (c) Marimer LLC