From 08efaa0572f7b707457a53aec161f2efa0415aef Mon Sep 17 00:00:00 2001 From: Aleksandar Fabijanic Date: Tue, 10 Feb 2009 15:51:42 +0000 Subject: [PATCH] Removed Transactor template (not needed), fixed documentation, additional tests --- Data/ODBC/testsuite/src/SQLExecutor.cpp | 45 +++++++++++-- Data/include/Poco/Data/Transaction.h | 87 +++++++++---------------- Data/src/Transaction.cpp | 4 +- 3 files changed, 73 insertions(+), 63 deletions(-) diff --git a/Data/ODBC/testsuite/src/SQLExecutor.cpp b/Data/ODBC/testsuite/src/SQLExecutor.cpp index a349a95fa..25a99f80a 100644 --- a/Data/ODBC/testsuite/src/SQLExecutor.cpp +++ b/Data/ODBC/testsuite/src/SQLExecutor.cpp @@ -3688,8 +3688,7 @@ void SQLExecutor::transactor() session().setTransactionIsolation(Session::TRANSACTION_READ_COMMITTED); TestCommitTransactor ct; - Transaction t1(session()); - t1.transact(ct); + Transaction t1(session(), ct); try { session() << "SELECT count(*) FROM PERSON", into(count), now; } catch(ConnectionException& ce){ std::cout << ce.toString() << std::endl; fail (funct); } @@ -3708,8 +3707,46 @@ void SQLExecutor::transactor() try { TestRollbackTransactor rt; - Transaction t2(session()); - t2.transact(rt); + Transaction t(session(), rt); + fail ("must fail"); + } catch (Poco::Exception&) { } + + try { session() << "SELECT count(*) FROM PERSON", into(count), now; } + catch(ConnectionException& ce){ std::cout << ce.toString() << std::endl; fail (funct); } + catch(StatementException& se){ std::cout << se.toString() << std::endl; fail (funct); } + assert (0 == count); + + try + { + TestRollbackTransactor rt; + Transaction t(session()); + t.transact(rt); + fail ("must fail"); + } catch (Poco::Exception&) { } + + try { session() << "SELECT count(*) FROM PERSON", into(count), now; } + catch(ConnectionException& ce){ std::cout << ce.toString() << std::endl; fail (funct); } + catch(StatementException& se){ std::cout << se.toString() << std::endl; fail (funct); } + assert (0 == count); + + try + { + TestRollbackTransactor rt; + Transaction t(session(), false); + t.transact(rt); + fail ("must fail"); + } catch (Poco::Exception&) { } + + try { session() << "SELECT count(*) FROM PERSON", into(count), now; } + catch(ConnectionException& ce){ std::cout << ce.toString() << std::endl; fail (funct); } + catch(StatementException& se){ std::cout << se.toString() << std::endl; fail (funct); } + assert (0 == count); + + try + { + TestRollbackTransactor rt; + Transaction t(session(), true); + t.transact(rt); fail ("must fail"); } catch (Poco::Exception&) { } diff --git a/Data/include/Poco/Data/Transaction.h b/Data/include/Poco/Data/Transaction.h index 64adc1fb0..c192d6459 100644 --- a/Data/include/Poco/Data/Transaction.h +++ b/Data/include/Poco/Data/Transaction.h @@ -59,52 +59,6 @@ class Data_API Transaction /// See Transaction for more detaisl nad purpose of this template. { public: - template - class Transactor - /// Transactor is a helper functor template. - /// It is used to consolidate the C++ code that participates in - /// the transaction. - /// - /// Example usage: - /// - /// struct ATransaction - /// { - /// void operator () (Session& session) const - /// { - /// // do something ... - /// } - /// }; - /// - /// ATransaction t; - /// Transaction at(session); - /// at.transact(t); // commits, if successful - /// - /// See Transaction for more details on how to use Transactor. - { - public: - Transactor(T& transactor): _transactor(transactor) - /// Creates the Transactor - { - } - - inline void operator () (Poco::Data::Session& session) - { - _transactor(session); - } - - inline void operator () (Poco::Data::Session& session) const - { - _transactor(session); - } - - private: - Transactor(); - Transactor(const Transactor&); - Transactor& operator = (const Transactor&); - - T& _transactor; - }; - Transaction(Poco::Data::Session& session, Poco::Logger* pLogger = 0); /// Creates the Transaction and starts it, using the given database session and logger. @@ -117,15 +71,35 @@ public: Transaction(Poco::Data::Session& rSession, T& t, Poco::Logger* pLogger = 0): _rSession(rSession), _pLogger(pLogger) - /// Creates the Transaction, using the given database session and logger. - /// The type for the second argument must be Transactor-compatible, i.e. - /// provide the overload for the operator (). + /// Creates the Transaction, using the given database session, transactor and logger. + /// The transactor type must provide operator () overload taking non-const Session + /// reference as an argument. + /// /// When transaction is created using this constructor, it is executed and /// commited automatically. If no error occurs, rollback is disabled and does - /// not occur at destruction time. + /// not occur at destruction time. If an error occurs resulting in exception being + /// thrown, the transaction is rolled back and exception propagated to calling code. + /// + /// Example usage: + /// + /// struct Transactor + /// { + /// void operator () (Session& session) const + /// { + /// // do something ... + /// } + /// }; + /// + /// Transactor tr; + /// Transaction tn(session, tr); { - begin(); - execute(t); + try { transact(t); } + catch (...) + { + if (_pLogger) _pLogger->error("Error executing transaction."); + rollback(); + throw; + } } ~Transaction(); @@ -164,12 +138,11 @@ public: template void transact(T& t) - /// Executes the transactor and, if doCommit is true, commits the transaction. - /// Passing true value for commit disables rollback during destruction - /// of this Transaction object. + /// Executes the transactor and, unless transactor throws an exception, + /// commits the transaction. { - Transactor transactor(t); - transactor(_rSession); + if (!isActive()) begin(); + t(_rSession); commit(); } diff --git a/Data/src/Transaction.cpp b/Data/src/Transaction.cpp index e62500bf4..fe975b5e1 100644 --- a/Data/src/Transaction.cpp +++ b/Data/src/Transaction.cpp @@ -69,10 +69,10 @@ Transaction::~Transaction() _rSession.rollback(); } - catch (Poco::Exception& exc) + catch (...) { if (_pLogger) - _pLogger->fatal("Error while rolling back database transaction: " + exc.displayText()); + _pLogger->error("Error while rolling back database transaction."); } } }