Skip to content

Commit 3922329

Browse files
committed
Add innodb-extra-system-table-prefixes option
Now you can add to the list of prefixes that designates a table as a "system" table for accounting purposes, rather than a user table. A prefix is a database name. For example, "use foo ; select * from bar" queries the table "foo/bar". If "foo/" is in the prefix list, then queries against "foo/bar" will be treated as system queries. System queries get counted against system {read,inserted,updated,deleted} metrics rather than the equivalent user metrics. At PlanetScale, this is important because the user rows_read metric is a major input to the billing system and Insights. The `innodb-extra-system-table-prefixes` option works on the command line: ``` --innodb-extra-system-table-prefixes=foo,bar ``` or in my.cnf: ``` [mysqld] rows-read-exclude-users = vt_repl,orc_client_user innodb-extra-system-table-prefixes = foo,bar ``` It cannot be shown using `SHOW VARIABLE like ...` syntax or set using `SET variable = ...` syntax. Specified prefix match a table spec iff they match up to a comma. Specifying a prefix `foo/` is the same as specifying a prefix `foo`. `foo` will only match `foo/something`, not `football/something`.
1 parent 9d871c2 commit 3922329

File tree

3 files changed

+46
-0
lines changed

3 files changed

+46
-0
lines changed

storage/innobase/dict/mem.cc

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ this program; if not, write to the Free Software Foundation, Inc.,
3535
other files in library. The code in this file is used to make a library for
3636
external tools. */
3737

38+
#include <algorithm>
3839
#include <new>
3940

4041
#include "dict0dict.h"
@@ -157,19 +158,39 @@ static std::vector<std::string> innobase_system_databases({
157158
static bool dict_mem_table_is_system(const std::string &name) {
158159
/* Table has the following format: database/table and some system table are
159160
of the form SYS_* */
161+
printf("PIKI: is_system?(\"%s\")\n", name.c_str());
160162
if (name.find('/') == std::string::npos) {
163+
printf("PIKI: true, no slash\n");
161164
return true;
162165
}
163166

164167
for (auto p : innobase_system_databases) {
168+
printf("PIKI: compare to \"%s\"\n", p.c_str());
165169
if (name.length() > p.length() && name.compare(0, p.length(), p) == 0) {
170+
printf("PIKI: true\n");
166171
return true;
167172
}
168173
}
169174

175+
printf("PIKI: false\n");
170176
return false;
171177
}
172178

179+
void dict_add_system_prefix(const char *pfx) {
180+
printf("PIKI: add \"%s\"\n", pfx);
181+
if (!pfx || !pfx[0])
182+
return;
183+
std::string pfx_s = pfx;
184+
if (pfx_s[pfx_s.size()-1] != '/')
185+
pfx_s += '/';
186+
if (std::find(innobase_system_databases.begin(), innobase_system_databases.end(), pfx_s) == innobase_system_databases.end()) {
187+
innobase_system_databases.push_back(pfx_s);
188+
}
189+
else {
190+
printf("PIKI: already present\n");
191+
}
192+
}
193+
173194
/** Creates a table memory object.
174195
@return own: table object */
175196
dict_table_t *dict_mem_table_create(

storage/innobase/dict/mem.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,4 +91,9 @@ const char *dict_add_col_name(const char *col_names, /*!< in: existing column
9191
ulint cols, /*!< in: number of existing columns */
9292
const char *name, /*!< in: new column name */
9393
mem_heap_t *heap); /*!< in: heap */
94+
95+
/** Add the prefix 'pfx' to the list of database names that count as
96+
* system tables, rather than user tables, for the purposes of rows
97+
* {read,inserted,updated,deleted} counters. */
98+
void dict_add_system_prefix(const char *pfx);
9499
#endif

storage/innobase/handler/ha_innodb.cc

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -269,6 +269,10 @@ static ulong innodb_flush_method;
269269
stopword table to be used */
270270
static char *innobase_server_stopword_table = nullptr;
271271

272+
/* A comma-separated list of prefixes that designate system (not user) tables
273+
for metrics accounting. See also dict_mem_table_is_system. */
274+
static char *extra_system_table_prefixes = nullptr;
275+
272276
/* Below we have boolean-valued start-up parameters, and their default
273277
values */
274278

@@ -5177,6 +5181,15 @@ static int innobase_init_files(dict_init_mode_t dict_init_mode,
51775181
/* Turn on monitor counters that are default on */
51785182
srv_mon_default_on();
51795183

5184+
if (extra_system_table_prefixes) {
5185+
char *copy = strdup(extra_system_table_prefixes);
5186+
char *saveptr, *tok;
5187+
for (tok=my_strtok_r(copy, ",", &saveptr); tok; tok=my_strtok_r(NULL, ",", &saveptr)) {
5188+
dict_add_system_prefix(tok);
5189+
}
5190+
free(copy);
5191+
}
5192+
51805193
/* Unit Tests */
51815194
#ifdef UNIV_ENABLE_UNIT_TEST_GET_PARENT_DIR
51825195
unit_test_os_file_get_parent_dir();
@@ -21362,6 +21375,12 @@ static MYSQL_SYSVAR_STR(ft_server_stopword_table,
2136221375
"The user supplied stopword table name.",
2136321376
innodb_stopword_table_validate, nullptr, nullptr);
2136421377

21378+
static MYSQL_SYSVAR_STR(extra_system_table_prefixes,
21379+
extra_system_table_prefixes,
21380+
PLUGIN_VAR_READONLY | PLUGIN_VAR_NOSYSVAR | PLUGIN_VAR_RQCMDARG,
21381+
"Additional prefixes that designate system (not user) tables for metrics accounting.",
21382+
nullptr, nullptr, nullptr);
21383+
2136521384
static MYSQL_SYSVAR_UINT(flush_log_at_timeout, srv_flush_log_at_timeout,
2136621385
PLUGIN_VAR_OPCMDARG,
2136721386
"Write and flush logs every (n) second.", nullptr,
@@ -22546,6 +22565,7 @@ static SYS_VAR *innobase_system_variables[] = {
2254622565
MYSQL_SYSVAR(ft_aux_table),
2254722566
MYSQL_SYSVAR(ft_enable_diag_print),
2254822567
MYSQL_SYSVAR(ft_server_stopword_table),
22568+
MYSQL_SYSVAR(extra_system_table_prefixes),
2254922569
MYSQL_SYSVAR(ft_user_stopword_table),
2255022570
MYSQL_SYSVAR(disable_sort_file_cache),
2255122571
MYSQL_SYSVAR(stats_on_metadata),

0 commit comments

Comments
 (0)