~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to plugin/hello_events/hello_events.cc

Merge Joe, plus I updated the tests.

Show diffs side-by-side

added added

removed removed

Lines of Context:
25
25
 * This plugin is an example events plugin that just prints some info for
26
26
 * the events that it is tracking. 
27
27
 *  
28
 
set global hello_events1_enable = ON;
29
 
set global hello_events1_watch_databases = "x";   
30
 
set global hello_events1_watch_tables = "x,y";
 
28
set global hello_events_enable = ON;
 
29
set global hello_events_watch_databases = "x";   
 
30
set global hello_events_watch_tables = "x,y";
31
31
 
32
32
 */
33
33
 
34
34
#include "config.h"
35
35
#include <string>
36
36
#include <cstdio>
37
 
#include <boost/program_options.hpp>
38
 
#include <drizzled/module/option_map.h>
 
37
 
39
38
#include "drizzled/session.h"
40
39
#include "hello_events.h"
41
40
 
42
 
namespace po= boost::program_options;
43
41
using namespace drizzled;
44
42
using namespace plugin;
45
43
using namespace std;
46
44
 
47
45
#define PLUGIN_NAME "hello_events1"
48
46
 
49
 
static bool sysvar_hello_events_enabled;
 
47
static bool sysvar_hello_events_enabled= true;
50
48
static HelloEvents *hello_events= NULL;
51
 
static string sysvar_db_list;
52
 
static string sysvar_table_list;
 
49
static char *sysvar_table_list= NULL;
 
50
static char *sysvar_db_list= NULL;
53
51
 
54
52
/*
55
53
 * Event observer positions are used to set the order in which
65
63
 * or the last position (-1) in the calling order, for example it makes no sence 
66
64
 * to initially ask to be called in position 13.
67
65
 */
68
 
typedef constrained_check<uint64_t, INT32_MAX-1, 1> position_constraint;
69
 
typedef constrained_check<int32_t, -1, INT32_MIN+1> post_drop_constraint;
70
 
 
71
 
static position_constraint sysvar_before_write_position;      // Call this event observer first.
72
 
static position_constraint sysvar_before_update_position;
73
 
static post_drop_constraint sysvar_post_drop_db_position;  // I want my event observer to be called last. No reason, I just do!
 
66
static int32_t sysvar_before_write_position= 1;      // Call this event observer first.
 
67
static int32_t sysvar_before_update_position= 1;
 
68
static int32_t sysvar_post_drop_db_position= -1;  // I want my event observer to be called last. No reason, I just do!
74
69
 
75
70
 
76
71
//==================================
78
73
static bool observeBeforeInsertRecord(BeforeInsertRecordEventData &data)
79
74
{
80
75
 
81
 
  static int count= 0;
82
 
  count++;
83
 
  data.session.setVariable("BEFORE_INSERT_RECORD", boost::lexical_cast<std::string>(count));
 
76
  fprintf(stderr, PLUGIN_NAME" EVENT observeBeforeInsertRecord(%s)\n", data.table.getTableName());
84
77
  return false;
85
78
}
86
79
 
87
80
//---
88
81
static void observeAfterInsertRecord(AfterInsertRecordEventData &data)
89
82
{
90
 
  static int count= 0;
91
 
  count++;
92
 
  data.session.setVariable("AFTER_INSERT_RECORD", boost::lexical_cast<std::string>(count));
 
83
  fprintf(stderr, PLUGIN_NAME" EVENT observeAfterInsertRecord(%s) err = %d\n", data.table.getTableName(), data.err);
93
84
}
94
85
 
95
86
//---
96
87
static bool observeBeforeDeleteRecord(BeforeDeleteRecordEventData &data)
97
88
{
98
 
  static int count= 0;
99
 
  count++;
100
 
  data.session.setVariable("AFTER_DELETE_RECORD", boost::lexical_cast<std::string>(count));
 
89
  fprintf(stderr, PLUGIN_NAME" EVENT observeBeforeDeleteRecord(%s)\n", data.table.getTableName());
101
90
  return false;
102
91
}
103
92
 
104
93
//---
105
94
static void observeAfterDeleteRecord(AfterDeleteRecordEventData &data)
106
95
{
107
 
  static int count= 0;
108
 
  count++;
109
 
  data.session.setVariable("AFTER_DELETE_RECORD", boost::lexical_cast<std::string>(count));
 
96
  fprintf(stderr, PLUGIN_NAME" EVENT observeAfterDeleteRecord(%s) err = %d\n", data.table.getTableName(), data.err);
110
97
}
111
98
 
112
99
//---
113
100
static bool observeBeforeUpdateRecord(BeforeUpdateRecordEventData &data)
114
101
{
115
 
  static int count= 0;
116
 
  count++;
117
 
  data.session.setVariable("BEFORE_UPDATE_RECORD", boost::lexical_cast<std::string>(count));
 
102
  fprintf(stderr, PLUGIN_NAME" EVENT observeBeforeUpdateRecord(%s)\n", data.table.getTableName());
118
103
  return false;
119
104
}
120
105
 
121
106
//---
122
107
static void observeAfterUpdateRecord(AfterUpdateRecordEventData &data)
123
108
{
124
 
  static int count= 0;
125
 
  count++;
126
 
  data.session.setVariable("AFTER_UPDATE_RECORD", boost::lexical_cast<std::string>(count));
 
109
  fprintf(stderr, PLUGIN_NAME" EVENT observeAfterUpdateRecord(%s) err = %d\n", data.table.getTableName(), data.err);
127
110
}
128
111
 
129
112
//==================================
130
113
// My schema event observers: 
131
114
static void observeAfterDropTable(AfterDropTableEventData &data)
132
115
{
133
 
  static int count= 0;
134
 
  count++;
135
 
  data.session.setVariable("AFTER_DROP_TABLE", boost::lexical_cast<std::string>(count));
 
116
  fprintf(stderr, PLUGIN_NAME" EVENT observeAfterDropTable(%s) err = %d\n", data.table.getTableName().c_str(), data.err);
136
117
}
137
118
 
138
119
//---
139
120
static void observeAfterRenameTable(AfterRenameTableEventData &data)
140
121
{
141
 
  static int count= 0;
142
 
  count++;
143
 
  data.session.setVariable("AFTER_RENAME_TABLE", boost::lexical_cast<std::string>(count));
 
122
  fprintf(stderr, PLUGIN_NAME" EVENT observeAfterRenameTable(%s, %s) err = %d\n", data.from.getTableName().c_str(), data.to.getTableName().c_str(), data.err);
144
123
}
145
124
 
146
125
//---
147
126
static void observeAfterCreateDatabase(AfterCreateDatabaseEventData &data)
148
127
{
149
 
  static int count= 0;
150
 
  count++;
151
 
  data.session.setVariable("AFTER_CREATE_DATABASE", boost::lexical_cast<std::string>(count));
 
128
  fprintf(stderr, PLUGIN_NAME" EVENT observeAfterCreateDatabase(%s) err = %d\n", data.db.c_str(), data.err);
152
129
}
153
130
 
154
131
//---
155
132
static void observeAfterDropDatabase(AfterDropDatabaseEventData &data)
156
133
{
157
 
  static int count= 0;
158
 
  count++;
159
 
  data.session.setVariable("AFTER_DROP_DATABASE", boost::lexical_cast<std::string>(count));
160
 
}
161
 
 
162
 
//---
163
 
static void observeConnectSession(ConnectSessionEventData &data)
164
 
{
165
 
  static int count= 0;
166
 
  count++;
167
 
  data.session.setVariable("CONNECT_SESSION", boost::lexical_cast<std::string>(count));
168
 
}
169
 
 
170
 
//---
171
 
static void observeDisconnectSession(DisconnectSessionEventData &data)
172
 
{
173
 
  static int count= 0;
174
 
  count++;
175
 
  data.session.setVariable("DISCONNECT_SESSION", boost::lexical_cast<std::string>(count));
176
 
}
177
 
 
178
 
//---
179
 
static void observeBeforeStatement(BeforeStatementEventData &data)
180
 
{
181
 
  static int count= 0;
182
 
  count++;
183
 
  data.session.setVariable("BEFORE_STATEMENT", boost::lexical_cast<std::string>(count));
184
 
}
185
 
 
186
 
//---
187
 
static void observeAfterStatement(AfterStatementEventData &data)
188
 
{
189
 
  static int count= 0;
190
 
  count++;
191
 
  data.session.setVariable("AFTER_STATEMENT", boost::lexical_cast<std::string>(count));
192
 
}
193
 
 
194
 
HelloEvents::~HelloEvents()
195
 
{ }
 
134
  fprintf(stderr, PLUGIN_NAME" EVENT observeAfterDropDatabase(%s) err = %d\n", data.db.c_str(), data.err);
 
135
}
196
136
 
197
137
//==================================
198
138
/* This is where I register which table events my pluggin is interested in.*/
203
143
    || !isDatabaseInteresting(table_share.getSchemaName()))
204
144
    return;
205
145
    
206
 
  registerEvent(observers, BEFORE_INSERT_RECORD, sysvar_before_write_position.get());
207
 
  // I want to be called first if passible
 
146
  registerEvent(observers, BEFORE_INSERT_RECORD, sysvar_before_write_position); // I want to be called first if passible
208
147
  registerEvent(observers, AFTER_INSERT_RECORD);
209
 
  registerEvent(observers, BEFORE_UPDATE_RECORD, sysvar_before_update_position.get());
 
148
  registerEvent(observers, BEFORE_UPDATE_RECORD, sysvar_before_update_position);
210
149
  registerEvent(observers, AFTER_UPDATE_RECORD);
211
150
  registerEvent(observers, BEFORE_DELETE_RECORD);
212
151
  registerEvent(observers, AFTER_DELETE_RECORD);
233
172
    return;
234
173
    
235
174
  registerEvent(observers, AFTER_CREATE_DATABASE);
236
 
  registerEvent(observers, AFTER_DROP_DATABASE, sysvar_post_drop_db_position.get());
237
 
  registerEvent(observers, DISCONNECT_SESSION);
238
 
  registerEvent(observers, CONNECT_SESSION);
239
 
  registerEvent(observers, BEFORE_STATEMENT);
240
 
  registerEvent(observers, AFTER_STATEMENT);
 
175
  registerEvent(observers, AFTER_DROP_DATABASE, sysvar_post_drop_db_position);
241
176
}
242
177
 
243
178
 
288
223
    observeAfterDropDatabase((AfterDropDatabaseEventData &)data);
289
224
    break;
290
225
 
291
 
  case CONNECT_SESSION:
292
 
    observeConnectSession((ConnectSessionEventData &)data);
293
 
    break;
294
 
 
295
 
  case DISCONNECT_SESSION:
296
 
    observeDisconnectSession((DisconnectSessionEventData &)data);
297
 
    break;
298
 
 
299
 
  case BEFORE_STATEMENT:
300
 
    observeBeforeStatement((BeforeStatementEventData &)data);
301
 
    break;
302
 
 
303
 
  case AFTER_STATEMENT:
304
 
    observeAfterStatement((AfterStatementEventData &)data);
305
 
    break;
306
 
 
307
226
  default:
308
227
    fprintf(stderr, "HelloEvents: Unexpected event '%s'\n", EventObserver::eventName(data.event));
309
228
 
318
237
 
319
238
/* Plugin initialization and system variables */
320
239
 
321
 
static void enable(Session*, sql_var_t)
 
240
static void enable(Session *,
 
241
                   drizzle_sys_var *,
 
242
                   void *var_ptr,
 
243
                   const void *save)
322
244
{
323
245
  if (hello_events)
324
246
  {
325
 
    if (sysvar_hello_events_enabled)
 
247
    if (*(bool *)save != false)
326
248
    {
327
249
      hello_events->enable();
 
250
      *(bool *) var_ptr= (bool) true;
328
251
    }
329
252
    else
330
253
    {
331
254
      hello_events->disable();
 
255
      *(bool *) var_ptr= (bool) false;
332
256
    }
333
257
  }
334
258
}
335
259
 
336
260
 
337
 
static int set_db_list(Session *, set_var *var)
 
261
static void set_db_list(Session *,
 
262
                   drizzle_sys_var *, 
 
263
                   void *var_ptr,     
 
264
                   const void *save)
338
265
{
339
 
  const char *db_list= var->value->str_value.ptr();
340
 
  if (db_list == NULL)
341
 
    return 1;
342
 
 
343
266
  if (hello_events)
344
267
  {
345
 
    hello_events->setDatabasesOfInterest(db_list);
346
 
    sysvar_db_list.assign(db_list);
 
268
    hello_events->setDatabasesOfInterest(*(const char **) save);
 
269
    *(const char **) var_ptr= hello_events->getDatabasesOfInterest();
347
270
  }
348
 
  return 0;
349
271
}
350
272
 
351
 
static int set_table_list(Session *, set_var *var)
 
273
static void set_table_list(Session *,
 
274
                   drizzle_sys_var *, 
 
275
                   void *var_ptr,     
 
276
                   const void *save)
352
277
{
353
 
  const char *table_list= var->value->str_value.ptr();
354
 
  if (table_list == NULL)
355
 
    return 1;
356
 
 
357
278
  if (hello_events)
358
279
  {
359
 
    hello_events->setTablesOfInterest(table_list);
360
 
    sysvar_table_list.assign(table_list);
 
280
    hello_events->setTablesOfInterest(*(const char **) save);
 
281
    *(const char **) var_ptr= hello_events->getTablesOfInterest();
361
282
  }
362
 
  return 0;
363
283
}
364
284
 
365
285
 
374
294
    hello_events->enable();
375
295
  }
376
296
 
377
 
  context.registerVariable(new sys_var_bool_ptr("enable",
378
 
                                                &sysvar_hello_events_enabled,
379
 
                                                enable));
380
 
  context.registerVariable(new sys_var_std_string("watch_databases",
381
 
                                                  sysvar_db_list,
382
 
                                                  set_db_list));
383
 
  context.registerVariable(new sys_var_std_string("watch_tables",
384
 
                                                  sysvar_table_list,
385
 
                                                  set_table_list));
386
 
  context.registerVariable(new sys_var_constrained_value<uint64_t>("before_write_position",
387
 
                                                         sysvar_before_write_position));
388
 
  context.registerVariable(new sys_var_constrained_value<uint64_t>("before_update_position",
389
 
                                                         sysvar_before_update_position));
390
 
  context.registerVariable(new sys_var_constrained_value<int32_t>("post_drop_position",
391
 
                                                         sysvar_post_drop_db_position));
392
 
 
393
 
 
394
297
  return 0;
395
298
}
396
299
 
397
 
static void init_options(drizzled::module::option_context &context)
398
 
{
399
 
  context("enable",
400
 
          po::value<bool>(&sysvar_hello_events_enabled)->default_value(false)->zero_tokens(),
401
 
          N_("Enable Example Events Plugin"));
402
 
  context("watch-databases",
403
 
          po::value<string>(&sysvar_db_list)->default_value(""),
404
 
          N_("A comma delimited list of databases to watch"));
405
 
  context("watch-tables",
406
 
          po::value<string>(&sysvar_table_list)->default_value(""),
407
 
          N_("A comma delimited list of databases to watch"));
408
 
  context("before-write-position",
409
 
          po::value<position_constraint>(&sysvar_before_write_position)->default_value(1),
410
 
          N_("Before write row event observer call position"));
411
 
  context("before-update-position",
412
 
          po::value<position_constraint>(&sysvar_before_update_position)->default_value(1),
413
 
          N_("Before update row event observer call position"));
414
 
  context("post-drop-db-position",
415
 
          po::value<post_drop_constraint>(&sysvar_post_drop_db_position)->default_value(-1),
416
 
          N_("After drop database event observer call position"));
417
 
}
418
 
 
419
 
 
 
300
static DRIZZLE_SYSVAR_STR(watch_databases,
 
301
                           sysvar_db_list,
 
302
                           PLUGIN_VAR_OPCMDARG,
 
303
                           N_("A comma delimited list of databases to watch"),
 
304
                           NULL, /* check func */
 
305
                           set_db_list, /* update func */
 
306
                           "" /* default */);
 
307
 
 
308
static DRIZZLE_SYSVAR_STR(watch_tables,
 
309
                           sysvar_table_list,
 
310
                           PLUGIN_VAR_OPCMDARG,
 
311
                           N_("A comma delimited list of tables to watch"),
 
312
                           NULL, /* check func */
 
313
                           set_table_list, /* update func */
 
314
                           "" /* default */);
 
315
 
 
316
static DRIZZLE_SYSVAR_BOOL(enable,
 
317
                           sysvar_hello_events_enabled,
 
318
                           PLUGIN_VAR_NOCMDARG,
 
319
                           N_("Enable Example Events Plugin"),
 
320
                           NULL, /* check func */
 
321
                           enable, /* update func */
 
322
                           false /* default */);
 
323
 
 
324
static DRIZZLE_SYSVAR_INT(before_write_position,
 
325
                           sysvar_before_write_position,
 
326
                           PLUGIN_VAR_NOCMDARG,
 
327
                           N_("Before write row event observer call position"),
 
328
                           NULL, /* check func */
 
329
                           NULL, /* update func */
 
330
                           1, /* default */
 
331
                           1, /* min */
 
332
                           INT32_MAX -1, /* max */
 
333
                           0 /* blk */);
 
334
 
 
335
static DRIZZLE_SYSVAR_INT(before_update_position,
 
336
                           sysvar_before_update_position,
 
337
                           PLUGIN_VAR_NOCMDARG,
 
338
                           N_("Before update row event observer call position"),
 
339
                           NULL, /* check func */
 
340
                           NULL, /* update func */
 
341
                           1, /* default */
 
342
                           1, /* min */
 
343
                           INT32_MAX -1, /* max */
 
344
                           0 /* blk */);
 
345
 
 
346
static DRIZZLE_SYSVAR_INT(post_drop_db_position,
 
347
                           sysvar_post_drop_db_position,
 
348
                           PLUGIN_VAR_NOCMDARG,
 
349
                           N_("After drop database event observer call position"),
 
350
                           NULL, /* check func */
 
351
                           NULL, /* update func */
 
352
                           -1, /* default */
 
353
                           INT32_MIN +1, /* min */
 
354
                           -1, /* max */
 
355
                           0 /* blk */);
 
356
 
 
357
static drizzle_sys_var* system_var[]= {
 
358
  DRIZZLE_SYSVAR(watch_databases),
 
359
  DRIZZLE_SYSVAR(watch_tables),
 
360
  DRIZZLE_SYSVAR(enable),
 
361
  DRIZZLE_SYSVAR(before_write_position),
 
362
  DRIZZLE_SYSVAR(before_update_position),
 
363
  DRIZZLE_SYSVAR(post_drop_db_position),
 
364
  NULL
 
365
};
420
366
 
421
367
DRIZZLE_DECLARE_PLUGIN
422
368
{
427
373
  N_("An example events Plugin"),
428
374
  PLUGIN_LICENSE_BSD,
429
375
  init,   /* Plugin Init      */
430
 
  NULL, /* depends */
431
 
  init_options    /* config options   */
 
376
  system_var, /* system variables */
 
377
  NULL    /* config options   */
432
378
}
433
379
DRIZZLE_DECLARE_PLUGIN_END;