aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBoris Kolpackov <boris@codesynthesis.com>2011-08-24 13:42:04 +0200
committerBoris Kolpackov <boris@codesynthesis.com>2011-08-24 13:42:04 +0200
commit7392db256c1587ff8fe87d95c5ae5c10f854f79e (patch)
treeb41dd7cea27ef46e13def92af80de1d310e3c43d
parent80c9352bdb197cea6a1fddc9f9e623c06e5d71ce (diff)
Add support for transaction multiplexing
Also delay getting a connection until after we do all the sanity checks (e.g., that there is no active transaction). Otherwise we are running risk of getting blocked rather than throwing an exception.
-rw-r--r--odb/sqlite/connection.cxx9
-rw-r--r--odb/sqlite/database.cxx18
-rw-r--r--odb/sqlite/database.hxx2
-rw-r--r--odb/sqlite/database.ixx18
-rw-r--r--odb/sqlite/transaction-impl.cxx35
-rw-r--r--odb/sqlite/transaction-impl.hxx10
-rw-r--r--odb/sqlite/transaction.hxx5
-rw-r--r--odb/sqlite/transaction.ixx6
8 files changed, 64 insertions, 39 deletions
diff --git a/odb/sqlite/connection.cxx b/odb/sqlite/connection.cxx
index ffb70a7..1e9ff6f 100644
--- a/odb/sqlite/connection.cxx
+++ b/odb/sqlite/connection.cxx
@@ -82,9 +82,6 @@ namespace odb
transaction_impl* connection::
begin ()
{
- if (transaction::has_current ())
- throw already_in_transaction ();
-
return new transaction_impl (
connection_ptr (inc_ref (this)), transaction_impl::deferred);
}
@@ -92,9 +89,6 @@ namespace odb
transaction_impl* connection::
begin_immediate ()
{
- if (transaction::has_current ())
- throw already_in_transaction ();
-
return new transaction_impl (
connection_ptr (inc_ref (this)), transaction_impl::immediate);
}
@@ -102,9 +96,6 @@ namespace odb
transaction_impl* connection::
begin_exclusive ()
{
- if (transaction::has_current ())
- throw already_in_transaction ();
-
return new transaction_impl (
connection_ptr (inc_ref (this)), transaction_impl::exclusive);
}
diff --git a/odb/sqlite/database.cxx b/odb/sqlite/database.cxx
index 6ce4621..04f788b 100644
--- a/odb/sqlite/database.cxx
+++ b/odb/sqlite/database.cxx
@@ -83,6 +83,24 @@ namespace odb
details::options::print_usage (os);
}
+ transaction_impl* database::
+ begin ()
+ {
+ return new transaction_impl (*this, transaction_impl::deferred);
+ }
+
+ transaction_impl* database::
+ begin_immediate ()
+ {
+ return new transaction_impl (*this, transaction_impl::immediate);
+ }
+
+ transaction_impl* database::
+ begin_exclusive ()
+ {
+ return new transaction_impl (*this, transaction_impl::exclusive);
+ }
+
odb::connection* database::
connection_ ()
{
diff --git a/odb/sqlite/database.hxx b/odb/sqlite/database.hxx
index 13c44e6..348f236 100644
--- a/odb/sqlite/database.hxx
+++ b/odb/sqlite/database.hxx
@@ -87,7 +87,7 @@ namespace odb
// Transactions.
//
public:
- transaction_impl*
+ virtual transaction_impl*
begin ();
transaction_impl*
diff --git a/odb/sqlite/database.ixx b/odb/sqlite/database.ixx
index f78d659..e7ae208 100644
--- a/odb/sqlite/database.ixx
+++ b/odb/sqlite/database.ixx
@@ -16,23 +16,5 @@ namespace odb
return connection_ptr (
static_cast<sqlite::connection*> (connection_ ()));
}
-
- inline transaction_impl* database::
- begin ()
- {
- return connection ()->begin ();
- }
-
- inline transaction_impl* database::
- begin_immediate ()
- {
- return connection ()->begin_immediate ();
- }
-
- inline transaction_impl* database::
- begin_exclusive ()
- {
- return connection ()->begin_exclusive ();
- }
}
}
diff --git a/odb/sqlite/transaction-impl.cxx b/odb/sqlite/transaction-impl.cxx
index 772b274..b425ed8 100644
--- a/odb/sqlite/transaction-impl.cxx
+++ b/odb/sqlite/transaction-impl.cxx
@@ -14,12 +14,38 @@ namespace odb
namespace sqlite
{
transaction_impl::
+ transaction_impl (database_type& db, lock l)
+ : odb::transaction_impl (db), lock_ (l)
+ {
+ }
+
+ transaction_impl::
transaction_impl (connection_ptr c, lock l)
- : odb::transaction_impl (c->database (), *c), connection_ (c)
+ : odb::transaction_impl (c->database (), *c),
+ connection_ (c),
+ lock_ (l)
+ {
+ }
+
+ transaction_impl::
+ ~transaction_impl ()
+ {
+ }
+
+ void transaction_impl::
+ start ()
{
+ // Grab a connection if we don't already have one.
+ //
+ if (connection_ == 0)
+ {
+ connection_ = static_cast<database_type&> (database_).connection ();
+ odb::transaction_impl::connection_ = connection_.get ();
+ }
+
statement_cache& sc (connection_->statement_cache ());
- switch (l)
+ switch (lock_)
{
case deferred:
{
@@ -39,11 +65,6 @@ namespace odb
}
}
- transaction_impl::
- ~transaction_impl ()
- {
- }
-
void transaction_impl::
commit ()
{
diff --git a/odb/sqlite/transaction-impl.hxx b/odb/sqlite/transaction-impl.hxx
index 8b5687b..f0df824 100644
--- a/odb/sqlite/transaction-impl.hxx
+++ b/odb/sqlite/transaction-impl.hxx
@@ -21,10 +21,7 @@ namespace odb
{
class LIBODB_SQLITE_EXPORT transaction_impl: public odb::transaction_impl
{
- protected:
- friend class connection;
- friend class transaction;
-
+ public:
typedef sqlite::database database_type;
typedef sqlite::connection connection_type;
@@ -35,12 +32,16 @@ namespace odb
exclusive
};
+ transaction_impl (database_type&, lock);
transaction_impl (connection_ptr, lock);
virtual
~transaction_impl ();
virtual void
+ start ();
+
+ virtual void
commit ();
virtual void
@@ -51,6 +52,7 @@ namespace odb
private:
connection_ptr connection_;
+ lock lock_;
};
}
}
diff --git a/odb/sqlite/transaction.hxx b/odb/sqlite/transaction.hxx
index aecf8aa..b30a818 100644
--- a/odb/sqlite/transaction.hxx
+++ b/odb/sqlite/transaction.hxx
@@ -45,6 +45,11 @@ namespace odb
static transaction&
current ();
+ // Set the current thread's transaction.
+ //
+ static void
+ current (transaction&);
+
public:
transaction_impl&
implementation ();
diff --git a/odb/sqlite/transaction.ixx b/odb/sqlite/transaction.ixx
index f2c9cc8..e8a6594 100644
--- a/odb/sqlite/transaction.ixx
+++ b/odb/sqlite/transaction.ixx
@@ -37,5 +37,11 @@ namespace odb
{
return implementation ().connection ();
}
+
+ inline void transaction::
+ current (transaction& t)
+ {
+ odb::transaction::current (t);
+ }
}
}