aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBoris Kolpackov <boris@codesynthesis.com>2010-11-26 13:24:00 +0200
committerBoris Kolpackov <boris@codesynthesis.com>2010-11-26 13:24:00 +0200
commit51a71bc5cfe38ab7d4789f90725f8a24f49bd057 (patch)
tree066cf64fb40528c1147bb9426b3794e187bea4b9
parente412109818a7e1b77c3cc955cadf56b34dde44a5 (diff)
Add support for recursive object loading
If an object of a type needs to be loaded recursively, then it is addded to the delayed loading list which is processed once the statements are unlocked.
-rw-r--r--odb/cache-traits.hxx36
-rw-r--r--odb/result.hxx4
-rw-r--r--odb/result.txx36
3 files changed, 44 insertions, 32 deletions
diff --git a/odb/cache-traits.hxx b/odb/cache-traits.hxx
index 5d32624..a475d35 100644
--- a/odb/cache-traits.hxx
+++ b/odb/cache-traits.hxx
@@ -27,12 +27,10 @@ namespace odb
struct insert_guard
{
insert_guard (const position_type& pos): pos_ (pos) {}
+ ~insert_guard () {erase (pos_);}
- ~insert_guard ()
- {
- if (pos_.map_ != 0)
- session::current ().erase<element_type> (pos_);
- }
+ position_type
+ position () const {return pos_;}
void
release () {pos_.map_ = 0;}
@@ -65,6 +63,13 @@ namespace odb
if (session::has_current ())
session::current ().erase<element_type> (db, id);
}
+
+ static void
+ erase (const position_type& p)
+ {
+ if (p.map_ != 0)
+ session::current ().erase<element_type> (p);
+ }
};
// Unique pointers don't work with the object cache.
@@ -80,7 +85,12 @@ namespace odb
struct insert_guard
{
insert_guard (const position_type&) {}
- void release () {}
+
+ position_type
+ position () const {return position_type ();}
+
+ void
+ release () {}
};
static position_type
@@ -94,6 +104,9 @@ namespace odb
static void
erase (database&, const id_type&) {}
+
+ static void
+ erase (const position_type&) {}
};
// Caching traits for objects passed by reference. Only if the object
@@ -108,12 +121,19 @@ namespace odb
typedef typename object_traits<element_type>::pointer_type pointer_type;
typedef typename object_traits<element_type>::id_type id_type;
- struct position_type {};
+ typedef
+ typename pointer_cache_traits<pointer_type>::position_type
+ position_type;
struct insert_guard
{
insert_guard (const position_type&) {}
- void release () {}
+
+ position_type
+ position () const {return position_type ();}
+
+ void
+ release () {}
};
static position_type
diff --git a/odb/result.hxx b/odb/result.hxx
index e87374e..cc7495f 100644
--- a/odb/result.hxx
+++ b/odb/result.hxx
@@ -77,10 +77,10 @@ namespace odb
protected:
virtual void
- current (object_type&) = 0;
+ load (object_type&) = 0;
virtual id_type
- current_id () = 0;
+ load_id () = 0;
virtual void
next () = 0;
diff --git a/odb/result.txx b/odb/result.txx
index 603ee54..1cbf6f7 100644
--- a/odb/result.txx
+++ b/odb/result.txx
@@ -25,20 +25,17 @@ namespace odb
{
if (!session::has_current ())
{
- // Non-const pointer.
- //
- unrestricted_pointer_type p (object_traits::create ());
- object_type& r (unrestricted_pointer_traits::get_ref (p));
-
- current (pointer_type (p));
- current (r);
+ unrestricted_pointer_type up (object_traits::create ());
+ object_type& obj (unrestricted_pointer_traits::get_ref (up));
+ current (pointer_type (up));
+ load (obj);
}
else
{
- const id_type& id (current_id ());
-
// First check the session.
//
+ const id_type& id (load_id ());
+
pointer_type p (
pointer_cache_traits<pointer_type>::find (database (), id));
@@ -50,14 +47,12 @@ namespace odb
typename
pointer_cache_traits<unrestricted_pointer_type>::insert_guard ig (
- pointer_cache_traits<unrestricted_pointer_type>::insert (
- database (), id, up));
-
- object_type& r (unrestricted_pointer_traits::get_ref (up));
+ pointer_cache_traits<unrestricted_pointer_type>::insert (
+ database (), id, up));
+ object_type& obj (unrestricted_pointer_traits::get_ref (up));
current (pointer_type (up));
- current (r);
-
+ load (obj);
ig.release ();
}
}
@@ -72,22 +67,19 @@ namespace odb
template <typename T>
void result_iterator<T>::
- load (object_type& x)
+ load (object_type& obj)
{
if (res_->end ())
return;
if (!session::has_current ())
- res_->current (x);
+ res_->load (obj);
else
{
- const id_type& id (res_->current_id ());
-
typename reference_cache_traits<object_type>::insert_guard ig (
reference_cache_traits<object_type>::insert (
- res_->database (), id, x));
-
- res_->current (x);
+ res_->database (), res_->load_id (), obj));
+ res_->load (obj);
ig.release ();
}
}