~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to plugin/logging_query/logging_query.cc

  • Committer: Mark Atwood
  • Date: 2008-10-17 20:35:11 UTC
  • mto: (520.1.13 drizzle)
  • mto: This revision was merged to the branch mainline in revision 530.
  • Revision ID: mark@fallenpegasus.com-20081017203511-q1s2pruvxf6d7it2
fixes as per MontyT's comments, prep for internationalization

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* 
2
 
 -*- mode: c++; c-basic-offset: 2; indent-tabs-mode: nil; -*-
 
1
/* -*- mode: c++; c-basic-offset: 2; indent-tabs-mode: nil; -*-
3
2
 *  vim:expandtab:shiftwidth=2:tabstop=2:smarttab:
4
 
 
 
3
 *
5
4
 *  Copyright (C) 2008 Mark Atwood
6
5
 *
7
6
 *  This program is free software; you can redistribute it and/or modify
16
15
 *  You should have received a copy of the GNU General Public License
17
16
 *  along with this program; if not, write to the Free Software
18
17
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
19
 
 
20
18
 */
21
19
 
22
20
/* need to define DRIZZLE_SERVER to get inside the THD */
28
26
#define MAX_MSG_LEN (32*1024)
29
27
 
30
28
static char* logging_query_filename= NULL;
 
29
static bool logging_query_enable= true;
 
30
static ulong logging_query_enable_time= 0;
 
31
static ulong logging_query_thresh_slow= 0;
 
32
static ulong logging_query_thresh_bigret= 0;
 
33
static ulong logging_query_thresh_bigexa= 0;
31
34
 
32
35
static int fd= -1;
33
36
 
72
75
  /*
73
76
    The following loop is here because gettimeofday may fail on some systems
74
77
  */
75
 
  while (gettimeofday(&t, NULL) != 0)
76
 
  {}
 
78
  while (gettimeofday(&t, NULL) != 0) {}
77
79
  newtime= (uint64_t)t.tv_sec * 1000000 + t.tv_usec;
78
80
  return newtime;
79
81
#endif  /* defined(HAVE_GETHRTIME) */
80
82
}
81
83
 
 
84
/* we could just not have a pre entrypoint at all,
 
85
   and have logging_pre == NULL
 
86
   but we have this here for the sake of being an example */
 
87
bool logging_query_func_pre (THD *thd __attribute__((unused)))
 
88
{
 
89
  return false;
 
90
}
82
91
 
83
 
bool logging_query_func_pre (THD *thd)
 
92
bool logging_query_func_post (THD *thd)
84
93
{
85
94
  char msgbuf[MAX_MSG_LEN];
86
95
  int msgbuf_len= 0;
87
96
  int wrv;
88
97
 
89
 
  if (fd < 0) 
90
 
    return false;
 
98
  if (fd < 0) return false;
91
99
 
92
100
  assert(thd != NULL);
93
101
 
106
114
  /* todo, the THD should have a "utime command completed" inside
107
115
     itself, so be more accurate, and so plugins dont have to keep
108
116
     calling current_utime, which can be slow */
109
 
 
110
 
  uint64_t t_mark= get_microtime();
111
 
 
112
 
  msgbuf_len=
113
 
    snprintf(msgbuf, MAX_MSG_LEN,
114
 
             "log bgn thread_id=%ld query_id=%ld"
115
 
             " t_connect=%lld"
116
 
             " command=%.*s"
117
 
             " db=\"%.*s\" query=\"%.*s\"\n",
118
 
             (unsigned long) thd->thread_id,
119
 
             (unsigned long) thd->query_id,
120
 
             t_mark - thd->connect_utime,
121
 
             (uint32_t)command_name[thd->command].length,
122
 
             command_name[thd->command].str,
123
 
             thd->db_length, thd->db,
124
 
             thd->query_length, thd->query);
125
 
  /* a single write has a OS level thread lock
126
 
     so there is no need to have mutexes guarding this write,
127
 
  */
128
 
  wrv= write(fd, msgbuf, msgbuf_len);
129
 
  assert(wrv == msgbuf_len);
130
 
 
131
 
  return false;
132
 
}
133
 
 
134
 
bool logging_query_func_post (THD *thd)
135
 
{
136
 
  char msgbuf[MAX_MSG_LEN];
137
 
  int msgbuf_len= 0;
138
 
  int wrv;
139
 
 
140
 
  if (fd < 0) return false;
141
 
 
142
 
  assert(thd != NULL);
143
 
 
144
 
  /* todo, the THD should have a "utime command completed" inside
145
 
     itself, so be more accurate, and so plugins dont have to keep
146
 
     calling current_utime, which can be slow */
147
 
  uint64_t t_mark= get_microtime();
148
 
 
149
 
  msgbuf_len=
150
 
    snprintf(msgbuf, MAX_MSG_LEN,
151
 
             "log end thread_id=%ld query_id=%ld"
152
 
             " t_connect=%lld t_start=%lld t_lock=%lld"
153
 
             " command=%.*s"
154
 
             " rows_sent=%ld rows_examined=%u\n",
 
117
  uint64_t t_mark= get_microtime();
 
118
 
 
119
  msgbuf_len=
 
120
    snprintf(msgbuf, MAX_MSG_LEN,
 
121
             _("thread_id=%ld query_id=%ld"
 
122
               " t_connect=%lld t_start=%lld t_lock=%lld"
 
123
               " command=%.*s"
 
124
               " rows_sent=%ld rows_examined=%u\n"
 
125
               " db=\"%.*s\" query=\"%.*s\"\n"),
155
126
             (unsigned long) thd->thread_id, 
156
127
             (unsigned long) thd->query_id,
157
128
             t_mark - thd->connect_utime,
160
131
             (uint32_t)command_name[thd->command].length,
161
132
             command_name[thd->command].str,
162
133
             (unsigned long) thd->sent_row_count,
163
 
             (uint32_t) thd->examined_row_count);
 
134
             (uint32_t) thd->examined_row_count,
 
135
             thd->db_length, thd->db,
 
136
             thd->query_length, thd->query);
164
137
  /* a single write has a OS level thread lock
165
138
     so there is no need to have mutexes guarding this write,
166
139
  */
167
140
  wrv= write(fd, msgbuf, msgbuf_len);
168
141
  assert(wrv == msgbuf_len);
169
142
 
170
 
 
171
143
  return false;
172
144
}
173
145
 
187
159
           S_IRUSR|S_IWUSR);
188
160
  if (fd < 0) 
189
161
  {
190
 
    fprintf(stderr, "fail open fn=%s er=%s\n",
191
 
            logging_query_filename,
192
 
            strerror(errno));
 
162
    sql_print_error(_("fail open() fn=%s er=%s\n"),
 
163
                    logging_query_filename,
 
164
                    strerror(errno));
193
165
 
194
166
    /* todo
195
167
       we should return an error here, so the plugin doesnt load
223
195
  return 0;
224
196
}
225
197
 
226
 
static DRIZZLE_SYSVAR_STR(filename, logging_query_filename,
 
198
static DRIZZLE_SYSVAR_STR(
 
199
  filename,
 
200
  logging_query_filename,
227
201
  PLUGIN_VAR_READONLY,
228
 
  "File to log queries to.",
229
 
  NULL, NULL, NULL);
 
202
  N_("File to log to"),
 
203
  NULL, /* check func */
 
204
  NULL, /* update func*/
 
205
  NULL /* default */);
 
206
 
 
207
static DRIZZLE_SYSVAR_BOOL(
 
208
  enable,
 
209
  logging_query_enable,
 
210
  PLUGIN_VAR_NOCMDARG,
 
211
  N_("Enable logging"),
 
212
  NULL, /* check func */
 
213
  NULL, /* update func */
 
214
  true /* default */);
 
215
 
 
216
static DRIZZLE_SYSVAR_ULONG(
 
217
  enable_time,
 
218
  logging_query_enable_time,
 
219
  PLUGIN_VAR_OPCMDARG,
 
220
  N_("Disable after this many seconds. Zero for forever"),
 
221
  NULL, /* check func */
 
222
  NULL, /* update func */
 
223
  0, /* default */
 
224
  0, /* min */
 
225
  ULONG_MAX, /* max */
 
226
  0 /* blksiz */);
 
227
 
 
228
static DRIZZLE_SYSVAR_ULONG(
 
229
  thresh_slow,
 
230
  logging_query_thresh_slow,
 
231
  PLUGIN_VAR_OPCMDARG,
 
232
  N_("Threshold for logging slow queries, in microseconds"),
 
233
  NULL, /* check func */
 
234
  NULL, /* update func */
 
235
  0, /* default */
 
236
  0, /* min */
 
237
  ULONG_MAX, /* max */
 
238
  0 /* blksiz */);
 
239
 
 
240
static DRIZZLE_SYSVAR_ULONG(
 
241
  thresh_bigret,
 
242
  logging_query_thresh_bigret,
 
243
  PLUGIN_VAR_OPCMDARG,
 
244
  N_("Threshold for logging big queries, for rows returned"),
 
245
  NULL, /* check func */
 
246
  NULL, /* update func */
 
247
  0, /* default */
 
248
  0, /* min */
 
249
  ULONG_MAX, /* max */
 
250
  0 /* blksiz */);
 
251
 
 
252
static DRIZZLE_SYSVAR_ULONG(
 
253
  thresh_bigexa,
 
254
  logging_query_thresh_bigexa,
 
255
  PLUGIN_VAR_OPCMDARG,
 
256
  N_("Threshold for logging big queries, for rows examined"),
 
257
  NULL, /* check func */
 
258
  NULL, /* update func */
 
259
  0, /* default */
 
260
  0, /* min */
 
261
  ULONG_MAX, /* max */
 
262
  0 /* blksiz */);
230
263
 
231
264
static struct st_mysql_sys_var* logging_query_system_variables[]= {
232
265
  DRIZZLE_SYSVAR(filename),
 
266
  DRIZZLE_SYSVAR(enable),
 
267
  DRIZZLE_SYSVAR(enable_time),
 
268
  DRIZZLE_SYSVAR(thresh_slow),
 
269
  DRIZZLE_SYSVAR(thresh_bigret),
 
270
  DRIZZLE_SYSVAR(thresh_bigexa),
233
271
  NULL
234
272
};
235
273
 
239
277
  "logging_query",
240
278
  "0.1",
241
279
  "Mark Atwood <mark@fallenpegasus.com>",
242
 
  "Log queries",
 
280
  N_("Log queries to a file"),
243
281
  PLUGIN_LICENSE_GPL,
244
282
  logging_query_plugin_init,
245
283
  logging_query_plugin_deinit,