00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #ifndef __PION_DATABASE_HEADER__
00021 #define __PION_DATABASE_HEADER__
00022
00023 #include <map>
00024 #include <string>
00025 #include <boost/regex.hpp>
00026 #include <pion/PionConfig.hpp>
00027 #include <pion/platform/Event.hpp>
00028 #include <pion/platform/Vocabulary.hpp>
00029 #include <pion/platform/PlatformPlugin.hpp>
00030 #include <pion/platform/Query.hpp>
00031 #include <pion/PionLogger.hpp>
00032
00033
00034 namespace pion {
00035 namespace platform {
00036
00037
00041 class PION_PLATFORM_API Database
00042 : public PlatformPlugin
00043 {
00044 public:
00045
00047 class DatabaseBusyException : public std::exception {
00048 public:
00049 virtual const char* what() const throw() {
00050 return "Database is busy. Try again later";
00051 }
00052 };
00053
00055 class QueryNotFoundException : public PionException {
00056 public:
00057 QueryNotFoundException(const std::string& query_id)
00058 : PionException("Unable find database query identified by: ", query_id) {}
00059 };
00060
00062 class OpenDatabaseException : public PionException {
00063 public:
00064 OpenDatabaseException(const std::string& db_name)
00065 : PionException("Unable to open database: ", db_name) {}
00066 };
00067
00069 class DatabaseConfigMissing: public PionException {
00070 public:
00071 DatabaseConfigMissing(const std::string& database_id)
00072 : PionException("Database template element missing: ", database_id) {}
00073 };
00074
00075 class DatabaseClientException : public PionException {
00076 public:
00077 DatabaseClientException(const std::string& database_id)
00078 : PionException("Database client not defined: ", database_id) {}
00079 };
00080
00082 class InvalidIsolationLevel : public PionException {
00083 public:
00084 InvalidIsolationLevel(const std::string& database_id)
00085 : PionException("Invalid Isolation level defined: ", database_id) {}
00086 };
00087
00089 class BadTypePair : public PionException {
00090 public:
00091 BadTypePair(const std::string& bad_pair)
00092 : PionException("Bad SQL Type pair: ", bad_pair) {}
00093 };
00094
00096 class MissingTypeMap : public PionException {
00097 public:
00098 MissingTypeMap(const std::string& database_id)
00099 : PionException("SQL Type map missing: ", database_id) {}
00100 };
00101
00102 class MissingTemplateException : public PionException {
00103 public:
00104 MissingTemplateException(const std::string& database_id)
00105 : PionException("Database template file not found: ", database_id) {}
00106 };
00107
00108 class MissingRootElementException : public PionException {
00109 public:
00110 MissingRootElementException(const std::string& database_id)
00111 : PionException("Database template file missing root element: ", database_id) {}
00112 };
00113
00114 class ReadConfigException: public PionException {
00115 public:
00116 ReadConfigException(const std::string& database_id)
00117 : PionException("Database template file not readable: ", database_id) {}
00118 };
00119
00121 Database(const std::string& logger_name)
00122 : m_isolation_level(IL_LevelUnknown), m_logger(PION_GET_LOGGER(logger_name))
00123 {}
00124
00126 virtual ~Database() {}
00127
00134 inline QueryPtr getQuery(QueryID query_id) const {
00135 QueryMap::const_iterator i = m_query_map.find(query_id);
00136 if (i == m_query_map.end())
00137 throw QueryNotFoundException(query_id);
00138 return i->second;
00139 }
00140
00146 virtual boost::shared_ptr<Database> clone(void) const = 0;
00147
00153 virtual void open(unsigned partition = 0) = 0;
00154
00156 virtual void close(void) = 0;
00157
00159 enum CACHEPARAM {
00160 CACHE_INDEX_ROW_OVERHEAD,
00161 CACHE_PAGE_CACHE_SIZE,
00162 CACHE_PAGE_UTILIZATION,
00163 DB_FILE_SIZE
00164 };
00165
00167 virtual boost::uint64_t getCache(CACHEPARAM what) = 0;
00168
00170 virtual bool is_open(void) const = 0;
00171
00178 virtual void runQuery(const std::string& sql_query, const boost::regex& suppress) = 0;
00179
00181 inline void runQuery(const std::string& sql_query)
00182 {
00183 static boost::regex no_suppress;
00184 runQuery(sql_query, no_suppress);
00185 }
00186
00193 virtual QueryPtr addQuery(QueryID query_id, const std::string& sql_query) = 0;
00194
00202 virtual void createTable(const Query::FieldMap& field_map,
00203 std::string& table_name,
00204 const Query::IndexMap& index_map,
00205 unsigned partition = 0) = 0;
00206
00213 virtual void dropTable(std::string& table_name, unsigned partition = 0) = 0;
00214
00221 virtual bool tableExists(std::string& table_name, unsigned partition = 0) = 0;
00222
00231 virtual QueryPtr prepareInsertQuery(const Query::FieldMap& field_map,
00232 const std::string& table_name) = 0;
00233
00234 virtual QueryPtr prepareInsertIgnoreQuery(const Query::FieldMap& field_map,
00235 const std::string& table_name) = 0;
00236
00245 virtual pion::platform::QueryPtr prepareFullQuery(const std::string& query, const boost::regex& suppress) = 0;
00246
00248 inline pion::platform::QueryPtr prepareFullQuery(const std::string& query)
00249 {
00250 static boost::regex no_suppress;
00251 return prepareFullQuery(query, no_suppress);
00252 }
00253
00259 virtual QueryPtr getBeginTransactionQuery(void) = 0;
00260
00266 virtual QueryPtr getCommitTransactionQuery(void) = 0;
00267
00275 virtual void setConfig(const Vocabulary& v, const xmlNodePtr config_ptr);
00276
00284 void stringReplace(std::string& src, const char* search, const std::string& substitute);
00285
00295 std::string& stringSubstitutes(std::string& query, const pion::platform::Query::FieldMap& field_map,
00296 const std::string& table_name, const std::string& columns_override = "");
00297
00299 enum IsolationLevel_t {
00300 IL_LevelUnknown = -1,
00301 IL_ReadUncommitted,
00302 IL_ReadCommitted,
00303 IL_RepeatableRead,
00304 IL_Serializable
00305 };
00306
00307 protected:
00308
00310 inline void copyDatabase(const Database& d) {
00311 PlatformPlugin::copyPlugin(d);
00312
00313 m_database_engine = d.m_database_engine;
00314 m_database_client = d.m_database_client;
00315 m_begin_insert = d.m_begin_insert;
00316 m_commit_insert = d.m_commit_insert;
00317 m_create_log = d.m_create_log;
00318 m_create_log_attr = d.m_create_log_attr;
00319 m_insert_log = d.m_insert_log;
00320 m_insert_log_attr = d.m_insert_log_attr;
00321 m_create_stat = d.m_create_stat;
00322 m_create_stat_attr = d.m_create_stat_attr;
00323 m_update_stat = d.m_update_stat;
00324 m_update_stat_attr = d.m_update_stat_attr;
00325 m_select_stat = d.m_select_stat;
00326 m_select_stat_attr = d.m_select_stat_attr;
00327 m_drop_index = d.m_drop_index;
00328 m_drop_index_attr = d.m_drop_index_attr;
00329 m_create_index_normal = d.m_create_index_normal;
00330 m_create_index_normal_attr = d.m_create_index_normal_attr;
00331 m_create_index_unique = d.m_create_index_unique;
00332 m_create_index_unique_attr = d.m_create_index_unique_attr;
00333 m_create_index_custom = d.m_create_index_custom;
00334 m_create_index_custom_attr = d.m_create_index_custom_attr;
00335 m_isolation_level = d.m_isolation_level;
00336
00337
00338 m_sql_affinity = d.m_sql_affinity;
00339 m_pre_sql = d.m_pre_sql;
00340 m_pre_sql_attr = d.m_pre_sql_attr;
00341 m_options = d.m_options;
00342 m_options_values = d.m_options_values;
00343 m_insert_ignore = d.m_insert_ignore;
00344 m_drop_table = d.m_drop_table;
00345 m_drop_table_attr = d.m_drop_table_attr;
00346 }
00347
00348
00350 typedef std::map<QueryID, QueryPtr> QueryMap;
00351
00353 static const std::string INSERT_QUERY_ID;
00354 static const std::string INSERT_IGNORE_QUERY_ID;
00355
00356
00358 static const std::string BEGIN_QUERY_ID;
00359
00361 static const std::string COMMIT_QUERY_ID;
00362
00363 static const std::string MAP_ELEMENT_NAME;
00364 static const std::string PAIR_ELEMENT_NAME;
00365
00366 static const std::string CLIENT_ELEMENT_NAME;
00367 static const std::string BEGIN_ELEMENT_NAME;
00368 static const std::string COMMIT_ELEMENT_NAME;
00369 static const std::string CREATE_LOG_ELEMENT_NAME;
00370 static const std::string INSERT_LOG_ELEMENT_NAME;
00371 static const std::string ISOLATION_ELEMENT_NAME;
00372 static const std::string PRESQL_ELEMENT_NAME;
00373 static const std::string OPTION_ELEMENT_NAME;
00374
00375 static const std::string CREATE_STAT_ELEMENT_NAME;
00376 static const std::string UPDATE_STAT_ELEMENT_NAME;
00377 static const std::string SELECT_STAT_ELEMENT_NAME;
00378
00379 static const std::string DROP_INDEX_ELEMENT_NAME;
00380 static const std::string CREATE_INDEX_NORMAL_ELEMENT_NAME;
00381 static const std::string CREATE_INDEX_UNIQUE_ELEMENT_NAME;
00382 static const std::string CREATE_INDEX_CUSTOM_ELEMENT_NAME;
00383
00384 static const std::string IGNORE_ATTRIBUTE_NAME;
00385 static const std::string OPTION_ATTRIBUTE_NAME;
00386
00387 static const std::string INSERT_IGNORE_ELEMENT_NAME;
00388 static const std::string DROP_TABLE_ELEMENT_NAME;
00389
00390
00397 void readConfig(const xmlNodePtr config_ptr, std::string engine_str);
00398
00404 void readConfigDetails(const xmlNodePtr config_ptr);
00405
00408 std::string m_database_engine;
00409
00411 std::string m_database_client;
00412
00414 std::string m_begin_insert;
00415 std::string m_commit_insert;
00416
00418 std::string m_create_log;
00419 boost::regex m_create_log_attr;
00420
00421 std::string m_insert_log;
00422 boost::regex m_insert_log_attr;
00423
00424 std::string m_create_stat;
00425 boost::regex m_create_stat_attr;
00426
00427 std::string m_update_stat;
00428 boost::regex m_update_stat_attr;
00429
00430 std::string m_select_stat;
00431 boost::regex m_select_stat_attr;
00432
00433 std::string m_drop_index;
00434 boost::regex m_drop_index_attr;
00435
00436 std::string m_create_index_normal;
00437 boost::regex m_create_index_normal_attr;
00438
00439 std::string m_create_index_unique;
00440 boost::regex m_create_index_unique_attr;
00441
00442 std::string m_create_index_custom;
00443 boost::regex m_create_index_custom_attr;
00444
00445 std::string m_insert_ignore;
00446 boost::regex m_insert_ignore_attr;
00447
00448 std::string m_drop_table;
00449 boost::regex m_drop_table_attr;
00450
00452 IsolationLevel_t m_isolation_level;
00453
00455 QueryMap m_query_map;
00456
00458 std::vector<std::string> m_sql_affinity;
00459
00461 std::vector<std::string> m_pre_sql;
00462
00464 std::vector<boost::regex> m_pre_sql_attr;
00465
00467 std::vector<std::string> m_options;
00468
00470 std::vector<std::string> m_options_values;
00471
00473 PionLogger m_logger;
00474 };
00475
00476
00478 typedef boost::shared_ptr<Database> DatabasePtr;
00479
00480
00481
00482
00483
00484
00485
00486
00487
00488
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498
00499
00500
00501
00502
00503
00504
00505
00506 }
00507 }
00508
00509 #endif