diff options
author | Boris Kolpackov <boris@codesynthesis.com> | 2010-08-10 11:16:42 +0200 |
---|---|---|
committer | Boris Kolpackov <boris@codesynthesis.com> | 2010-08-10 11:16:42 +0200 |
commit | ec6b9f59d40b2c389496f8e6af6bce64944af998 (patch) | |
tree | b042d94161432c66336972471a82dcdca9cb3eea | |
parent | 3d1ccd52f417c6e5e333e4f48130b043106215ad (diff) |
Add query support
-rw-r--r-- | odb/database.hxx | 16 | ||||
-rw-r--r-- | odb/database.txx | 24 | ||||
-rw-r--r-- | odb/forward.hxx | 3 | ||||
-rw-r--r-- | odb/query.hxx | 38 | ||||
-rw-r--r-- | odb/result.hxx | 188 | ||||
-rw-r--r-- | odb/result.txx | 13 |
6 files changed, 282 insertions, 0 deletions
diff --git a/odb/database.hxx b/odb/database.hxx index bfd6b0b..1b3a6d6 100644 --- a/odb/database.hxx +++ b/odb/database.hxx @@ -8,6 +8,8 @@ #include <odb/traits.hxx> #include <odb/forward.hxx> +#include <odb/query.hxx> +#include <odb/result.hxx> namespace odb { @@ -66,6 +68,20 @@ namespace odb void erase (typename object_traits<T>::id_type const& id); + // Object query API. + // + template <typename T> + shared_ptr<result_impl<T> > + query (); + + template <typename T> + shared_ptr<result_impl<T> > + query (const std::string&); + + template <typename T> + shared_ptr<result_impl<T> > + query (const odb::query<T>&); + // Transaction API. // public: diff --git a/odb/database.txx b/odb/database.txx index 402fc0b..7440127 100644 --- a/odb/database.txx +++ b/odb/database.txx @@ -92,4 +92,28 @@ namespace odb object_traits<T>::erase (*this, id); } + + template <typename T> + shared_ptr<result_impl<T> > database:: + query () + { + return query (odb::query<T> ()); + } + + template <typename T> + shared_ptr<result_impl<T> > database:: + query (const std::string& q) + { + return query (odb::query<T> (q)); + } + + template <typename T> + shared_ptr<result_impl<T> > database:: + query (const odb::query<T>& q) + { + if (!transaction::has_current ()) + throw not_in_transaction (); + + return object_traits<T>::query (*this, q); + } } diff --git a/odb/forward.hxx b/odb/forward.hxx index 8e91407..7c1fb27 100644 --- a/odb/forward.hxx +++ b/odb/forward.hxx @@ -12,6 +12,9 @@ namespace odb class transaction; template <typename T> + class query; + + template <typename T> class shared_ptr; class access diff --git a/odb/query.hxx b/odb/query.hxx new file mode 100644 index 0000000..d52e1cc --- /dev/null +++ b/odb/query.hxx @@ -0,0 +1,38 @@ +// file : odb/query.hxx +// author : Boris Kolpackov <boris@codesynthesis.com> +// copyright : Copyright (c) 2009-2010 Code Synthesis Tools CC +// license : GNU GPL v2; see accompanying LICENSE file + +#ifndef ODB_QUERY_HXX +#define ODB_QUERY_HXX + +#include <string> + +#include <odb/forward.hxx> +#include <odb/traits.hxx> + +namespace odb +{ + template <typename T> + class query: public object_traits<T>::query_type + { + public: + typedef typename object_traits<T>::query_type base_type; + + query () + { + } + + query (const std::string& q) + : base_type (q) + { + } + + query (const base_type& q) + : base_type (q) + { + } + }; +} + +#endif // ODB_QUERY_HXX diff --git a/odb/result.hxx b/odb/result.hxx new file mode 100644 index 0000000..979988a --- /dev/null +++ b/odb/result.hxx @@ -0,0 +1,188 @@ +// file : odb/result.hxx +// author : Boris Kolpackov <boris@codesynthesis.com> +// copyright : Copyright (c) 2009-2010 Code Synthesis Tools CC +// license : GNU GPL v2; see accompanying LICENSE file + +#ifndef ODB_RESULT_HXX +#define ODB_RESULT_HXX + +#include <cstddef> // std::ptrdiff_t, std::size_t +#include <iterator> // iterator categories + +#include <odb/forward.hxx> +#include <odb/shared-ptr.hxx> + +namespace odb +{ + template <typename T> + class result; + + template <typename T> + class result_impl; + + template <typename T> + class result_iterator + { + public: + typedef typename object_traits<T>::pointer_type value_type; + typedef value_type& reference; + typedef value_type* pointer; + typedef std::ptrdiff_t difference_type; + typedef std::input_iterator_tag iterator_category; + + public: + result_iterator () + : res_ (0) + { + } + + explicit + result_iterator (result_impl<T>& res) + : res_ (&res) + { + } + + // Input iterator requirements. + // + public: + value_type + operator* () const + { + return res_->current (true); + } + + // Our value_type is already a pointer so return it instead of + // a pointer to it (operator-> will just have to go one deeper + // in the latter case). + // + value_type + operator-> () const + { + return res_->current (false); + } + + result_iterator& + operator++ () + { + res_->next (); + return *this; + } + + result_iterator + operator++ (int) + { + // All non-end iterators for a result object move together. + // + res_->next (); + return *this; + } + + bool + equal (const result_iterator& j) + { + return (res_ ? res_->current (false) : 0) == + (j.res_ ? j.res_->current (false) : 0); + } + + private: + result_impl<T>* res_; + }; + + // Input iterator requirements. + // + template <typename T> + inline bool + operator== (result_iterator<T> i, result_iterator<T> j) + { + return i.equal (j); + } + + template <typename T> + inline bool + operator!= (result_iterator<T> i, result_iterator<T> j) + { + return !i.equal (j); + } + + // + // + template <typename T> + class result_impl: public shared_base + { + public: + virtual + ~result_impl (); + + protected: + friend class result<T>; + friend class result_iterator<T>; + + virtual typename object_traits<T>::pointer_type + current (bool release) = 0; + + virtual void + next () = 0; + }; + + template <typename T> + class result + { + public: + typedef typename object_traits<T>::pointer_type value_type; + typedef value_type* pointer; + typedef const value_type* const_pointer; + typedef value_type& reference; + typedef const value_type& const_reference; + + typedef result_iterator<T> iterator; + + typedef std::size_t size_type; + typedef std::ptrdiff_t difference_type; + + public: + result (shared_ptr<result_impl<T> > impl) + : impl_ (impl) + { + } + + /* + result& + operator= (shared_ptr<result_impl<T> > impl) + { + impl_ = impl; + } + */ + + public: + iterator + begin () + { + return iterator (*impl_); + } + + iterator + end () + { + return iterator (); + } + + public: + operator shared_ptr<result_impl<T> > () + { + return impl_; + } + + // Copying or assignment of results is not supported. + // + private: + result (const result&); + result& operator= (const result&); + + private: + shared_ptr<result_impl<T> > impl_; + }; +} + +#include <odb/result.txx> + +#endif // ODB_RESULT_HXX diff --git a/odb/result.txx b/odb/result.txx new file mode 100644 index 0000000..4b77c7e --- /dev/null +++ b/odb/result.txx @@ -0,0 +1,13 @@ +// file : odb/result.txx +// author : Boris Kolpackov <boris@codesynthesis.com> +// copyright : Copyright (c) 2009-2010 Code Synthesis Tools CC +// license : GNU GPL v2; see accompanying LICENSE file + +namespace odb +{ + template <typename T> + result_impl<T>:: + ~result_impl () + { + } +} |