00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00034 #include <config.h>
00035 #include <string>
00036 #include <cstdio>
00037 #include <boost/program_options.hpp>
00038 #include <drizzled/item.h>
00039 #include <drizzled/module/option_map.h>
00040 #include <drizzled/session.h>
00041 #include <drizzled/table/instance/base.h>
00042 #include "hello_events.h"
00043
00044 namespace po= boost::program_options;
00045 using namespace drizzled;
00046 using namespace plugin;
00047 using namespace std;
00048
00049 #define PLUGIN_NAME "hello_events1"
00050
00051 static bool sysvar_hello_events_enabled;
00052 static HelloEvents *hello_events= NULL;
00053 static string sysvar_db_list;
00054 static string sysvar_table_list;
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070 typedef constrained_check<uint64_t, INT32_MAX-1, 1> position_constraint;
00071 typedef constrained_check<int32_t, -1, INT32_MIN+1> post_drop_constraint;
00072
00073 static position_constraint sysvar_before_write_position;
00074 static position_constraint sysvar_before_update_position;
00075 static post_drop_constraint sysvar_post_drop_db_position;
00076
00077
00078
00079
00080 static bool observeBeforeInsertRecord(BeforeInsertRecordEventData &data)
00081 {
00082
00083 static int count= 0;
00084 count++;
00085 data.session.setVariable("BEFORE_INSERT_RECORD", boost::lexical_cast<std::string>(count));
00086 return false;
00087 }
00088
00089
00090 static void observeAfterInsertRecord(AfterInsertRecordEventData &data)
00091 {
00092 static int count= 0;
00093 count++;
00094 data.session.setVariable("AFTER_INSERT_RECORD", boost::lexical_cast<std::string>(count));
00095 }
00096
00097
00098 static bool observeBeforeDeleteRecord(BeforeDeleteRecordEventData &data)
00099 {
00100 static int count= 0;
00101 count++;
00102 data.session.setVariable("AFTER_DELETE_RECORD", boost::lexical_cast<std::string>(count));
00103 return false;
00104 }
00105
00106
00107 static void observeAfterDeleteRecord(AfterDeleteRecordEventData &data)
00108 {
00109 static int count= 0;
00110 count++;
00111 data.session.setVariable("AFTER_DELETE_RECORD", boost::lexical_cast<std::string>(count));
00112 }
00113
00114
00115 static bool observeBeforeUpdateRecord(BeforeUpdateRecordEventData &data)
00116 {
00117 static int count= 0;
00118 count++;
00119 data.session.setVariable("BEFORE_UPDATE_RECORD", boost::lexical_cast<std::string>(count));
00120 return false;
00121 }
00122
00123
00124 static void observeAfterUpdateRecord(AfterUpdateRecordEventData &data)
00125 {
00126 static int count= 0;
00127 count++;
00128 data.session.setVariable("AFTER_UPDATE_RECORD", boost::lexical_cast<std::string>(count));
00129 }
00130
00131
00132
00133 static void observeAfterDropTable(AfterDropTableEventData &data)
00134 {
00135 static int count= 0;
00136 count++;
00137 data.session.setVariable("AFTER_DROP_TABLE", boost::lexical_cast<std::string>(count));
00138 }
00139
00140
00141 static void observeAfterRenameTable(AfterRenameTableEventData &data)
00142 {
00143 static int count= 0;
00144 count++;
00145 data.session.setVariable("AFTER_RENAME_TABLE", boost::lexical_cast<std::string>(count));
00146 }
00147
00148
00149 static void observeAfterCreateDatabase(AfterCreateDatabaseEventData &data)
00150 {
00151 static int count= 0;
00152 count++;
00153 data.session.setVariable("AFTER_CREATE_DATABASE", boost::lexical_cast<std::string>(count));
00154 }
00155
00156
00157 static void observeAfterDropDatabase(AfterDropDatabaseEventData &data)
00158 {
00159 static int count= 0;
00160 count++;
00161 data.session.setVariable("AFTER_DROP_DATABASE", boost::lexical_cast<std::string>(count));
00162 }
00163
00164
00165 static void observeConnectSession(ConnectSessionEventData &data)
00166 {
00167 static int count= 0;
00168 count++;
00169 data.session.setVariable("CONNECT_SESSION", boost::lexical_cast<std::string>(count));
00170 }
00171
00172
00173 static void observeDisconnectSession(DisconnectSessionEventData &data)
00174 {
00175 static int count= 0;
00176 count++;
00177 data.session.setVariable("DISCONNECT_SESSION", boost::lexical_cast<std::string>(count));
00178 }
00179
00180
00181 static void observeBeforeStatement(BeforeStatementEventData &data)
00182 {
00183 static int count= 0;
00184 count++;
00185 data.session.setVariable("BEFORE_STATEMENT", boost::lexical_cast<std::string>(count));
00186 }
00187
00188
00189 static void observeAfterStatement(AfterStatementEventData &data)
00190 {
00191 static int count= 0;
00192 count++;
00193 data.session.setVariable("AFTER_STATEMENT", boost::lexical_cast<std::string>(count));
00194 }
00195
00196 HelloEvents::~HelloEvents()
00197 { }
00198
00199
00200
00201 void HelloEvents::registerTableEventsDo(TableShare &table_share, EventObserverList &observers)
00202 {
00203 if ((is_enabled == false)
00204 || !isTableInteresting(table_share.getTableName())
00205 || !isDatabaseInteresting(table_share.getSchemaName()))
00206 return;
00207
00208 registerEvent(observers, BEFORE_INSERT_RECORD, sysvar_before_write_position.get());
00209
00210 registerEvent(observers, AFTER_INSERT_RECORD);
00211 registerEvent(observers, BEFORE_UPDATE_RECORD, sysvar_before_update_position.get());
00212 registerEvent(observers, AFTER_UPDATE_RECORD);
00213 registerEvent(observers, BEFORE_DELETE_RECORD);
00214 registerEvent(observers, AFTER_DELETE_RECORD);
00215 }
00216
00217
00218
00219 void HelloEvents::registerSchemaEventsDo(const std::string &db, EventObserverList &observers)
00220 {
00221 if ((is_enabled == false)
00222 || !isDatabaseInteresting(db))
00223 return;
00224
00225 registerEvent(observers, AFTER_DROP_TABLE);
00226 registerEvent(observers, AFTER_RENAME_TABLE);
00227 }
00228
00229
00230
00231 void HelloEvents::registerSessionEventsDo(Session &session, EventObserverList &observers)
00232 {
00233 if ((is_enabled == false)
00234 || !isSessionInteresting(session))
00235 return;
00236
00237 registerEvent(observers, AFTER_CREATE_DATABASE);
00238 registerEvent(observers, AFTER_DROP_DATABASE, sysvar_post_drop_db_position.get());
00239 registerEvent(observers, DISCONNECT_SESSION);
00240 registerEvent(observers, CONNECT_SESSION);
00241 registerEvent(observers, BEFORE_STATEMENT);
00242 registerEvent(observers, AFTER_STATEMENT);
00243 }
00244
00245
00246
00247
00248 bool HelloEvents::observeEventDo(EventData &data)
00249 {
00250 bool result= false;
00251
00252 switch (data.event) {
00253 case AFTER_DROP_TABLE:
00254 observeAfterDropTable((AfterDropTableEventData &)data);
00255 break;
00256
00257 case AFTER_RENAME_TABLE:
00258 observeAfterRenameTable((AfterRenameTableEventData &)data);
00259 break;
00260
00261 case BEFORE_INSERT_RECORD:
00262 result = observeBeforeInsertRecord((BeforeInsertRecordEventData &)data);
00263 break;
00264
00265 case AFTER_INSERT_RECORD:
00266 observeAfterInsertRecord((AfterInsertRecordEventData &)data);
00267 break;
00268
00269 case BEFORE_UPDATE_RECORD:
00270 result = observeBeforeUpdateRecord((BeforeUpdateRecordEventData &)data);
00271 break;
00272
00273 case AFTER_UPDATE_RECORD:
00274 observeAfterUpdateRecord((AfterUpdateRecordEventData &)data);
00275 break;
00276
00277 case BEFORE_DELETE_RECORD:
00278 result = observeBeforeDeleteRecord((BeforeDeleteRecordEventData &)data);
00279 break;
00280
00281 case AFTER_DELETE_RECORD:
00282 observeAfterDeleteRecord((AfterDeleteRecordEventData &)data);
00283 break;
00284
00285 case AFTER_CREATE_DATABASE:
00286 observeAfterCreateDatabase((AfterCreateDatabaseEventData &)data);
00287 break;
00288
00289 case AFTER_DROP_DATABASE:
00290 observeAfterDropDatabase((AfterDropDatabaseEventData &)data);
00291 break;
00292
00293 case CONNECT_SESSION:
00294 observeConnectSession((ConnectSessionEventData &)data);
00295 break;
00296
00297 case DISCONNECT_SESSION:
00298 observeDisconnectSession((DisconnectSessionEventData &)data);
00299 break;
00300
00301 case BEFORE_STATEMENT:
00302 observeBeforeStatement((BeforeStatementEventData &)data);
00303 break;
00304
00305 case AFTER_STATEMENT:
00306 observeAfterStatement((AfterStatementEventData &)data);
00307 break;
00308
00309 default:
00310 fprintf(stderr, "HelloEvents: Unexpected event '%s'\n", EventObserver::eventName(data.event));
00311
00312 }
00313
00314 return false;
00315 }
00316
00317
00318
00319
00320
00321
00322
00323 static void enable(Session*, sql_var_t)
00324 {
00325 if (hello_events)
00326 {
00327 if (sysvar_hello_events_enabled)
00328 {
00329 hello_events->enable();
00330 }
00331 else
00332 {
00333 hello_events->disable();
00334 }
00335 }
00336 }
00337
00338
00339 static int set_db_list(Session *, set_var *var)
00340 {
00341 const char *db_list= var->value->str_value.ptr();
00342 if (db_list == NULL)
00343 return 1;
00344
00345 if (hello_events)
00346 {
00347 hello_events->setDatabasesOfInterest(db_list);
00348 sysvar_db_list.assign(db_list);
00349 }
00350 return 0;
00351 }
00352
00353 static int set_table_list(Session *, set_var *var)
00354 {
00355 const char *table_list= var->value->str_value.ptr();
00356 if (table_list == NULL)
00357 return 1;
00358
00359 if (hello_events)
00360 {
00361 hello_events->setTablesOfInterest(table_list);
00362 sysvar_table_list.assign(table_list);
00363 }
00364 return 0;
00365 }
00366
00367
00368 static int init(module::Context &context)
00369 {
00370 hello_events= new HelloEvents(PLUGIN_NAME);
00371
00372 context.add(hello_events);
00373
00374 if (sysvar_hello_events_enabled)
00375 {
00376 hello_events->enable();
00377 }
00378
00379 context.registerVariable(new sys_var_bool_ptr("enable",
00380 &sysvar_hello_events_enabled,
00381 enable));
00382 context.registerVariable(new sys_var_std_string("watch_databases",
00383 sysvar_db_list,
00384 set_db_list));
00385 context.registerVariable(new sys_var_std_string("watch_tables",
00386 sysvar_table_list,
00387 set_table_list));
00388 context.registerVariable(new sys_var_constrained_value<uint64_t>("before_write_position",
00389 sysvar_before_write_position));
00390 context.registerVariable(new sys_var_constrained_value<uint64_t>("before_update_position",
00391 sysvar_before_update_position));
00392 context.registerVariable(new sys_var_constrained_value<int32_t>("post_drop_position",
00393 sysvar_post_drop_db_position));
00394
00395
00396 return 0;
00397 }
00398
00399 static void init_options(drizzled::module::option_context &context)
00400 {
00401 context("enable",
00402 po::value<bool>(&sysvar_hello_events_enabled)->default_value(false)->zero_tokens(),
00403 N_("Enable Example Events Plugin"));
00404 context("watch-databases",
00405 po::value<string>(&sysvar_db_list)->default_value(""),
00406 N_("A comma delimited list of databases to watch"));
00407 context("watch-tables",
00408 po::value<string>(&sysvar_table_list)->default_value(""),
00409 N_("A comma delimited list of databases to watch"));
00410 context("before-write-position",
00411 po::value<position_constraint>(&sysvar_before_write_position)->default_value(1),
00412 N_("Before write row event observer call position"));
00413 context("before-update-position",
00414 po::value<position_constraint>(&sysvar_before_update_position)->default_value(1),
00415 N_("Before update row event observer call position"));
00416 context("post-drop-db-position",
00417 po::value<post_drop_constraint>(&sysvar_post_drop_db_position)->default_value(-1),
00418 N_("After drop database event observer call position"));
00419 }
00420
00421
00422
00423 DRIZZLE_DECLARE_PLUGIN
00424 {
00425 DRIZZLE_VERSION_ID,
00426 PLUGIN_NAME,
00427 "0.1",
00428 "Barry Leslie",
00429 N_("An example events Plugin"),
00430 PLUGIN_LICENSE_BSD,
00431 init,
00432 NULL,
00433 init_options
00434 }
00435 DRIZZLE_DECLARE_PLUGIN_END;