odb对象关系映射系统
总结:将头文件中的C++类代码映射到数据库,实现对类对象的持久化,查找和更新
开发者在头文件写C++可持久化类代码,通过odb编译器生成.cxx, .hxx, .ixx(inline file), .sql(Generated code)。然后编译成目标文件,链接libodb.a(ODB Common Runtime)和数据库libodb-pgsql.a(ODB PGSQL Runtime),生成可执行文件(进而与数据库交互)
odb-arch:
odb-flow:
libodb: compilers,details,tr1
libboost: boost
libpgsql: pgsql
lib目录:
libodb.a,libodb.la
libodb-boost.a,libodb-boost.la
libodb-pgsql.a,libodb-pgsql.la
//odb compiler
输入头文件,输出C++类代码
odb -I.../libodb -d mysql --generate-query person.hxx
生成person-odb.hxx, person-odb.ixx, person-odb.cxx
odb -d mysql --generate-query --generate-schema person.hxx
生成person-odb.hxx, person-odb.ixx, person-odb.cxx,person.sql
使用这个命令进行进行编译
odb -I "../include" --std c++11 --database pgsql --profile boost --generate-schema --hxx-prologue "#include \"traits-pgsql.hxx\"" --generate-query ids.h
//
#include <string>
#include <odb/core.hxx> // (1) 包含odb::access等
#pragma db object // (2) 放类定义前,告诉odb编译器接下来的类是persistent
class person
{
...
private:
person () {} // (3) odb生成的数据库支持代码使用该默认构造函数
friend class odb::access; // (4) 使默认构造函数能访问数据库支持代码,如果默认构造函数是public的,就不用
#pragma db id auto // (5)
unsigned long id_; // (5) 唯一标识符
std::string first_;
std::string last_;
unsigned short age_;
};
query::age.in(1,3,5) 最多5个值
query::age.in_range(begin,end)
query q1 (query::age < age); // By value.
query q2 (query::age < query::_val (age)); // By value.
query q3 (query::age < query::_ref (age)); // By reference.
query q4 ("age < " + age); // Error.
query q5 ("age < " + query::_val (age)); // By value.
query q6 ("age < " + query::_ref (age)); // By reference.
原生sql必须要显示使用_val或者_ref
Transactions(事务)
#include <odb/transaction.hxx>
transaction t (db.begin ())
// Perform database operations.
t.commit ();
The odb::transaction class has the following interface:
namespace odb
{
class transaction
{
public:
typedef odb::database database_type;
typedef odb::connection connection_type;
explicit
transaction (transaction_impl*, bool make_current = true);
transaction ();
void
reset (transaction_impl*, bool make_current = true);
void
commit (); // 提交事务
void
rollback (); // 回滚事务
database_type&
database (); // 当前database
connection_type&
connection (); // 当前connection
bool
finilized () const;
public:
static bool
has_current ();
static transaction&
current (); // 返回当前**的事务
static void
current (transaction&); // **当前事务
static bool
reset_current ();
// Callback API.
//
public:
...
};
}
除非事务被显式的commit或者roll back,否则当事务实例离开作用域的时候,析构函数会自动回滚
如果我们尝试commit或者roll back一个已经finalized的事务,会抛出odb::transaction_already_finalized
transaction t1 (db1.begin ()); // Active transaction.
transaction t2 (db2.begin (), false); // Not active.
// Perform database operations on db1.
transaction::current (t2); // Deactivate t1, activate t2.
// Perform database operations on db2.
transaction::current (t1); // Switch back to t1.
// Perform some more database operations on db1.
t1.commit ();
transaction::current (t2); // Switch to t2.
// Perform some more database operations on db2.
t2.commit ();