[Home]People/PaulHarris

BOOST WIKI | People | RecentChanges | Preferences | Page List | Links List

Difference (from prior major revision) (no other diffs)

Changed: 3,109c3
Time to think about Boost::DB, and this is my hopefully unobtrusive thought-page on the topic.

I have been contributing to the DTL for some time now, and I'd like to see something like it added to boost. I've taken a look at SOCI, and I really like its syntax... however I'm not sure if it would work in major projects since there isn't much activity on the mailing list yet, but it has huge potential.

So, my focus is figuring out how to rewrite the DTL in a boost-friendly fashion. This will serve as a public thinkpad so I don't bombard the mailing lists with stupid questions and ideas.


My application is 99% static tables and rows and other things, so I'm more interested in getting strong type safety and using template-specialisations to specify how the database is accessed. The database follows the application, so the database must conform or else chaos reigns. I could use serialisation, but I want multi-users, multi-threading and the ability to use raw SQL queries occasionally.

Use Cases




Note: While it is really handy to have a global database connection to utilise at any time, like dtl::DBConnection, I personally would prefer if multiple independent connections were possible. If the user wants a global connection, then let them use a singleton.

Read a single value ===


SOCI ====
unsigned int value;
sql << "select value from table" << into(value);
cout << value << endl;
Pros


* Really simple, easy to understand.
* Potential for into() specialisation.
Cons


* Does not build the query for you.
* Error-prone, easy to screw it up if you have to select from that table many times.
* You can cache a pre-defined query in Statement, but I'm not sure how powerful that would be.

Of course, you could just do:
unsigned int get_value( Session& sql )
{
unsigned int value;
sql << "select value from table" << into(value);
return value;
}

cout << get_value(sql) << endl;

DTL




struct Row
{
unsigned int value;
};

namespace dtl
{
template <>
struct DefaultBCA?<Row>
{
void operator()( BoundIOs? & b, Row & r )
{
b["value"] == r;
}
};
}

DBView<Row> view("table");
unsigned int value = *view.begin();
cout << value << endl;

There are less verbose ways using anonymous BCAs, but this is how I do it. TODO.
Pros


* This is a bad example, the DTL works much better when you want more than one row.
Cons


* Hard to do a quick query.
* Really verbose.
* Hello templates, namespaces, and other steep-learning-curve things.
* Still need to specify the table name.

An adaption of the DTL for my own twisted needs




namespace dtl
{
DefaultBCA? AS ABOVE

template <>
struct TableInfo?<Row>
{
static std::string desc() { return "Table"; }
static std::string table() { return "table"; }
static std::string postfix() { return ""; }
};

// a helper function - not quite what I use, but close enough
template <class Data>
void get_row( Data & x )
{
DBView<Data> view(
TableInfo?<Data>::table(),
DefaultBCA?<Data>(),
TableInfo?<Data>::postfix());
typename DBView<Data>::select_iterator row = view.begin();
assert(row != view.end());
x = *row;
}

}

Row whatnot;
dtl::get_row(whatnot);
cout << whatnot.value << endl;
Here is an attempt to create an idea of how the "ideal" database library would work.

Added: 110a5
(I think I'll do a draft on my PC first)

I am a lone programmer who is silly enough to enjoy diving head-first into big projects.

Here is an attempt to create an idea of how the "ideal" database library would work.

(I think I'll do a draft on my PC first)


BOOST WIKI | People | RecentChanges | Preferences | Page List | Links List
Edit text of this page | View other revisions
Last edited June 28, 2005 3:37 am (diff)
Search:
Disclaimer: This site not officially maintained by Boost Developers