mirror of
https://github.com/MariaDB/server.git
synced 2025-08-08 11:22:35 +03:00
MDEV-27306: SET STATEMENT optimizer_trace=1 Doesn't save the trace
In mysql_execute_command(), move optimizer trace initialization to be after run_set_statement_if_requested() call. Unfortunately, mysql_execute_command() code uses "goto error" a lot, and this means optimizer trace code cannot use RAII objects. Work this around by: - Make Opt_trace_start a non-RAII object, add init() method. - Move the code that writes the top-level object and array into Opt_trace_start::init().
This commit is contained in:
@@ -9248,5 +9248,22 @@ json_detailed(json_extract(trace, '$**.best_join_order'))
|
|||||||
]
|
]
|
||||||
]
|
]
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
|
#
|
||||||
|
# MDEV-27306: SET STATEMENT optimizer_trace=1 Doesn't save the trace
|
||||||
|
#
|
||||||
|
set optimizer_trace=0;
|
||||||
|
set statement optimizer_trace=1 for select * from seq_1_to_10 where seq<2;
|
||||||
|
seq
|
||||||
|
1
|
||||||
|
# The trace must not be empty:
|
||||||
|
select left(trace, 100) from information_schema.optimizer_trace;
|
||||||
|
left(trace, 100)
|
||||||
|
{
|
||||||
|
"steps": [
|
||||||
|
{
|
||||||
|
"join_preparation": {
|
||||||
|
"select_id": 1,
|
||||||
|
"steps": [
|
||||||
|
|
||||||
# End of 10.6 tests
|
# End of 10.6 tests
|
||||||
set optimizer_trace='enabled=off';
|
set optimizer_trace='enabled=off';
|
||||||
|
@@ -865,5 +865,13 @@ select json_detailed(json_extract(trace, '$**.best_join_order'))
|
|||||||
from information_schema.OPTIMIZER_TRACE;
|
from information_schema.OPTIMIZER_TRACE;
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # MDEV-27306: SET STATEMENT optimizer_trace=1 Doesn't save the trace
|
||||||
|
--echo #
|
||||||
|
set optimizer_trace=0;
|
||||||
|
set statement optimizer_trace=1 for select * from seq_1_to_10 where seq<2;
|
||||||
|
--echo # The trace must not be empty:
|
||||||
|
select left(trace, 100) from information_schema.optimizer_trace;
|
||||||
|
|
||||||
--echo # End of 10.6 tests
|
--echo # End of 10.6 tests
|
||||||
set optimizer_trace='enabled=off';
|
set optimizer_trace='enabled=off';
|
||||||
|
@@ -471,12 +471,14 @@ void Opt_trace_context::end()
|
|||||||
current_trace= NULL;
|
current_trace= NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
Opt_trace_start::Opt_trace_start(THD *thd, TABLE_LIST *tbl,
|
|
||||||
enum enum_sql_command sql_command,
|
void Opt_trace_start::init(THD *thd,
|
||||||
List<set_var_base> *set_vars,
|
TABLE_LIST *tbl,
|
||||||
const char *query,
|
enum enum_sql_command sql_command,
|
||||||
size_t query_length,
|
List<set_var_base> *set_vars,
|
||||||
const CHARSET_INFO *query_charset):ctx(&thd->opt_trace)
|
const char *query,
|
||||||
|
size_t query_length,
|
||||||
|
const CHARSET_INFO *query_charset)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
if optimizer trace is enabled and the statment we have is traceable,
|
if optimizer trace is enabled and the statment we have is traceable,
|
||||||
@@ -496,6 +498,9 @@ Opt_trace_start::Opt_trace_start(THD *thd, TABLE_LIST *tbl,
|
|||||||
ctx->set_query(query, query_length, query_charset);
|
ctx->set_query(query, query_length, query_charset);
|
||||||
traceable= TRUE;
|
traceable= TRUE;
|
||||||
opt_trace_disable_if_no_tables_access(thd, tbl);
|
opt_trace_disable_if_no_tables_access(thd, tbl);
|
||||||
|
Json_writer *w= ctx->get_current_json();
|
||||||
|
w->start_object();
|
||||||
|
w->add_member("steps").start_array();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -503,6 +508,9 @@ Opt_trace_start::~Opt_trace_start()
|
|||||||
{
|
{
|
||||||
if (traceable)
|
if (traceable)
|
||||||
{
|
{
|
||||||
|
Json_writer *w= ctx->get_current_json();
|
||||||
|
w->end_array();
|
||||||
|
w->end_object();
|
||||||
ctx->end();
|
ctx->end();
|
||||||
traceable= FALSE;
|
traceable= FALSE;
|
||||||
}
|
}
|
||||||
|
@@ -72,14 +72,18 @@ struct Opt_trace_info
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
class Opt_trace_start {
|
class Opt_trace_start
|
||||||
|
{
|
||||||
public:
|
public:
|
||||||
Opt_trace_start(THD *thd_arg, TABLE_LIST *tbl,
|
Opt_trace_start(THD *thd_arg): ctx(&thd_arg->opt_trace), traceable(false) {}
|
||||||
enum enum_sql_command sql_command,
|
|
||||||
List<set_var_base> *set_vars,
|
void init(THD *thd, TABLE_LIST *tbl,
|
||||||
const char *query,
|
enum enum_sql_command sql_command,
|
||||||
size_t query_length,
|
List<set_var_base> *set_vars,
|
||||||
const CHARSET_INFO *query_charset);
|
const char *query,
|
||||||
|
size_t query_length,
|
||||||
|
const CHARSET_INFO *query_charset);
|
||||||
|
|
||||||
~Opt_trace_start();
|
~Opt_trace_start();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
@@ -3489,10 +3489,9 @@ sp_lex_keeper::reset_lex_and_exec_core(THD *thd, uint *nextp,
|
|||||||
thd->lex->safe_to_cache_query= 0;
|
thd->lex->safe_to_cache_query= 0;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
Opt_trace_start ots(thd, m_lex->query_tables,
|
Opt_trace_start ots(thd);
|
||||||
SQLCOM_SELECT, &m_lex->var_list,
|
ots.init(thd, m_lex->query_tables, SQLCOM_SELECT, &m_lex->var_list,
|
||||||
NULL, 0,
|
NULL, 0, thd->variables.character_set_client);
|
||||||
thd->variables.character_set_client);
|
|
||||||
|
|
||||||
Json_writer_object trace_command(thd);
|
Json_writer_object trace_command(thd);
|
||||||
Json_writer_array trace_command_steps(thd, "steps");
|
Json_writer_array trace_command_steps(thd, "steps");
|
||||||
|
@@ -3644,12 +3644,7 @@ mysql_execute_command(THD *thd, bool is_called_from_prepared_stmt)
|
|||||||
#ifdef HAVE_REPLICATION
|
#ifdef HAVE_REPLICATION
|
||||||
} /* endif unlikely slave */
|
} /* endif unlikely slave */
|
||||||
#endif
|
#endif
|
||||||
Opt_trace_start ots(thd, all_tables, lex->sql_command, &lex->var_list,
|
Opt_trace_start ots(thd);
|
||||||
thd->query(), thd->query_length(),
|
|
||||||
thd->variables.character_set_client);
|
|
||||||
|
|
||||||
Json_writer_object trace_command(thd);
|
|
||||||
Json_writer_array trace_command_steps(thd, "steps");
|
|
||||||
|
|
||||||
/* store old value of binlog format */
|
/* store old value of binlog format */
|
||||||
enum_binlog_format orig_binlog_format,orig_current_stmt_binlog_format;
|
enum_binlog_format orig_binlog_format,orig_current_stmt_binlog_format;
|
||||||
@@ -3715,6 +3710,10 @@ mysql_execute_command(THD *thd, bool is_called_from_prepared_stmt)
|
|||||||
if (run_set_statement_if_requested(thd, lex))
|
if (run_set_statement_if_requested(thd, lex))
|
||||||
goto error;
|
goto error;
|
||||||
|
|
||||||
|
/* After SET STATEMENT is done, we can initialize the Optimizer Trace: */
|
||||||
|
ots.init(thd, all_tables, lex->sql_command, &lex->var_list, thd->query(),
|
||||||
|
thd->query_length(), thd->variables.character_set_client);
|
||||||
|
|
||||||
if (thd->lex->mi.connection_name.str == NULL)
|
if (thd->lex->mi.connection_name.str == NULL)
|
||||||
thd->lex->mi.connection_name= thd->variables.default_master_connection;
|
thd->lex->mi.connection_name= thd->variables.default_master_connection;
|
||||||
|
|
||||||
|
@@ -2437,9 +2437,9 @@ static bool check_prepared_statement(Prepared_statement *stmt)
|
|||||||
For the optimizer trace, this is the symmetric, for statement preparation,
|
For the optimizer trace, this is the symmetric, for statement preparation,
|
||||||
of what is done at statement execution (in mysql_execute_command()).
|
of what is done at statement execution (in mysql_execute_command()).
|
||||||
*/
|
*/
|
||||||
Opt_trace_start ots(thd, tables, lex->sql_command, &lex->var_list,
|
Opt_trace_start ots(thd);
|
||||||
thd->query(), thd->query_length(),
|
ots.init(thd, tables, lex->sql_command, &lex->var_list, thd->query(),
|
||||||
thd->variables.character_set_client);
|
thd->query_length(), thd->variables.character_set_client);
|
||||||
|
|
||||||
Json_writer_object trace_command(thd);
|
Json_writer_object trace_command(thd);
|
||||||
Json_writer_array trace_command_steps(thd, "steps");
|
Json_writer_array trace_command_steps(thd, "steps");
|
||||||
|
Reference in New Issue
Block a user