A few of weeks ago I blogged about flowing a transaction across AppDomain boundaries. Apparently, there’s a little gotcha that you need to be aware of: Even if you don’t flow the transaction to the other AppDomain, and the thread in the other AppDomain executes a method that calls back into the original AppDomain, the transaction will flow across the reentrant call.
In other words, if you have two objects, A and B, where A lives in one AppDomain and B lives in another AppDomain, then the following can happen: A calls a method of B within a transaction, but without flowing the transaction. The method of B executes without an ambient transaction. During the execution of that method, B calls a method of A without flowing the transaction. Nonetheless, the reentrant method of A executes within the same ambient transaction (which is not promoted to a distributed transaction).
This is actually quite reasonable, when you think about the way .NET Remoting works. The outgoing proxy remembers the call context that was used, and the incoming stub on the reentrant call restores the ambient transaction from that call context. Still, it can be quite misleading to see a completely different method of your class execute under the same ambient transaction from another method that didn’t ever call it directly.