oops...nice catch
On Jun 1, 4:53 pm, Ayende Rahien <[email protected]> wrote:
> You should call TryDisposeUoW in one place, Message Completed.This is called
> if there is a error or not, and intended for cleanup operations.
>
> On Mon, Jun 1, 2009 at 7:39 PM, Mike Nichols <[email protected]>wrote:
>
> > here is my unit of work module MessageProcessingCompleted handler. Placing
> > this in MessageProcessingFailure handler seems to fix matters.
> > NHProf was showing me that all the DTC errors were in the same session but
> > I didn't think about the problems that creates. Let me be a little cheesy
> > and say that if I didn't have NHProf showing me such clear boundaries on
> > events I really am not sure how I was going to track this sucka down.
>
> > Anyways, here is my new UnitOfWorkMessageModule for future victims of
> > transaction torture :)
> > public class UnitOfWorkMessageModule : IMessageModule
> > {
>
> > public void Init(ITransport transport)
> > {
> > transport.MessageArrived += transport_MessageArrived;
> > transport.MessageProcessingCompleted +=
> > transport_MessageProcessingCompleted;
> > transport.MessageProcessingFailure +=
> > transport_MessageProcessingFailure;
> > }
>
> > private void
> > transport_MessageProcessingFailure(CurrentMessageInformation information,
> > Exception exception)
> > {
> > TryDisposeUnitOfWork();
>
> > if (exception != null)
> > {
> > Log.For(this).Error(exception.ToString());
> > }
>
> > }
>
> > public void Stop(ITransport transport)
> > {
> > transport.MessageArrived -= transport_MessageArrived;
> > transport.MessageProcessingCompleted -=
> > transport_MessageProcessingCompleted;
> > transport.MessageProcessingFailure -=
> > transport_MessageProcessingFailure;
> > }
>
> > bool transport_MessageArrived(CurrentMessageInformation arg)
> > {
> > UnitOfWork.Start();
> > return false;
> > }
>
> > void transport_MessageProcessingCompleted(CurrentMessageInformation
> > obj, Exception exception)
> > {
> > if(exception!=null)
> > {
> > Log.For(this).Error("An error occured on message process
> > completion:" + exception);
> > }
> > else
> > {
> > TryDisposeUnitOfWork();
> > }
>
> > }
> > private void TryDisposeUnitOfWork()
> > {
> > try
> > {
> > if (UnitOfWork.IsStarted)
> > {
> > UnitOfWork.Current.Dispose();
> > }
> > }
> > catch (Exception ex)
> > {
> > Log.For(this).Error(ex.ToString());
> > throw;
> > }
> > }
> > }
> > On Mon, Jun 1, 2009 at 4:11 PM, Ayende Rahien <[email protected]> wrote:
>
> >> Oh, that is probably it! You are not properly disposing the session in
> >> that scenario?
> >> Don't forget that if a message is failing, it is going to get retried.
>
> >> On Mon, Jun 1, 2009 at 7:08 PM, Mike Nichols
> >> <[email protected]>wrote:
>
> >>> The test I wrote passes (unfortunately). I just can't figure out why NH
> >>> would try to insert again after the previous message was failed, almost
> >>> like
> >>> the session wasn't disposed in my UnitOfWork module after the previous
> >>> message was moved to the error queue...Let me check to make sure the
> >>> message
> >>> module MessageProcesSINGCompleted event is getting fired after a
> >>> transaction
> >>> failure....
> >>> On Mon, Jun 1, 2009 at 4:03 PM, Ayende Rahien <[email protected]>wrote:
>
> >>>> Hm, can you try to write a test that reproduce this?
>
> >>>> On Mon, Jun 1, 2009 at 6:55 PM, Mike Nichols
> >>>> <[email protected]>wrote:
>
> >>>>> Yes I see all those passing. Here's what's happening:
> >>>>> 1. Send good message and all works
> >>>>> 2. Send message that causes transaction exception (as before) :: App
> >>>>> doesn't crash now (yeaay!)
> >>>>> 3. Send good message : Message is received (therefore the transport is
> >>>>> still alive even after previous exception) but before it is processed
> >>>>> the previous bad transaction is attempted ONCE and so the whole
> >>>>> processing fails...almost like the transaction wasn't disposed after
> >>>>> the error queue handling was done. Interestingly, NHProf isn't showing
> >>>>> all this in a new session either, but not sure that is truthful or
> >>>>> not. The 'Error DTC Transaction prepre (sic) phase failed' error pops
> >>>>> up BEFORE the other message has a chance to fully process.
> >>>>> Oi-vey
>
> >>>>> On Jun 1, 2:57 pm, Ayende Rahien <[email protected]> wrote:
> >>>>> > Hm, can you look at the tests that I committed, they are testing that
> >>>>> the
> >>>>> > message arrive in the error queue.
>
> >>>>> > On Mon, Jun 1, 2009 at 4:05 PM, Mike Nichols <
> >>>>> [email protected]>wrote:
>
> >>>>> > > Hm...the host isn't crashing now but the message that causes the
> >>>>> error
> >>>>> > > seems not to be moving to the errors queues, or, the transport is
> >>>>> > > shutting down. i can't tell yet.
>
> >>>>> > > On Jun 1, 11:01 am, Ayende Rahien <[email protected]> wrote:
> >>>>> > > > Okay, this is now fixed, have fun :-)
>
> >>>>> > > > On Mon, Jun 1, 2009 at 1:40 PM, Mike Nichols <
> >>>>> [email protected]
> >>>>> > > >wrote:
>
> >>>>> > > > > Man thanks Ayende
>
> >>>>> > > > > On Mon, Jun 1, 2009 at 10:13 AM, Ayende Rahien <
> >>>>> [email protected]>
> >>>>> > > wrote:
>
> >>>>> > > > >> Yes, I can.You need to use IEnlistmentNotification impl and
> >>>>> register
> >>>>> > > that
> >>>>> > > > >> on the TX.
> >>>>> > > > >> I'll have a fix shortly
>
> >>>>> > > > >> On Mon, Jun 1, 2009 at 1:01 PM, Mike Nichols <
> >>>>> > > [email protected]>wrote:
>
> >>>>> > > > >>> Are you able to test this without all the NH dependency
> >>>>> cruft? I want
> >>>>> > > to
> >>>>> > > > >>> keep hacking on this but can't figure out how to write a
> >>>>> lighter test
> >>>>> > > for it
> >>>>> > > > >>> to stick in RSB code base. Just throwing
> >>>>> TransactionExceptions
> >>>>> > > doesn't work
>
> >>>>> > > > >>> On Mon, Jun 1, 2009 at 8:12 AM, Ayende Rahien <
> >>>>> [email protected]>
> >>>>> > > wrote:
>
> >>>>> > > > >>>> Sigh,
> >>>>> > > > >>>> I reproduced the issue, not fun.
>
> >>>>> > > > >>>> On Mon, Jun 1, 2009 at 1:29 PM, Mike Nichols <
> >>>>> > > [email protected]>wrote:
>
> >>>>> > > > >>>>> I think I have narrowed the problem to transaction commit
> >>>>> failures
> >>>>> > > > >>>>> that take place AFTER the 'Consume' invocation is made (ie
> >>>>> in
> >>>>> > > > >>>>> MessageCompleted). These exceptions are outside the scope
> >>>>> of the
> >>>>> > > > >>>>> try...catch wrapping the ProcessMessage call.
> >>>>> > > > >>>>> In the code I have above the transaction tries to commit
> >>>>> (in ATM)
> >>>>> > > and
> >>>>> > > > >>>>> then rolls back since SQL Server throws, aborting the
> >>>>> transaction.
> >>>>> > > > >>>>> When the TransactionScope attempts to Dispose in
> >>>>> RQTransport
> >>>>> > > > >>>>> ReceiveMessage method, the InternalTransaction throws since
> >>>>> it was
> >>>>> > > > >>>>> aborted, making the whole app crash since it is unhandled.
>
> >>>>> > > > >>>>> Any ideas on this? My attempts to handle
> >>>>> TransactionException have
> >>>>> > > so
> >>>>> > > > >>>>> far just thrown RSB into a loop.
>
> >>>>> > > > >>>>> On May 30, 11:41 pm, Mike Nichols <
> >>>>> [email protected]>
> >>>>> > > wrote:
> >>>>> > > > >>>>> > I have a test case here that demonstrates the problem. I
> >>>>> changed
> >>>>> > > > >>>>> > RQTransport on ReceiveMessage to catch
> >>>>> > > TransactionAbortedException
> >>>>> > > > >>>>> and
> >>>>> > > > >>>>> > Debugger.Launch inside the catch statement.
> >>>>> > > > >>>>> > Note this test is 'heavy' intentionally . RSB tries 5
> >>>>> times to
> >>>>> > > handle
> >>>>> > > > >>>>> > the message but when the Session flushes the transaction
> >>>>> aborts
> >>>>> > > and
> >>>>> > > > >>>>> > since the transaction reference is outside the
> >>>>> try...catch in
> >>>>> > > > >>>>> > ReceiveMessage it goes unhandled.
>
> >>>>> > > > >>>>> > First here is output from NHProf Error logging:
> >>>>> > > > >>>>> > It seems like since the exception is thrown inside the
> >>>>> > > > >>>>> > TransactionScope (tx) instead the inner try..catch is
> >>>>> ignored and
> >>>>> > > > >>>>> > hence the TransactionAbortedException goes unhandled in
> >>>>> the app,
> >>>>> > > > >>>>> > stopping it altogether.
>
> >>>>> > > > >>>>> > ERROR:
> >>>>> > > > >>>>> > DTC transaction prepre phase failed
> >>>>> > > > >>>>> > System.Data.SqlTypes.SqlTypeException: SqlDateTime
> >>>>> overflow. Must
> >>>>> > > be
> >>>>> > > > >>>>> > between 1/1/1753 12:00:00 AM and 12/31/9999 11:59:59 PM.
> >>>>> > > > >>>>> > at
> >>>>> System.Data.SqlTypes.SqlDateTime.FromTimeSpan(TimeSpan
> >>>>> > > value)
> >>>>> > > > >>>>> > at
> >>>>> System.Data.SqlTypes.SqlDateTime.FromDateTime(DateTime
> >>>>> > > value)
> >>>>> > > > >>>>> > at
> >>>>> System.Data.SqlClient.MetaType.FromDateTime(DateTime
> >>>>> > > dateTime,
> >>>>> > > > >>>>> > Byte cb)
> >>>>> > > > >>>>> > at System.Data.SqlClient.TdsParser.WriteValue(Object
> >>>>> value,
> >>>>> > > > >>>>> > MetaType type, Byte scale, Int32 actualLength, Int32
> >>>>> > > > >>>>> encodingByteSize,
> >>>>> > > > >>>>> > Int32 offset, TdsParserStateObject stateObj)
> >>>>> > > > >>>>> > at
> >>>>> System.Data.SqlClient.TdsParser.TdsExecuteRPC(_SqlRPC[]
> >>>>> > > > >>>>> > rpcArray, Int32 timeout, Boolean inSchema,
> >>>>> SqlNotificationRequest
> >>>>> > > > >>>>> > notificationRequest, TdsParserStateObject stateObj,
> >>>>> Boolean
> >>>>> > > > >>>>> > isCommandProc)
> >>>>> > > > >>>>> > at
>
> ...
>
> read more »
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups
"Rhino Tools Dev" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to
[email protected]
For more options, visit this group at
http://groups.google.com/group/rhino-tools-dev?hl=en
-~----------~----~----~----~------~----~------~--~---