aboutsummaryrefslogtreecommitdiff
path: root/odb/mysql/statement.cxx
diff options
context:
space:
mode:
authorBoris Kolpackov <boris@codesynthesis.com>2010-11-06 18:00:43 +0200
committerBoris Kolpackov <boris@codesynthesis.com>2010-11-06 18:00:43 +0200
commit5daaa1a6d9c8f5d3a4ad3d7009df564bc6506424 (patch)
treeb96d205208587208a4e443be192fe264d2f53d57 /odb/mysql/statement.cxx
parent6fd2fb44263eb6704905cddcc607462c21c5e687 (diff)
Add support for container persistence
Generalize statements that were used for persisting objects to work for both objects and containers. Implement a cache for container statements.
Diffstat (limited to 'odb/mysql/statement.cxx')
-rw-r--r--odb/mysql/statement.cxx269
1 files changed, 64 insertions, 205 deletions
diff --git a/odb/mysql/statement.cxx b/odb/mysql/statement.cxx
index 6193f39..0f21917 100644
--- a/odb/mysql/statement.cxx
+++ b/odb/mysql/statement.cxx
@@ -35,15 +35,13 @@ namespace odb
{
}
- // query_statement
+ // select_statement
//
- query_statement::
- ~query_statement ()
+ select_statement::
+ ~select_statement ()
{
- statement* as (conn_.active ());
-
- if (cached_ || as == this)
+ if (cached_ || conn_.active () == this)
{
try
{
@@ -53,23 +51,21 @@ namespace odb
{
}
}
-
- if (as == this)
- conn_.active (0);
}
- query_statement::
- query_statement (connection& conn,
- const string& s,
- binding& image,
- MYSQL_BIND* parameters)
+ select_statement::
+ select_statement (connection& conn,
+ const string& s,
+ binding& cond,
+ binding& data)
: statement (conn),
end_ (false),
cached_ (false),
rows_ (0),
- image_ (image),
- image_version_ (0),
- parameters_ (parameters)
+ cond_ (cond),
+ cond_version_ (0),
+ data_ (data),
+ data_version_ (0)
{
if (statement* a = conn_.active ())
a->cancel ();
@@ -78,7 +74,7 @@ namespace odb
throw database_exception (stmt_);
}
- void query_statement::
+ void select_statement::
execute ()
{
if (statement* a = conn_.active ())
@@ -93,20 +89,20 @@ namespace odb
if (mysql_stmt_reset (stmt_))
throw database_exception (stmt_);
- if (image_version_ != image_.version)
+ if (cond_version_ != cond_.version)
{
- if (mysql_stmt_bind_result (stmt_, image_.bind))
+ if (mysql_stmt_bind_param (stmt_, cond_.bind))
throw database_exception (stmt_);
- image_version_ = image_.version;
+ cond_version_ = cond_.version;
}
- if (parameters_ != 0)
+ if (data_version_ != data_.version)
{
- // @@ versioning
- //
- if (mysql_stmt_bind_param (stmt_, parameters_))
+ if (mysql_stmt_bind_result (stmt_, data_.bind))
throw database_exception (stmt_);
+
+ data_version_ = data_.version;
}
if (mysql_stmt_execute (stmt_))
@@ -122,7 +118,7 @@ namespace odb
conn_.active (this);
}
- void query_statement::
+ void select_statement::
cache ()
{
if (!cached_)
@@ -139,7 +135,7 @@ namespace odb
}
}
- std::size_t query_statement::
+ std::size_t select_statement::
result_size ()
{
if (!cached_)
@@ -151,18 +147,18 @@ namespace odb
return rows_ + static_cast<std::size_t> (mysql_stmt_num_rows (stmt_));
}
- query_statement::result query_statement::
+ select_statement::result select_statement::
fetch ()
{
- // If the result was cached the image can grow between calls
+ // If the result was cached the data image can grow between calls
// to fetch() as a result of other statements execution.
//
- if (cached_ && image_version_ != image_.version)
+ if (cached_ && data_version_ != data_.version)
{
- if (mysql_stmt_bind_result (stmt_, image_.bind))
+ if (mysql_stmt_bind_result (stmt_, data_.bind))
throw database_exception (stmt_);
- image_version_ = image_.version;
+ data_version_ = data_.version;
}
int r (mysql_stmt_fetch (stmt_));
@@ -195,25 +191,25 @@ namespace odb
}
}
- void query_statement::
+ void select_statement::
refetch ()
{
// Re-fetch columns that were truncated.
//
- for (size_t i (0); i < image_.count; ++i)
+ for (size_t i (0); i < data_.count; ++i)
{
- if (*image_.bind[i].error)
+ if (*data_.bind[i].error)
{
- *image_.bind[i].error = 0;
+ *data_.bind[i].error = 0;
if (mysql_stmt_fetch_column (
- stmt_, image_.bind + i, static_cast<unsigned int> (i), 0))
+ stmt_, data_.bind + i, static_cast<unsigned int> (i), 0))
throw database_exception (stmt_);
}
}
}
- void query_statement::
+ void select_statement::
free_result ()
{
end_ = true;
@@ -222,30 +218,33 @@ namespace odb
if (mysql_stmt_free_result (stmt_))
throw database_exception (stmt_);
+
+ if (conn_.active () == this)
+ conn_.active (0);
}
- void query_statement::
+ void select_statement::
cancel ()
{
// If we cached the result, don't free it just yet.
//
if (!cached_)
free_result ();
-
- conn_.active (0);
+ else
+ conn_.active (0);
}
- // persist_statement
+ // insert_statement
//
- persist_statement::
- ~persist_statement ()
+ insert_statement::
+ ~insert_statement ()
{
}
- persist_statement::
- persist_statement (connection& conn, const string& s, binding& image)
- : statement (conn), image_ (image), version_ (0)
+ insert_statement::
+ insert_statement (connection& conn, const string& s, binding& data)
+ : statement (conn), data_ (data), data_version_ (0)
{
if (statement* a = conn_.active ())
a->cancel ();
@@ -254,7 +253,7 @@ namespace odb
throw database_exception (stmt_);
}
- void persist_statement::
+ bool insert_statement::
execute ()
{
if (statement* a = conn_.active ())
@@ -263,12 +262,12 @@ namespace odb
if (mysql_stmt_reset (stmt_))
throw database_exception (stmt_);
- if (version_ != image_.version)
+ if (data_version_ != data_.version)
{
- if (mysql_stmt_bind_param (stmt_, image_.bind))
+ if (mysql_stmt_bind_param (stmt_, data_.bind))
throw database_exception (stmt_);
- version_ = image_.version;
+ data_version_ = data_.version;
}
if (mysql_stmt_execute (stmt_))
@@ -277,7 +276,7 @@ namespace odb
{
case ER_DUP_ENTRY:
{
- throw object_already_persistent ();
+ return false;
}
case ER_LOCK_DEADLOCK:
{
@@ -289,139 +288,10 @@ namespace odb
}
}
}
- }
-
- // find_statement
- //
-
- find_statement::
- ~find_statement ()
- {
- if (conn_.active () == this)
- {
- try
- {
- free_result ();
- }
- catch (...)
- {
- }
- }
- }
-
- find_statement::
- find_statement (connection& conn,
- const string& s,
- binding& id,
- binding& image)
- : statement (conn),
- id_ (id),
- id_version_ (0),
- image_ (image),
- image_version_ (0)
- {
- if (statement* a = conn_.active ())
- a->cancel ();
-
- if (mysql_stmt_prepare (stmt_, s.c_str (), s.size ()) != 0)
- throw database_exception (stmt_);
- }
-
- find_statement::result find_statement::
- execute ()
- {
- if (statement* a = conn_.active ())
- a->cancel ();
-
- if (mysql_stmt_reset (stmt_))
- throw database_exception (stmt_);
-
- if (id_version_ != id_.version)
- {
- if (mysql_stmt_bind_param (stmt_, id_.bind))
- throw database_exception (stmt_);
-
- id_version_ = id_.version;
- }
-
- if (image_version_ != image_.version)
- {
- if (mysql_stmt_bind_result (stmt_, image_.bind))
- throw database_exception (stmt_);
-
- image_version_ = image_.version;
- }
-
- if (mysql_stmt_execute (stmt_))
- {
- unsigned int e (mysql_stmt_errno (stmt_));
-
- if (e == ER_LOCK_DEADLOCK)
- throw deadlock ();
- else
- throw database_exception (stmt_);
- }
-
- conn_.active (this);
-
- int r (mysql_stmt_fetch (stmt_));
-
- switch (r)
- {
- case 0:
- {
- return success;
- }
- case MYSQL_NO_DATA:
- {
- free_result ();
- return no_data;
- }
- case MYSQL_DATA_TRUNCATED:
- {
- return truncated;
- }
- default:
- {
- throw database_exception (stmt_);
- }
- }
- }
- void find_statement::
- refetch ()
- {
- // Re-fetch columns that were truncated.
- //
- for (size_t i (0); i < image_.count; ++i)
- {
- if (*image_.bind[i].error)
- {
- *image_.bind[i].error = 0;
-
- if (mysql_stmt_fetch_column (
- stmt_, image_.bind + i, static_cast<unsigned int> (i), 0))
- throw database_exception (stmt_);
- }
- }
+ return true;
}
- void find_statement::
- free_result ()
- {
- if (mysql_stmt_free_result (stmt_))
- throw database_exception (stmt_);
-
- conn_.active (0);
- }
-
- void find_statement::
- cancel ()
- {
- free_result ();
- }
-
-
// update_statement
//
@@ -490,17 +360,17 @@ namespace odb
throw database_exception (stmt_);
}
- // erase_statement
+ // delete_statement
//
- erase_statement::
- ~erase_statement ()
+ delete_statement::
+ ~delete_statement ()
{
}
- erase_statement::
- erase_statement (connection& conn, const string& s, binding& id)
- : statement (conn), id_ (id), version_ (0)
+ delete_statement::
+ delete_statement (connection& conn, const string& s, binding& cond)
+ : statement (conn), cond_ (cond), cond_version_ (0)
{
if (statement* a = conn_.active ())
a->cancel ();
@@ -509,7 +379,7 @@ namespace odb
throw database_exception (stmt_);
}
- void erase_statement::
+ unsigned long long delete_statement::
execute ()
{
if (statement* a = conn_.active ())
@@ -518,12 +388,12 @@ namespace odb
if (mysql_stmt_reset (stmt_))
throw database_exception (stmt_);
- if (version_ != id_.version)
+ if (cond_version_ != cond_.version)
{
- if (mysql_stmt_bind_param (stmt_, id_.bind))
+ if (mysql_stmt_bind_param (stmt_, cond_.bind))
throw database_exception (stmt_);
- version_ = id_.version;
+ cond_version_ = cond_.version;
}
if (mysql_stmt_execute (stmt_))
@@ -538,21 +408,10 @@ namespace odb
my_ulonglong r (mysql_stmt_affected_rows (stmt_));
- if (r > 0)
- return;
-
- if (r == 0)
- throw object_not_persistent ();
- else
+ if (r == static_cast<my_ulonglong> (-1))
throw database_exception (stmt_);
- }
-
- // object_statements_base
- //
- object_statements_base::
- ~object_statements_base ()
- {
+ return static_cast<unsigned long long> (r);
}
}
}