From: <aye...@us...> - 2009-01-05 12:57:56
|
Revision: 3977 http://nhibernate.svn.sourceforge.net/nhibernate/?rev=3977&view=rev Author: ayenderahien Date: 2009-01-05 12:57:44 +0000 (Mon, 05 Jan 2009) Log Message: ----------- Fixing NH-1632 and NH-754 Modified Paths: -------------- trunk/nhibernate/src/NHibernate/AdoNet/ConnectionManager.cs trunk/nhibernate/src/NHibernate/Impl/AbstractSessionImpl.cs trunk/nhibernate/src/NHibernate/Impl/SessionImpl.cs trunk/nhibernate/src/NHibernate/Impl/StatelessSessionImpl.cs trunk/nhibernate/src/NHibernate.Test/NHibernate.Test.csproj Added Paths: ----------- trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/ trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Fixture.cs trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Mappings.hbm.xml trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Model.cs Modified: trunk/nhibernate/src/NHibernate/AdoNet/ConnectionManager.cs =================================================================== --- trunk/nhibernate/src/NHibernate/AdoNet/ConnectionManager.cs 2009-01-05 10:54:05 UTC (rev 3976) +++ trunk/nhibernate/src/NHibernate/AdoNet/ConnectionManager.cs 2009-01-05 12:57:44 UTC (rev 3977) @@ -44,6 +44,8 @@ [NonSerialized] private bool isFlushing; + private bool flushingFromDtcTransaction; + public ConnectionManager( ISessionImplementor session, IDbConnection suppliedConnection, @@ -256,7 +258,7 @@ private void AggressiveRelease() { - if (ownConnection) + if (ownConnection && flushingFromDtcTransaction == false) { log.Debug("aggressively releasing database connection"); if (connection != null) @@ -388,5 +390,29 @@ { get { return batcher; } } + + public IDisposable FlushingFromDtcTransaction + { + get + { + flushingFromDtcTransaction = true; + return new StopFlushingFromDtcTransaction(this); + } + } + + private class StopFlushingFromDtcTransaction : IDisposable + { + private readonly ConnectionManager manager; + + public StopFlushingFromDtcTransaction(ConnectionManager manager) + { + this.manager = manager; + } + + public void Dispose() + { + manager.flushingFromDtcTransaction = false; + } + } } } Modified: trunk/nhibernate/src/NHibernate/Impl/AbstractSessionImpl.cs =================================================================== --- trunk/nhibernate/src/NHibernate/Impl/AbstractSessionImpl.cs 2009-01-05 10:54:05 UTC (rev 3976) +++ trunk/nhibernate/src/NHibernate/Impl/AbstractSessionImpl.cs 2009-01-05 12:57:44 UTC (rev 3977) @@ -26,7 +26,16 @@ private bool closed = false; private System.Transactions.Transaction ambientTransation; private bool isAlreadyDisposed; + protected bool shouldCloseSessionOnDtcTransactionCompleted; + protected bool TakingPartInDtcTransaction + { + get + { + return ambientTransation != null; + } + } + internal AbstractSessionImpl() { } protected internal AbstractSessionImpl(ISessionFactoryImplementor factory) @@ -246,7 +255,8 @@ BeforeTransactionCompletion(null); if (FlushMode != FlushMode.Never) { - Flush(); + using (ConnectionManager.FlushingFromDtcTransaction) + Flush(); } preparingEnlistment.Prepared(); } @@ -282,10 +292,14 @@ { bool wasSuccessful = e.Transaction.TransactionInformation.Status == TransactionStatus.Committed; AfterTransactionCompletion(wasSuccessful, null); + if (shouldCloseSessionOnDtcTransactionCompleted) + Dispose(true); }; ambientTransation.EnlistVolatile(this, EnlistmentOptions.None); } + protected abstract void Dispose(bool disposing); + #endregion } } Modified: trunk/nhibernate/src/NHibernate/Impl/SessionImpl.cs =================================================================== --- trunk/nhibernate/src/NHibernate/Impl/SessionImpl.cs 2009-01-05 10:54:05 UTC (rev 3976) +++ trunk/nhibernate/src/NHibernate/Impl/SessionImpl.cs 2009-01-05 12:57:44 UTC (rev 3977) @@ -1363,6 +1363,11 @@ public void Dispose() { log.Debug("running ISession.Dispose()"); + if (TakingPartInDtcTransaction) + { + shouldCloseSessionOnDtcTransactionCompleted = true; + return; + } Dispose(true); } @@ -1375,7 +1380,7 @@ /// If this Session is being Finalized (<c>isDisposing==false</c>) then make sure not /// to call any methods that could potentially bring this Session back to life. /// </remarks> - private void Dispose(bool isDisposing) + protected override void Dispose(bool isDisposing) { if (IsAlreadyDisposed) { Modified: trunk/nhibernate/src/NHibernate/Impl/StatelessSessionImpl.cs =================================================================== --- trunk/nhibernate/src/NHibernate/Impl/StatelessSessionImpl.cs 2009-01-05 10:54:05 UTC (rev 3976) +++ trunk/nhibernate/src/NHibernate/Impl/StatelessSessionImpl.cs 2009-01-05 12:57:44 UTC (rev 3977) @@ -731,10 +731,15 @@ public void Dispose() { log.Debug("running IStatelessSession.Dispose()"); + if(TakingPartInDtcTransaction) + { + shouldCloseSessionOnDtcTransactionCompleted = true; + return; + } Dispose(true); } - private void Dispose(bool isDisposing) + protected override void Dispose(bool isDisposing) { if (_isAlreadyDisposed) { Copied: trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Fixture.cs (from rev 3965, trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1621/Fixture.cs) =================================================================== --- trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Fixture.cs (rev 0) +++ trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Fixture.cs 2009-01-05 12:57:44 UTC (rev 3977) @@ -0,0 +1,148 @@ +using NUnit.Framework; +using NUnit.Framework.SyntaxHelpers; + +namespace NHibernate.Test.NHSpecificTest.NH1632 +{ + using System.Transactions; + + [TestFixture] + public class Fixture : BugTestCase + { + public override string BugNumber + { + get { return "NH1632"; } + } + + [Test] + public void Dispose_session_inside_transaction_scope() + { + ISession s; + + using (var tx = new TransactionScope()) + { + using (s = sessions.OpenSession()) + { + + } + tx.Complete(); + } + + Assert.IsFalse(s.IsOpen); + } + + [Test] + public void When_committing_transaction_scope_will_commit_transaction() + { + object id; + using (var tx = new TransactionScope()) + { + using (ISession s = sessions.OpenSession()) + { + id = s.Save(new Nums { NumA = 1, NumB = 2, ID = 5 }); + } + tx.Complete(); + } + + using (ISession s = sessions.OpenSession()) + using (ITransaction tx = s.BeginTransaction()) + { + Nums nums = s.Get<Nums>(id); + Assert.IsNotNull(nums); + s.Delete(nums); + + tx.Commit(); + } + } + + [Test] + public void Will_not_save_when_flush_mode_is_never() + { + object id; + using (var tx = new TransactionScope()) + { + using (ISession s = sessions.OpenSession()) + { + s.FlushMode = FlushMode.Never; + id = s.Save(new Nums { NumA = 1, NumB = 2, ID = 5 }); + } + tx.Complete(); + } + + using (ISession s = sessions.OpenSession()) + using (ITransaction tx = s.BeginTransaction()) + { + Nums nums = s.Get<Nums>(id); + Assert.IsNull(nums); + tx.Commit(); + } + } + + [Test] + public void When_using_two_sessions_with_explicit_flush() + { + object id1, id2; + using (var tx = new TransactionScope()) + { + using (ISession s1 = sessions.OpenSession()) + using (ISession s2 = sessions.OpenSession()) + { + + id1 = s1.Save(new Nums { NumA = 1, NumB = 2, ID = 5 }); + s1.Flush(); + + id2 = s2.Save(new Nums { NumA = 1, NumB = 2, ID = 6 }); + s2.Flush(); + + tx.Complete(); + } + } + + using (ISession s = sessions.OpenSession()) + using (ITransaction tx = s.BeginTransaction()) + { + Nums nums = s.Get<Nums>(id1); + Assert.IsNotNull(nums); + s.Delete(nums); + + nums = s.Get<Nums>(id2); + Assert.IsNotNull(nums); + s.Delete(nums); + + tx.Commit(); + } + } + + [Test] + public void When_using_two_sessions() + { + object id1, id2; + using (var tx = new TransactionScope()) + { + using (ISession s1 = sessions.OpenSession()) + using (ISession s2 = sessions.OpenSession()) + { + + id1 = s1.Save(new Nums { NumA = 1, NumB = 2, ID = 5 }); + + id2 = s2.Save(new Nums { NumA = 1, NumB = 2, ID = 6 }); + + tx.Complete(); + } + } + + using (ISession s = sessions.OpenSession()) + using (ITransaction tx = s.BeginTransaction()) + { + Nums nums = s.Get<Nums>(id1); + Assert.IsNotNull(nums); + s.Delete(nums); + + nums = s.Get<Nums>(id2); + Assert.IsNotNull(nums); + s.Delete(nums); + + tx.Commit(); + } + } + } +} Property changes on: trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Fixture.cs ___________________________________________________________________ Added: svn:mergeinfo + Copied: trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Mappings.hbm.xml (from rev 3965, trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1621/Mappings.hbm.xml) =================================================================== --- trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Mappings.hbm.xml (rev 0) +++ trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Mappings.hbm.xml 2009-01-05 12:57:44 UTC (rev 3977) @@ -0,0 +1,14 @@ +<?xml version="1.0" encoding="utf-8" ?> +<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2" + namespace="NHibernate.Test.NHSpecificTest.NH1632" + assembly="NHibernate.Test" +> + <class name="Nums" table="nums"> + <id name="ID"> + <generator class="assigned"/> + </id> + <property name="NumA"/> + <property name="NumB"/> + <property name="Sum" access="readonly"/> + </class> +</hibernate-mapping> Property changes on: trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Mappings.hbm.xml ___________________________________________________________________ Added: svn:mergeinfo + Copied: trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Model.cs (from rev 3965, trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1621/Model.cs) =================================================================== --- trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Model.cs (rev 0) +++ trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Model.cs 2009-01-05 12:57:44 UTC (rev 3977) @@ -0,0 +1,17 @@ +namespace NHibernate.Test.NHSpecificTest.NH1632 +{ + public class Nums + { + public virtual int ID { get; set; } + + public virtual int NumA { get; set; } + public virtual int NumB { get; set; } + public virtual int Sum + { + get + { + return NumA + NumB; + } + } + } +} Property changes on: trunk/nhibernate/src/NHibernate.Test/NHSpecificTest/NH1632/Model.cs ___________________________________________________________________ Added: svn:mergeinfo + Modified: trunk/nhibernate/src/NHibernate.Test/NHibernate.Test.csproj =================================================================== --- trunk/nhibernate/src/NHibernate.Test/NHibernate.Test.csproj 2009-01-05 10:54:05 UTC (rev 3976) +++ trunk/nhibernate/src/NHibernate.Test/NHibernate.Test.csproj 2009-01-05 12:57:44 UTC (rev 3977) @@ -567,6 +567,8 @@ <Compile Include="NHSpecificTest\NH1612\Person.cs" /> <Compile Include="NHSpecificTest\NH1621\Fixture.cs" /> <Compile Include="NHSpecificTest\NH1621\Model.cs" /> + <Compile Include="NHSpecificTest\NH1632\Fixture.cs" /> + <Compile Include="NHSpecificTest\NH1632\Model.cs" /> <Compile Include="NHSpecificTest\NH280\Fixture.cs" /> <Compile Include="NHSpecificTest\NH280\Foo.cs" /> <Compile Include="NHSpecificTest\NH1018\Employee.cs" /> @@ -1588,6 +1590,11 @@ <EmbeddedResource Include="Cascade\JobBatch.hbm.xml" /> <EmbeddedResource Include="Deletetransient\Person.hbm.xml" /> <Content Include="DynamicEntity\package.html" /> + <EmbeddedResource Include="NHSpecificTest\NH1632\Mappings.hbm.xml" /> + + + + <EmbeddedResource Include="NHSpecificTest\NH1612\Mappings.hbm.xml" /> <EmbeddedResource Include="NHSpecificTest\NH1549\Mappings.hbm.xml" /> <EmbeddedResource Include="NHSpecificTest\NH1521\AclassWithSpecific.hbm.xml" /> @@ -1699,4 +1706,4 @@ if exist "$(ProjectDir)hibernate.cfg.xml" (copy "$(ProjectDir)hibernate.cfg.xml" "hibernate.cfg.xml") copy /y "..\..\..\NHibernate.DomainModel\ABC.hbm.xml" "ABC.hbm.xml"</PostBuildEvent> </PropertyGroup> -</Project> \ No newline at end of file +</Project> This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |