00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041 #ifndef MYSQLPP_SQL_QUERY_H
00042 #define MYSQLPP_SQL_QUERY_H
00043
00044 #include "defs.h"
00045 #include "sql_string.h"
00046 #include "tiny_int.h"
00047
00048 #include <sstream>
00049 #include <vector>
00050 #include <map>
00051
00053 #define mysql_query_define0(RETURN, FUNC)\
00054 RETURN FUNC (ss a)\
00055 {return FUNC (parms() << a);}\
00056 RETURN FUNC (ss a, ss b)\
00057 {return FUNC (parms() << a << b);}\
00058 RETURN FUNC (ss a, ss b, ss c)\
00059 {return FUNC (parms() << a << b << c);}\
00060 RETURN FUNC (ss a, ss b, ss c, ss d)\
00061 {return FUNC (parms() << a << b << c << d);}\
00062 RETURN FUNC (ss a, ss b, ss c, ss d, ss e)\
00063 {return FUNC (parms() << a << b << c << d << e);} \
00064 RETURN FUNC (ss a, ss b, ss c, ss d, ss e, ss f)\
00065 {return FUNC (parms() << a << b << c << d << e << f);}\
00066 RETURN FUNC (ss a, ss b, ss c, ss d, ss e, ss f, ss g)\
00067 {return FUNC (parms() << a << b << c << d << e << f << g);}\
00068 RETURN FUNC (ss a, ss b, ss c, ss d, ss e, ss f, ss g, ss h)\
00069 {return FUNC (parms() << a << b << c << d << e << f << g << h);}\
00070 RETURN FUNC (ss a, ss b, ss c, ss d, ss e, ss f, ss g, ss h, ss i)\
00071 {return FUNC (parms() << a << b << c << d << e << f << g << h << i);}\
00072 RETURN FUNC (ss a,ss b,ss c,ss d,ss e,ss f,ss g,ss h,ss i,ss j)\
00073 {return FUNC (parms() <<a <<b <<c <<d <<e <<f <<g <<h <<i <<j);}\
00074 RETURN FUNC (ss a,ss b,ss c,ss d,ss e,ss f,ss g,ss h,ss i,ss j,ss k)\
00075 {return FUNC (parms() <<a <<b <<c <<d <<e <<f <<g <<h <<i <<j <<k);}\
00076 RETURN FUNC (ss a,ss b,ss c,ss d,ss e,ss f,ss g,ss h,ss i,ss j,ss k,\
00077 ss l)\
00078 {return FUNC (parms() <<a <<b <<c <<d <<e <<f <<g <<h <<i <<j <<k <<l);}\
00079
00080 namespace mysqlpp {
00081
00082 class Query;
00083 class SQLQuery;
00084
00085
00088 class SQLQueryParms : public std::vector<SQLString>
00089 {
00090 private:
00091 friend class Query;
00092
00093 typedef const SQLString& ss;
00094 SQLQuery *parent;
00095
00096 public:
00098 SQLQueryParms() :
00099 parent(0)
00100 {
00101 }
00102
00107 SQLQueryParms(SQLQuery* p) :
00108 parent(p)
00109 {
00110 }
00111
00115 bool bound()
00116 {
00117 return parent != 0;
00118 }
00119
00121 void clear()
00122 {
00123 erase(begin(), end());
00124 }
00125
00127 SQLString& operator [](size_type n)
00128 {
00129 if (n >= size())
00130 insert(end(), (n + 1) - size(), "");
00131 return std::vector<SQLString>::operator [](n);
00132 }
00133
00135 const SQLString& operator [](size_type n) const
00136 {
00137 return std::vector<SQLString>::operator [](n);
00138 }
00139
00141 SQLString& operator [](const char *str);
00142
00144 const SQLString& operator [](const char *str) const;
00145
00147 SQLQueryParms& operator <<(const SQLString& str)
00148 {
00149 push_back(str);
00150 return *this;
00151 }
00152
00154 SQLQueryParms& operator +=(const SQLString& str)
00155 {
00156 push_back(str);
00157 return *this;
00158 }
00159
00169 SQLQueryParms operator +(const SQLQueryParms& other) const;
00170
00171 #if !defined(DOXYGEN_IGNORE)
00172
00173 void set(ss a)
00174 {
00175 clear();
00176 *this << a;
00177 }
00178 void set(ss a, ss b)
00179 {
00180 clear();
00181 *this << a << b;
00182 }
00183 void set(ss a, ss b, ss c)
00184 {
00185 clear();
00186 *this << a << b << c;
00187 }
00188 void set(ss a, ss b, ss c, ss d)
00189 {
00190 clear();
00191 *this << a << b << c << d;
00192 }
00193 void set(ss a, ss b, ss c, ss d, ss e)
00194 {
00195 clear();
00196 *this << a << b << c << d << e;
00197 }
00198 void set(ss a, ss b, ss c, ss d, ss e, ss f)
00199 {
00200 clear();
00201 *this << a << b << c << d << e << f;
00202 }
00203 void set(ss a, ss b, ss c, ss d, ss e, ss f, ss g)
00204 {
00205 clear();
00206 *this << a << b << c << d << e << f << g;
00207 }
00208 void set(ss a, ss b, ss c, ss d, ss e, ss f, ss g, ss h)
00209 {
00210 clear();
00211 *this << a << b << c << d << e << f << g << h;
00212 }
00213 void set(ss a, ss b, ss c, ss d, ss e, ss f, ss g, ss h, ss i)
00214 {
00215 clear();
00216 *this << a << b << c << d << e << f << g << h << i;
00217 }
00218 void set(ss a, ss b, ss c, ss d, ss e, ss f, ss g, ss h, ss i,
00219 ss j)
00220 {
00221 clear();
00222 *this << a << b << c << d << e << f << g << h << i << j;
00223 }
00224 void set(ss a, ss b, ss c, ss d, ss e, ss f, ss g, ss h, ss i,
00225 ss j, ss k)
00226 {
00227 clear();
00228 *this << a << b << c << d << e << f << g << h << i << j << k;
00229 }
00230 #endif // !defined(DOXYGEN_IGNORE)
00231
00237 void set(ss a, ss b, ss c, ss d, ss e, ss f, ss g, ss h, ss i,
00238 ss j, ss k, ss l)
00239 {
00240 clear();
00241 *this << a << b << c << d << e << f << g << h << i << j << k << l;
00242 }
00243 };
00244
00245
00248 enum query_reset { DONT_RESET, RESET_QUERY };
00249
00250
00272
00273 struct SQLParseElement {
00279 SQLParseElement(std::string b, char o, char n) :
00280 before(b),
00281 option(o),
00282 num(n)
00283 {
00284 }
00285
00286 std::string before;
00287 char option;
00288 char num;
00289 };
00290
00291
00312 class SQLQuery : public std::stringstream
00313 {
00314 private:
00315 friend class SQLQueryParms;
00316
00317 char *preview_char();
00318
00319 protected:
00320 bool Success;
00321 char* errmsg;
00322
00324 std::vector<SQLParseElement> parsed;
00325
00328 std::vector<std::string> parsed_names;
00329
00331 std::map<std::string, int> parsed_nums;
00332
00333 typedef const SQLString& ss;
00334 typedef SQLQueryParms parms;
00335
00337 void proc(SQLQueryParms& p);
00338
00339 public:
00341 SQLQuery() :
00342 std::stringstream(),
00343 Success(false),
00344 errmsg(0),
00345 def(this)
00346 {
00347 }
00348
00350 SQLQuery(const SQLQuery& q);
00351
00355 SQLQueryParms def;
00356
00364 void parse();
00365
00370 std::string error() const
00371 {
00372 return errmsg;
00373 }
00374
00376 bool success() const { return Success; }
00377
00379 operator bool() { return success(); }
00380
00382 bool operator !() { return !success(); }
00383
00388 void reset();
00389
00395 template <class T>
00396 SQLQuery& update(const T& o, const T& n)
00397 {
00398 reset();
00399
00400
00401
00402
00403 dynamic_cast<std::stringstream&>(*this) << "UPDATE " <<
00404 o.table() << " SET " << n.equal_list() << " WHERE " <<
00405 o.equal_list(" AND ", sql_use_compare);
00406 return *this;
00407 }
00408
00412 template <class T>
00413 SQLQuery& insert(const T& v)
00414 {
00415 reset();
00416
00417
00418 dynamic_cast<std::stringstream&>(*this) << "INSERT INTO " <<
00419 v.table() << " (" << v.field_list() << ") VALUES (" <<
00420 v.value_list() << ")";
00421 return *this;
00422 }
00423
00429 template <class Iter>
00430 SQLQuery& insert(Iter first, Iter last)
00431 {
00432 reset();
00433 if (first == last) {
00434 return *this;
00435 }
00436
00437
00438 dynamic_cast<std::stringstream&>(*this) << "INSERT INTO " <<
00439 first->table() << " (" << first->field_list() <<
00440 ") VALUES (" << first->value_list() << ')';
00441
00442 Iter it = first + 1;
00443 while (it != last) {
00444 dynamic_cast<std::stringstream&>(*this) << ",(" <<
00445 it->value_list() << ')';
00446 ++it;
00447 }
00448
00449 return *this;
00450 }
00451
00457 template <class T>
00458 SQLQuery& replace(const T& v)
00459 {
00460 reset();
00461
00462
00463 dynamic_cast<std::stringstream&>(*this) << "REPLACE INTO " <<
00464 v.table() << " (" << v.field_list() << ") VALUES (" <<
00465 v.value_list() << ")";
00466 return *this;
00467 }
00468
00470 std::string str()
00471 {
00472 return str(def);
00473 }
00474
00479 std::string str(query_reset r)
00480 {
00481 return str(def, r);
00482 }
00483
00488 std::string str(SQLQueryParms& p);
00489
00496 std::string str(SQLQueryParms& p, query_reset r);
00497
00498 #if !defined(DOXYGEN_IGNORE)
00499
00500 mysql_query_define0(std::string, str);
00501 #endif // !defined(DOXYGEN_IGNORE)
00502 };
00503
00504
00505 inline SQLString& SQLQueryParms::operator [](const char* str)
00506 {
00507 if (parent) {
00508 return operator [](parent->parsed_nums[str]);
00509 }
00510 throw;
00511 }
00512
00513 inline const SQLString& SQLQueryParms::operator[] (const char* str) const
00514 {
00515 if (parent) {
00516 return operator [](parent->parsed_nums[str]);
00517 }
00518 throw;
00519 }
00520
00521 }
00522
00523 #endif
00524