From 70960e7ab7e1d8d1872cd6882ce4a5d870283288 Mon Sep 17 00:00:00 2001 From: Oleksandr Byelkin Date: Sun, 12 Apr 2015 15:56:21 +1000 Subject: [PATCH 01/23] MDEV-6916: Upgrade from MySQL to MariaDB breaks already created views mysql_upgrade upgrades views` from r4408: missing files from mysql-test/std_data/mysql_upgrade/* --- client/mysql_upgrade.c | 69 +++++++++++++++++++++++- client/mysqlcheck.c | 45 +++++++++++++--- mysql-test/r/mysql_upgrade_view.result | 74 ++++++++++++++++++++++++++ mysql-test/t/mysql_upgrade_view.test | 53 ++++++++++++++++++ 4 files changed, 232 insertions(+), 9 deletions(-) create mode 100644 mysql-test/r/mysql_upgrade_view.result create mode 100644 mysql-test/t/mysql_upgrade_view.test diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index 5fb3b1317d9..acb480da570 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -40,7 +40,8 @@ static char mysql_path[FN_REFLEN]; static char mysqlcheck_path[FN_REFLEN]; static my_bool opt_force, opt_verbose, debug_info_flag, debug_check_flag, - opt_systables_only, opt_version_check; + opt_systables_only, opt_version_check, + opt_mysql_upgrade= 0, opt_skip_mysql_upgrade= 0; static my_bool opt_not_used, opt_silent; static uint my_end_arg= 0; static char *opt_user= (char*)"root"; @@ -150,6 +151,14 @@ static struct my_option my_long_options[]= &opt_not_used, &opt_not_used, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0}, {"version", 'V', "Output version information and exit.", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, + {"mysql-upgrade", 'y', + "Skip automatic detection MySQL and assume that we upgrade it", + &opt_mysql_upgrade, &opt_mysql_upgrade, 0, GET_BOOL, NO_ARG, + 0, 0, 0, 0, 0, 0}, + {"skip-mysql-upgrade", 'Y', + "Skip view algorithm upgrade from MySQL", + &opt_skip_mysql_upgrade, &opt_skip_mysql_upgrade, 0, GET_BOOL, NO_ARG, + 0, 0, 0, 0, 0, 0}, {"version-check", 'k', "Run this program only if its \'server version\' " "matches the version of the server to which it's connecting, (enabled by " "default); use --skip-version-check to avoid this check. Note: the \'server " @@ -344,6 +353,14 @@ get_one_option(int optid, const struct my_option *opt, case OPT_DEFAULT_AUTH: /* --default-auth */ add_one_option(&conn_args, opt, argument); break; + case 'y': + opt_mysql_upgrade= 1; + add_option= FALSE; + break; + case 'Y': + opt_skip_mysql_upgrade= 1; + add_option= FALSE; + break; } if (add_option) @@ -754,6 +771,23 @@ static int run_mysqlcheck_upgrade(void) NULL); } +static int run_mysqlcheck_views(void) +{ + if (!opt_mysql_upgrade) + return 0; + verbose("Phase 0: Fixing views"); + print_conn_args("mysqlcheck"); + return run_tool(mysqlcheck_path, + NULL, /* Send output from mysqlcheck directly to screen */ + "--no-defaults", + ds_args.str, + "--all-databases", + "--mysql-upgrade", + opt_verbose ? "--verbose": "", + opt_silent ? "--silent": "", + "2>&1", + NULL); +} static int run_mysqlcheck_fixnames(void) { @@ -928,6 +962,28 @@ static int check_version_match(void) return 0; } +#define EVENTS_STRUCT_LEN 7000 + +my_bool is_mysql() +{ + my_bool ret= TRUE; + DYNAMIC_STRING ds_events_struct; + + if (init_dynamic_string(&ds_events_struct, NULL, + EVENTS_STRUCT_LEN, EVENTS_STRUCT_LEN)) + die("Out of memory"); + + if (run_query("show create table mysql.event", + &ds_events_struct, FALSE) || + strstr(ds_events_struct.str, "IGNORE_BAD_TABLE_OPTIONS") != NULL) + ret= FALSE; + else + verbose("MySQL upgrade detected"); + + dynstr_free(&ds_events_struct); + return(ret); +} + int main(int argc, char **argv) { @@ -997,11 +1053,20 @@ int main(int argc, char **argv) if (opt_version_check && check_version_match()) die("Upgrade failed"); + if (!opt_systables_only && !opt_skip_mysql_upgrade) + { + if (!opt_mysql_upgrade) + opt_mysql_upgrade= is_mysql(); + } + else + opt_mysql_upgrade= 0; + /* Run "mysqlcheck" and "mysql_fix_privilege_tables.sql" */ if ((!opt_systables_only && - (run_mysqlcheck_fixnames() || run_mysqlcheck_upgrade())) || + (run_mysqlcheck_views() || + run_mysqlcheck_fixnames() || run_mysqlcheck_upgrade())) || run_sql_fix_privilege_tables()) { /* diff --git a/client/mysqlcheck.c b/client/mysqlcheck.c index a4549432c2c..7446d75d0a3 100644 --- a/client/mysqlcheck.c +++ b/client/mysqlcheck.c @@ -42,7 +42,8 @@ static my_bool opt_alldbs = 0, opt_check_only_changed = 0, opt_extended = 0, opt_medium_check = 0, opt_quick = 0, opt_all_in_1 = 0, opt_silent = 0, opt_auto_repair = 0, ignore_errors = 0, tty_password= 0, opt_frm= 0, debug_info_flag= 0, debug_check_flag= 0, - opt_fix_table_names= 0, opt_fix_db_names= 0, opt_upgrade= 0; + opt_fix_table_names= 0, opt_fix_db_names= 0, opt_upgrade= 0, + opt_mysql_upgrade= 0; static my_bool opt_write_binlog= 1, opt_flush_tables= 0; static uint verbose = 0, opt_mysql_port=0; static int my_end_arg; @@ -196,6 +197,9 @@ static struct my_option my_long_options[] = NO_ARG, 0, 0, 0, 0, 0, 0}, {"version", 'V', "Output version information and exit.", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, + {"mysql-upgrade", 'y', + "Fix view algorithm view field if it is not new MariaDB view.", + 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0} }; @@ -332,7 +336,13 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), case 'v': verbose++; break; - case 'V': print_version(); exit(0); + case 'V': + print_version(); exit(0); + break; + case 'y': + what_to_do= DO_REPAIR; + opt_mysql_upgrade= 1; + break; case OPT_MYSQL_PROTOCOL: opt_protocol= find_type_or_exit(argument, &sql_protocol_typelib, opt->name); @@ -587,7 +597,15 @@ static int process_all_tables_in_db(char *database) for (end = tables + 1; (row = mysql_fetch_row(res)) ;) { if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) - continue; + { + if (!opt_mysql_upgrade) + continue; + } + else + { + if (opt_mysql_upgrade) + continue; + } end= fix_table_name(end, row[0]); *end++= ','; @@ -603,7 +621,15 @@ static int process_all_tables_in_db(char *database) { /* Skip views if we don't perform renaming. */ if ((what_to_do != DO_UPGRADE) && (num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) - continue; + { + if (!opt_mysql_upgrade) + continue; + } + else + { + if (opt_mysql_upgrade) + continue; + } if (system_database && (!strcmp(row[0], "general_log") || !strcmp(row[0], "slow_log"))) @@ -748,10 +774,12 @@ static int handle_request_for_tables(char *tables, uint length) if (opt_upgrade) end = strmov(end, " FOR UPGRADE"); break; case DO_REPAIR: - op= (opt_write_binlog) ? "REPAIR" : "REPAIR NO_WRITE_TO_BINLOG"; + op= ((opt_write_binlog || opt_mysql_upgrade) ? + "REPAIR" : "REPAIR NO_WRITE_TO_BINLOG"); if (opt_quick) end = strmov(end, " QUICK"); if (opt_extended) end = strmov(end, " EXTENDED"); if (opt_frm) end = strmov(end, " USE_FRM"); + if (opt_mysql_upgrade) end = strmov(end, " FROM MYSQL"); break; case DO_ANALYZE: op= (opt_write_binlog) ? "ANALYZE" : "ANALYZE NO_WRITE_TO_BINLOG"; @@ -768,14 +796,17 @@ static int handle_request_for_tables(char *tables, uint length) if (opt_all_in_1) { /* No backticks here as we added them before */ - query_length= sprintf(query, "%s TABLE %s %s", op, tables, options); + query_length= sprintf(query, "%s %s %s %s", op, + (opt_mysql_upgrade ? "VIEW" : "TABLE"), + tables, options); table_name= tables; } else { char *ptr, *org; - org= ptr= strmov(strmov(query, op), " TABLE "); + org= ptr= strmov(strmov(query, op), + (opt_mysql_upgrade ? " VIEW " : " TABLE ")); ptr= fix_table_name(ptr, tables); strmake(table_name_buff, org, min((int) sizeof(table_name_buff)-1, (int) (ptr - org))); diff --git a/mysql-test/r/mysql_upgrade_view.result b/mysql-test/r/mysql_upgrade_view.result new file mode 100644 index 00000000000..b6df411d37f --- /dev/null +++ b/mysql-test/r/mysql_upgrade_view.result @@ -0,0 +1,74 @@ +drop table if exists t1,v1,v2,v3,v4; +drop view if exists t1,v1,v2,v3,v4; +flush tables; +create table t1(a int); +create algorithm=temptable view v4 as select a from t1; +show create view v1; +View Create View character_set_client collation_connection +v1 CREATE ALGORITHM=MERGE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v1` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v2; +View Create View character_set_client collation_connection +v2 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v3; +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v4; +View Create View character_set_client collation_connection +v4 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v4` AS select `t1`.`a` AS `a` from `t1` latin1 latin1_swedish_ci +MySQL upgrade detected +Phase 0: Fixing views +test.v1 view is repaired +test.v2 view is repaired +test.v3 view is repaired +test.v4 OK +Phase 1/3: Fixing table and database names +Phase 2/3: Checking and upgrading tables +Processing databases +information_schema +mtr +mtr.global_suppressions OK +mtr.test_suppressions OK +mysql +mysql.columns_priv OK +mysql.db OK +mysql.ev_bk OK +mysql.event OK +mysql.func OK +mysql.help_category OK +mysql.help_keyword OK +mysql.help_relation OK +mysql.help_topic OK +mysql.host OK +mysql.ndb_binlog_index OK +mysql.plugin OK +mysql.proc OK +mysql.procs_priv OK +mysql.proxies_priv OK +mysql.servers OK +mysql.tables_priv OK +mysql.time_zone OK +mysql.time_zone_leap_second OK +mysql.time_zone_name OK +mysql.time_zone_transition OK +mysql.time_zone_transition_type OK +mysql.user OK +performance_schema +test +test.t1 OK +Phase 3/3: Running 'mysql_fix_privilege_tables'... +OK +show create view v1; +View Create View character_set_client collation_connection +v1 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v1` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v2; +View Create View character_set_client collation_connection +v2 CREATE ALGORITHM=MERGE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v3; +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v4; +View Create View character_set_client collation_connection +v4 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v4` AS select `t1`.`a` AS `a` from `t1` latin1 latin1_swedish_ci +flush tables; +drop view v1,v2,v3,v4; +drop table t1; diff --git a/mysql-test/t/mysql_upgrade_view.test b/mysql-test/t/mysql_upgrade_view.test new file mode 100644 index 00000000000..42c0a7f3c75 --- /dev/null +++ b/mysql-test/t/mysql_upgrade_view.test @@ -0,0 +1,53 @@ + +--disable_warnings +drop table if exists t1,v1,v2,v3,v4; +drop view if exists t1,v1,v2,v3,v4; +--enable_warnings + +let $MYSQLD_DATADIR= `select @@datadir`; + +--copy_file $MYSQLD_DATADIR/mysql/event.MYI $MYSQLD_DATADIR/mysql/ev_bk.MYI +--copy_file $MYSQLD_DATADIR/mysql/event.MYD $MYSQLD_DATADIR/mysql/ev_bk.MYD +--copy_file $MYSQLD_DATADIR/mysql/event.frm $MYSQLD_DATADIR/mysql/ev_bk.frm +--remove_file $MYSQLD_DATADIR/mysql/event.MYI +--remove_file $MYSQLD_DATADIR/mysql/event.MYD +--remove_file $MYSQLD_DATADIR/mysql/event.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.MYI $MYSQLD_DATADIR/mysql/event.MYI +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.MYD $MYSQLD_DATADIR/mysql/event.MYD +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.frm $MYSQLD_DATADIR/mysql/event.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v1.frm $MYSQLD_DATADIR/test/v1.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v2.frm $MYSQLD_DATADIR/test/v2.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v3.frm $MYSQLD_DATADIR/test/v3.frm + +flush tables; + +create table t1(a int); +create algorithm=temptable view v4 as select a from t1; +show create view v1; +show create view v2; +show create view v3; +show create view v4; + +--replace_result $MYSQLTEST_VARDIR var +--exec $MYSQL_UPGRADE --force 2>&1 + +show create view v1; +show create view v2; +show create view v3; +show create view v4; + +--remove_file $MYSQLD_DATADIR/mysql/event.MYI +--remove_file $MYSQLD_DATADIR/mysql/event.MYD +--remove_file $MYSQLD_DATADIR/mysql/event.frm +--copy_file $MYSQLD_DATADIR/mysql/ev_bk.MYI $MYSQLD_DATADIR/mysql/event.MYI +--copy_file $MYSQLD_DATADIR/mysql/ev_bk.MYD $MYSQLD_DATADIR/mysql/event.MYD +--copy_file $MYSQLD_DATADIR/mysql/ev_bk.frm $MYSQLD_DATADIR/mysql/event.frm +--remove_file $MYSQLD_DATADIR/mysql/ev_bk.MYI +--remove_file $MYSQLD_DATADIR/mysql/ev_bk.MYD +--remove_file $MYSQLD_DATADIR/mysql/ev_bk.frm +flush tables; + +drop view v1,v2,v3,v4; +drop table t1; + +#select sleep(100); From 87f5bae0b56253df965230f585bcb58352b4ef01 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Sun, 12 Apr 2015 16:50:16 +1000 Subject: [PATCH 02/23] Get my_getop to parse opt_mysql_upgrade in mysqlcheck requested by Sergei Golubchik in review 9 Feb 2015 17:28:08 +0100 --- client/mysqlcheck.c | 17 ++++++++++++----- 1 file changed, 12 insertions(+), 5 deletions(-) diff --git a/client/mysqlcheck.c b/client/mysqlcheck.c index 7446d75d0a3..fa6fa4eecf7 100644 --- a/client/mysqlcheck.c +++ b/client/mysqlcheck.c @@ -199,7 +199,7 @@ static struct my_option my_long_options[] = NO_ARG, 0, 0, 0, 0, 0, 0}, {"mysql-upgrade", 'y', "Fix view algorithm view field if it is not new MariaDB view.", - 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, + &opt_mysql_upgrade, &opt_mysql_upgrade, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0} }; @@ -339,10 +339,6 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), case 'V': print_version(); exit(0); break; - case 'y': - what_to_do= DO_REPAIR; - opt_mysql_upgrade= 1; - break; case OPT_MYSQL_PROTOCOL: opt_protocol= find_type_or_exit(argument, &sql_protocol_typelib, opt->name); @@ -373,6 +369,17 @@ static int get_options(int *argc, char ***argv) if ((ho_error=handle_options(argc, argv, my_long_options, get_one_option))) exit(ho_error); + if (opt_mysql_upgrade && what_to_do!=DO_REPAIR) + { + if (!what_to_do) + what_to_do= DO_REPAIR; + else + { + fprintf(stderr, "Error: %s doesn't support non-repair command with option mysql-upgrade.\n", + my_progname); + exit(1); + } + } if (!what_to_do) { size_t pnlen= strlen(my_progname); From ebd3c6ccbe43b691515cb05cf4919ff46f15c7f0 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Sun, 12 Apr 2015 17:05:02 +1000 Subject: [PATCH 03/23] Remove mysql-upgrade / skip-mysql-upgrade options from mysql-upgrade.c --- client/mysql_upgrade.c | 73 ++++++++++++++---------------------------- 1 file changed, 24 insertions(+), 49 deletions(-) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index acb480da570..c2da47b370c 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -40,8 +40,7 @@ static char mysql_path[FN_REFLEN]; static char mysqlcheck_path[FN_REFLEN]; static my_bool opt_force, opt_verbose, debug_info_flag, debug_check_flag, - opt_systables_only, opt_version_check, - opt_mysql_upgrade= 0, opt_skip_mysql_upgrade= 0; + opt_systables_only, opt_version_check; static my_bool opt_not_used, opt_silent; static uint my_end_arg= 0; static char *opt_user= (char*)"root"; @@ -151,14 +150,6 @@ static struct my_option my_long_options[]= &opt_not_used, &opt_not_used, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0}, {"version", 'V', "Output version information and exit.", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, - {"mysql-upgrade", 'y', - "Skip automatic detection MySQL and assume that we upgrade it", - &opt_mysql_upgrade, &opt_mysql_upgrade, 0, GET_BOOL, NO_ARG, - 0, 0, 0, 0, 0, 0}, - {"skip-mysql-upgrade", 'Y', - "Skip view algorithm upgrade from MySQL", - &opt_skip_mysql_upgrade, &opt_skip_mysql_upgrade, 0, GET_BOOL, NO_ARG, - 0, 0, 0, 0, 0, 0}, {"version-check", 'k', "Run this program only if its \'server version\' " "matches the version of the server to which it's connecting, (enabled by " "default); use --skip-version-check to avoid this check. Note: the \'server " @@ -353,14 +344,6 @@ get_one_option(int optid, const struct my_option *opt, case OPT_DEFAULT_AUTH: /* --default-auth */ add_one_option(&conn_args, opt, argument); break; - case 'y': - opt_mysql_upgrade= 1; - add_option= FALSE; - break; - case 'Y': - opt_skip_mysql_upgrade= 1; - add_option= FALSE; - break; } if (add_option) @@ -771,9 +754,31 @@ static int run_mysqlcheck_upgrade(void) NULL); } +#define EVENTS_STRUCT_LEN 7000 + +static my_bool is_mysql() +{ + my_bool ret= TRUE; + DYNAMIC_STRING ds_events_struct; + + if (init_dynamic_string(&ds_events_struct, NULL, + EVENTS_STRUCT_LEN, EVENTS_STRUCT_LEN)) + die("Out of memory"); + + if (run_query("show create table mysql.event", + &ds_events_struct, FALSE) || + strstr(ds_events_struct.str, "IGNORE_BAD_TABLE_OPTIONS") != NULL) + ret= FALSE; + else + verbose("MySQL upgrade detected"); + + dynstr_free(&ds_events_struct); + return(ret); +} + static int run_mysqlcheck_views(void) { - if (!opt_mysql_upgrade) + if (!is_mysql()) return 0; verbose("Phase 0: Fixing views"); print_conn_args("mysqlcheck"); @@ -962,28 +967,6 @@ static int check_version_match(void) return 0; } -#define EVENTS_STRUCT_LEN 7000 - -my_bool is_mysql() -{ - my_bool ret= TRUE; - DYNAMIC_STRING ds_events_struct; - - if (init_dynamic_string(&ds_events_struct, NULL, - EVENTS_STRUCT_LEN, EVENTS_STRUCT_LEN)) - die("Out of memory"); - - if (run_query("show create table mysql.event", - &ds_events_struct, FALSE) || - strstr(ds_events_struct.str, "IGNORE_BAD_TABLE_OPTIONS") != NULL) - ret= FALSE; - else - verbose("MySQL upgrade detected"); - - dynstr_free(&ds_events_struct); - return(ret); -} - int main(int argc, char **argv) { @@ -1053,14 +1036,6 @@ int main(int argc, char **argv) if (opt_version_check && check_version_match()) die("Upgrade failed"); - if (!opt_systables_only && !opt_skip_mysql_upgrade) - { - if (!opt_mysql_upgrade) - opt_mysql_upgrade= is_mysql(); - } - else - opt_mysql_upgrade= 0; - /* Run "mysqlcheck" and "mysql_fix_privilege_tables.sql" */ From 25872e2802a4ae32d4f18132d569599295c963cd Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Sun, 12 Apr 2015 17:21:02 +1000 Subject: [PATCH 04/23] Correct phase count on mysql_upgrade Add static vars on phases to make merging consistent. client/mysql_upgrade --verbose -S /tmp/s.sock Looking for 'mysql' as: client/mysql Looking for 'mysqlcheck' as: client/mysqlcheck Phase 1/4: Fixing views - skipped - not required Phase 2/4: Fixing table and database names Processing databases information_schema mysql performance_schema test Phase 3/4: Checking and upgrading tables Processing databases information_schema mysql mysql.columns_priv OK mysql.db OK mysql.event OK mysql.func OK mysql.help_category OK mysql.help_keyword OK mysql.help_relation OK mysql.help_topic OK mysql.host OK mysql.ndb_binlog_index OK mysql.plugin OK mysql.proc OK mysql.procs_priv OK mysql.proxies_priv OK mysql.servers OK mysql.tables_priv OK mysql.time_zone OK mysql.time_zone_leap_second OK mysql.time_zone_name OK mysql.time_zone_transition OK mysql.time_zone_transition_type OK mysql.user OK performance_schema test Phase 4/4: Running 'mysql_fix_privilege_tables'... OK --- client/mysql_upgrade.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index c2da47b370c..fd4df9a9ffb 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -36,6 +36,8 @@ # endif #endif +static int phase = 1; +static int phases_total = 4; static char mysql_path[FN_REFLEN]; static char mysqlcheck_path[FN_REFLEN]; @@ -738,7 +740,7 @@ static void print_conn_args(const char *tool_name) static int run_mysqlcheck_upgrade(void) { - verbose("Phase 2/3: Checking and upgrading tables"); + verbose("Phase %d/%d: Checking and upgrading tables", phase++, phases_total); print_conn_args("mysqlcheck"); return run_tool(mysqlcheck_path, NULL, /* Send output from mysqlcheck directly to screen */ @@ -779,8 +781,11 @@ static my_bool is_mysql() static int run_mysqlcheck_views(void) { if (!is_mysql()) + { + verbose("Phase %d/%d: Fixing views - skipped - not required", phase++, phases_total); return 0; - verbose("Phase 0: Fixing views"); + } + verbose("Phase %d/%d: Fixing views", phase++, phases_total); print_conn_args("mysqlcheck"); return run_tool(mysqlcheck_path, NULL, /* Send output from mysqlcheck directly to screen */ @@ -796,7 +801,7 @@ static int run_mysqlcheck_views(void) static int run_mysqlcheck_fixnames(void) { - verbose("Phase 1/3: Fixing table and database names"); + verbose("Phase %d/%d: Fixing table and database names", phase++, phases_total); print_conn_args("mysqlcheck"); return run_tool(mysqlcheck_path, NULL, /* Send output from mysqlcheck directly to screen */ @@ -877,7 +882,7 @@ static int run_sql_fix_privilege_tables(void) if (init_dynamic_string(&ds_result, "", 512, 512)) die("Out of memory"); - verbose("Phase 3/3: Running 'mysql_fix_privilege_tables'..."); + verbose("Phase %d/%d: Running 'mysql_fix_privilege_tables'...", phase++, phases_total); run_query(mysql_fix_privilege_tables, &ds_result, /* Collect result */ TRUE); From e5191dd11beaec44230f97ec1402439ffd27333b Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Sun, 12 Apr 2015 17:26:50 +1000 Subject: [PATCH 05/23] mysql-upgrade -> fix-view-algorithm as mysqlcheck option --- client/mysql_upgrade.c | 2 +- client/mysqlcheck.c | 26 +++++++++++++------------- 2 files changed, 14 insertions(+), 14 deletions(-) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index fd4df9a9ffb..7747a96eccf 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -792,7 +792,7 @@ static int run_mysqlcheck_views(void) "--no-defaults", ds_args.str, "--all-databases", - "--mysql-upgrade", + "--fix-view-algorithm", opt_verbose ? "--verbose": "", opt_silent ? "--silent": "", "2>&1", diff --git a/client/mysqlcheck.c b/client/mysqlcheck.c index fa6fa4eecf7..710674ed2f6 100644 --- a/client/mysqlcheck.c +++ b/client/mysqlcheck.c @@ -43,7 +43,7 @@ static my_bool opt_alldbs = 0, opt_check_only_changed = 0, opt_extended = 0, opt_silent = 0, opt_auto_repair = 0, ignore_errors = 0, tty_password= 0, opt_frm= 0, debug_info_flag= 0, debug_check_flag= 0, opt_fix_table_names= 0, opt_fix_db_names= 0, opt_upgrade= 0, - opt_mysql_upgrade= 0; + opt_fix_view_algorithm= 0; static my_bool opt_write_binlog= 1, opt_flush_tables= 0; static uint verbose = 0, opt_mysql_port=0; static int my_end_arg; @@ -197,9 +197,9 @@ static struct my_option my_long_options[] = NO_ARG, 0, 0, 0, 0, 0, 0}, {"version", 'V', "Output version information and exit.", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, - {"mysql-upgrade", 'y', + {"fix-view-algorithm", 'y', "Fix view algorithm view field if it is not new MariaDB view.", - &opt_mysql_upgrade, &opt_mysql_upgrade, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, + &opt_fix_view_algorithm, &opt_fix_view_algorithm, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0} }; @@ -369,13 +369,13 @@ static int get_options(int *argc, char ***argv) if ((ho_error=handle_options(argc, argv, my_long_options, get_one_option))) exit(ho_error); - if (opt_mysql_upgrade && what_to_do!=DO_REPAIR) + if (opt_fix_view_algorithm && what_to_do!=DO_REPAIR) { if (!what_to_do) what_to_do= DO_REPAIR; else { - fprintf(stderr, "Error: %s doesn't support non-repair command with option mysql-upgrade.\n", + fprintf(stderr, "Error: %s doesn't support non-repair command with option fix-view-algorithm.\n", my_progname); exit(1); } @@ -605,12 +605,12 @@ static int process_all_tables_in_db(char *database) { if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) { - if (!opt_mysql_upgrade) + if (!opt_fix_view_algorithm) continue; } else { - if (opt_mysql_upgrade) + if (opt_fix_view_algorithm) continue; } @@ -629,12 +629,12 @@ static int process_all_tables_in_db(char *database) /* Skip views if we don't perform renaming. */ if ((what_to_do != DO_UPGRADE) && (num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) { - if (!opt_mysql_upgrade) + if (!opt_fix_view_algorithm) continue; } else { - if (opt_mysql_upgrade) + if (opt_fix_view_algorithm) continue; } if (system_database && @@ -781,12 +781,12 @@ static int handle_request_for_tables(char *tables, uint length) if (opt_upgrade) end = strmov(end, " FOR UPGRADE"); break; case DO_REPAIR: - op= ((opt_write_binlog || opt_mysql_upgrade) ? + op= ((opt_write_binlog || opt_fix_view_algorithm) ? "REPAIR" : "REPAIR NO_WRITE_TO_BINLOG"); if (opt_quick) end = strmov(end, " QUICK"); if (opt_extended) end = strmov(end, " EXTENDED"); if (opt_frm) end = strmov(end, " USE_FRM"); - if (opt_mysql_upgrade) end = strmov(end, " FROM MYSQL"); + if (opt_fix_view_algorithm) end = strmov(end, " FROM MYSQL"); break; case DO_ANALYZE: op= (opt_write_binlog) ? "ANALYZE" : "ANALYZE NO_WRITE_TO_BINLOG"; @@ -804,7 +804,7 @@ static int handle_request_for_tables(char *tables, uint length) { /* No backticks here as we added them before */ query_length= sprintf(query, "%s %s %s %s", op, - (opt_mysql_upgrade ? "VIEW" : "TABLE"), + (opt_fix_view_algorithm ? "VIEW" : "TABLE"), tables, options); table_name= tables; } @@ -813,7 +813,7 @@ static int handle_request_for_tables(char *tables, uint length) char *ptr, *org; org= ptr= strmov(strmov(query, op), - (opt_mysql_upgrade ? " VIEW " : " TABLE ")); + (opt_fix_view_algorithm ? " VIEW " : " TABLE ")); ptr= fix_table_name(ptr, tables); strmake(table_name_buff, org, min((int) sizeof(table_name_buff)-1, (int) (ptr - org))); From c8dbef22add27eb6cc737b12eb80b968663d34bb Mon Sep 17 00:00:00 2001 From: Oleksandr Byelkin Date: Sun, 12 Apr 2015 20:41:28 +1000 Subject: [PATCH 06/23] MDEV-6916 REPAIR VIEW / mysql migration from: r4407 --- include/myisamchk.h | 1 + sql/handler.h | 2 + sql/lex.h | 1 + sql/share/errmsg-utf8.txt | 6 ++ sql/sql_admin.cc | 44 ++++++++-- sql/sql_base.cc | 10 ++- sql/sql_table.cc | 2 +- sql/sql_view.cc | 172 ++++++++++++++++++++++++++++++++++---- sql/sql_view.h | 2 + sql/sql_yacc.yy | 41 ++++++++- 10 files changed, 254 insertions(+), 27 deletions(-) diff --git a/include/myisamchk.h b/include/myisamchk.h index a09e53eb387..ded463f10ca 100644 --- a/include/myisamchk.h +++ b/include/myisamchk.h @@ -34,6 +34,7 @@ #define TT_USEFRM 1 #define TT_FOR_UPGRADE 2 +#define TT_FROM_MYSQL 4 /* Bits set in out_flag */ #define O_NEW_DATA 2 diff --git a/sql/handler.h b/sql/handler.h index 642a922b544..f05fce39cfc 100644 --- a/sql/handler.h +++ b/sql/handler.h @@ -42,6 +42,7 @@ // the following is for checking tables +#define HA_ADMIN_VIEW_REPAIR_IS_DONE 2 #define HA_ADMIN_ALREADY_DONE 1 #define HA_ADMIN_OK 0 #define HA_ADMIN_NOT_IMPLEMENTED -1 @@ -56,6 +57,7 @@ #define HA_ADMIN_NEEDS_UPGRADE -10 #define HA_ADMIN_NEEDS_ALTER -11 #define HA_ADMIN_NEEDS_CHECK -12 +#define HA_ADMIN_NEEDS_REPAIR -13 /* Bits in table_flags() to show what database can do */ diff --git a/sql/lex.h b/sql/lex.h index 9bf4c439cb6..65411402f6a 100644 --- a/sql/lex.h +++ b/sql/lex.h @@ -376,6 +376,7 @@ static SYMBOL symbols[] = { { "MULTIPOINT", SYM(MULTIPOINT)}, { "MULTIPOLYGON", SYM(MULTIPOLYGON)}, { "MUTEX", SYM(MUTEX_SYM)}, + { "MYSQL", SYM(MYSQL_SYM)}, { "MYSQL_ERRNO", SYM(MYSQL_ERRNO_SYM)}, { "NAME", SYM(NAME_SYM)}, { "NAMES", SYM(NAMES_SYM)}, diff --git a/sql/share/errmsg-utf8.txt b/sql/share/errmsg-utf8.txt index 6fcb460e6c6..428be309c2a 100644 --- a/sql/share/errmsg-utf8.txt +++ b/sql/share/errmsg-utf8.txt @@ -6565,3 +6565,9 @@ ER_QUERY_EXCEEDED_ROWS_EXAMINED_LIMIT ER_NO_SUCH_TABLE_IN_ENGINE 42S02 eng "Table '%-.192s.%-.192s' doesn't exist in engine" swe "Det finns ingen tabell som heter '%-.192s.%-.192s' i handlern" +ER_NO_MARIADB_SERVER_FIELD + eng "view '%-.192s.%-.192s' has no field mariadb server in its .frm file" +ER_VIEW_REPAIR_IS_DONE + eng "view is repaired" +ER_NEEDS_REPAIR + eng "needs repair" diff --git a/sql/sql_admin.cc b/sql/sql_admin.cc index 92aa414b569..20c23afe228 100644 --- a/sql/sql_admin.cc +++ b/sql/sql_admin.cc @@ -314,7 +314,8 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, HA_CHECK_OPT *), int (handler::*operator_func)(THD *, HA_CHECK_OPT *), - int (view_operator_func)(THD *, TABLE_LIST*)) + int (view_operator_func)(THD *, TABLE_LIST*, + HA_CHECK_OPT *)) { TABLE_LIST *table; SELECT_LEX *select= &thd->lex->select_lex; @@ -380,7 +381,18 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, lex->query_tables_own_last= 0; if (view_operator_func == NULL) + { table->required_type=FRMTYPE_TABLE; + DBUG_ASSERT(!lex->only_view); + } + else if (lex->only_view) + { + table->required_type= FRMTYPE_VIEW; + } + else if (!lex->only_view && lex->sql_command == SQLCOM_REPAIR) + { + table->required_type= FRMTYPE_TABLE; + } if (lex->sql_command == SQLCOM_CHECK || lex->sql_command == SQLCOM_REPAIR || @@ -506,9 +518,9 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, } /* - CHECK TABLE command is only command where VIEW allowed here and this - command use only temporary teble method for VIEWs resolving => there - can't be VIEW tree substitition of join view => if opening table + CHECK/REPAIR TABLE command is only command where VIEW allowed here and + this command use only temporary table method for VIEWs resolving => + there can't be VIEW tree substitition of join view => if opening table succeed then table->table will have real TABLE pointer as value (in case of join view substitution table->table can be 0, but here it is impossible) @@ -521,7 +533,7 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, ER_CHECK_NO_SUCH_TABLE, ER(ER_CHECK_NO_SUCH_TABLE)); /* if it was a view will check md5 sum */ if (table->view && - view_checksum(thd, table) == HA_ADMIN_WRONG_CHECKSUM) + view_check(thd, table, check_opt) == HA_ADMIN_WRONG_CHECKSUM) push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, ER_VIEW_CHECKSUM, ER(ER_VIEW_CHECKSUM)); if (thd->stmt_da->is_error() && @@ -536,7 +548,7 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, if (table->view) { DBUG_PRINT("admin", ("calling view_operator_func")); - result_code= (*view_operator_func)(thd, table); + result_code= (*view_operator_func)(thd, table, check_opt); goto send_result; } @@ -867,6 +879,22 @@ send_result_message: fatal_error=1; break; } + case HA_ADMIN_VIEW_REPAIR_IS_DONE: + { + protocol->store(STRING_WITH_LEN("status"), system_charset_info); + protocol->store(ER(ER_VIEW_REPAIR_IS_DONE), + strlen(ER(ER_VIEW_REPAIR_IS_DONE)), + system_charset_info); + break; + } + case HA_ADMIN_NEEDS_REPAIR: + { + protocol->store(STRING_WITH_LEN("status"), system_charset_info); + protocol->store(ER(ER_NEEDS_REPAIR), + strlen(ER(ER_NEEDS_REPAIR)), + system_charset_info); + break; + } default: // Probably HA_ADMIN_INTERNAL_ERROR { @@ -1071,7 +1099,7 @@ bool Check_table_statement::execute(THD *thd) res= mysql_admin_table(thd, first_table, &m_lex->check_opt, "check", lock_type, 0, 0, HA_OPEN_FOR_REPAIR, 0, - &handler::ha_check, &view_checksum); + &handler::ha_check, &view_check); m_lex->select_lex.table_list.first= first_table; m_lex->query_tables= first_table; @@ -1126,7 +1154,7 @@ bool Repair_table_statement::execute(THD *thd) TL_WRITE, 1, test(m_lex->check_opt.sql_flags & TT_USEFRM), HA_OPEN_FOR_REPAIR, &prepare_for_repair, - &handler::ha_repair, 0); + &handler::ha_repair, &view_repair); /* ! we write after unlocking the table */ if (!res && !m_lex->no_write_to_binlog) diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 3c36c2b514a..8be057eb08e 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -643,7 +643,8 @@ found: open_table_error(share, share->error, share->open_errno, share->errarg); DBUG_RETURN(0); } - if (share->is_view && !(db_flags & OPEN_VIEW)) + if ((share->is_view && !(db_flags & OPEN_VIEW)) || + (!share->is_view && (db_flags & OPEN_VIEW_ONLY))) { open_table_error(share, 1, ENOENT, 0); DBUG_RETURN(0); @@ -3022,12 +3023,17 @@ bool open_table(THD *thd, TABLE_LIST *table_list, MEM_ROOT *mem_root, else if (table_list->open_strategy == TABLE_LIST::OPEN_STUB) DBUG_RETURN(FALSE); + retry_share: mysql_mutex_lock(&LOCK_open); if (!(share= get_table_share_with_discover(thd, table_list, key, - key_length, OPEN_VIEW, + key_length, + (OPEN_VIEW | + ((table_list->required_type == + FRMTYPE_VIEW) ? + OPEN_VIEW_ONLY : 0)), &error, hash_value))) { diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 477ecf4a350..39e8e0d0d55 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -28,7 +28,7 @@ #include "sql_base.h" // open_table_uncached, lock_table_names #include "lock.h" // mysql_unlock_tables #include "strfunc.h" // find_type2, find_set -#include "sql_view.h" // view_checksum +#include "sql_view.h" // view_check #include "sql_truncate.h" // regenerate_locked_table #include "sql_partition.h" // mem_alloc_error, // generate_partition_syntax, diff --git a/sql/sql_view.cc b/sql/sql_view.cc index 09784f7257a..8ba1e33836f 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -729,6 +729,26 @@ err: } +static void make_view_filename(LEX_STRING *dir, char *dir_buff, + size_t dir_buff_len, + LEX_STRING *path, char *path_buff, + size_t path_buff_len, + LEX_STRING *file, + TABLE_LIST *view) +{ + /* print file name */ + dir->length= build_table_filename(dir_buff, dir_buff_len - 1, + view->db, "", "", 0); + dir->str= dir_buff; + + path->length= build_table_filename(path_buff, path_buff_len - 1, + view->db, view->table_name, reg_ext, 0); + path->str= path_buff; + + file->str= path->str + dir->length; + file->length= path->length - dir->length; +} + /* number of required parameters for making view */ static const int required_view_parameters= 15; @@ -791,6 +811,81 @@ static File_option view_parameters[]= static LEX_STRING view_file_type[]= {{(char*) STRING_WITH_LEN("VIEW") }}; +int mariadb_fix_view(THD *thd, TABLE_LIST *view, bool wrong_checksum, + bool swap_alg) +{ + char dir_buff[FN_REFLEN + 1], path_buff[FN_REFLEN + 1]; + LEX_STRING dir, file, path; + DBUG_ENTER("mariadb_fix_view"); + + if (view->algorithm == VIEW_ALGORITHM_UNDEFINED && + !wrong_checksum && view->mariadb_version) + DBUG_RETURN(HA_ADMIN_OK); + + make_view_filename(&dir, dir_buff, sizeof(dir_buff), + &path, path_buff, sizeof(path_buff), + &file, view); + /* init timestamp */ + if (!view->timestamp.str) + view->timestamp.str= view->timestamp_buffer; + + /* check old .frm */ + { + char path_buff[FN_REFLEN]; + LEX_STRING path; + File_parser *parser; + + path.str= path_buff; + fn_format(path_buff, file.str, dir.str, "", MY_UNPACK_FILENAME); + path.length= strlen(path_buff); + if (access(path.str, F_OK)) + DBUG_RETURN(HA_ADMIN_INVALID); + + if (!(parser= sql_parse_prepare(&path, thd->mem_root, 0))) + DBUG_RETURN(HA_ADMIN_INTERNAL_ERROR); + + if (!parser->ok() || !is_equal(&view_type, parser->type())) + DBUG_RETURN(HA_ADMIN_INVALID); + } + + if (swap_alg && view->algorithm != VIEW_ALGORITHM_UNDEFINED) + { + DBUG_ASSERT(view->algorithm == VIEW_ALGORITHM_MERGE || + view->algorithm == VIEW_ALGORITHM_TMPTABLE); + if (view->algorithm == VIEW_ALGORITHM_MERGE) + view->algorithm= VIEW_ALGORITHM_TMPTABLE; + else + view->algorithm= VIEW_ALGORITHM_MERGE; + } + if (wrong_checksum) + { + if (view->md5.length != 32) + { + if ((view->md5.str= (char *)thd->alloc(32 + 1)) == NULL) + DBUG_RETURN(HA_ADMIN_FAILED); + } + view->calc_md5(view->md5.str); + view->md5.length= 32; + } + view->mariadb_version= MYSQL_VERSION_ID; + + if (sql_create_definition_file(&dir, &file, view_file_type, + (uchar*)view, view_parameters)) + { + sql_print_error("View '%-.192s'.'%-.192s': algorithm swap error.", + view->db, view->table_name); + DBUG_RETURN(HA_ADMIN_INTERNAL_ERROR); + } + sql_print_information("View '%-.192s'.'%-.192s': algorithm swapped to '%s'", + view->db, view->table_name, + (view->algorithm == VIEW_ALGORITHM_MERGE)? + "MERGE":"TEMPTABLE"); + + + DBUG_RETURN(HA_ADMIN_VIEW_REPAIR_IS_DONE); +} + + /* Register VIEW (write .frm & process .frm's history backups) @@ -927,17 +1022,9 @@ static int mysql_register_view(THD *thd, TABLE_LIST *view, } loop_out: /* print file name */ - dir.length= build_table_filename(dir_buff, sizeof(dir_buff) - 1, - view->db, "", "", 0); - dir.str= dir_buff; - - path.length= build_table_filename(path_buff, sizeof(path_buff) - 1, - view->db, view->table_name, reg_ext, 0); - path.str= path_buff; - - file.str= path.str + dir.length; - file.length= path.length - dir.length; - + make_view_filename(&dir, dir_buff, sizeof(dir_buff), + &path, path_buff, sizeof(path_buff), + &file, view); /* init timestamp */ if (!view->timestamp.str) view->timestamp.str= view->timestamp_buffer; @@ -1063,7 +1150,7 @@ err: SYNOPSIS mysql_make_view() - thd Thread handler + thd Thread handle parser parser object table TABLE_LIST structure for filling flags flags @@ -1634,7 +1721,7 @@ err: SYNOPSIS mysql_drop_view() - thd - thread handler + thd - thread handle views - views to delete drop_mode - cascade/check @@ -1755,7 +1842,7 @@ bool mysql_drop_view(THD *thd, TABLE_LIST *views, enum_drop_mode drop_mode) SYNOPSIS check_key_in_view() - thd thread handler + thd thread handle view view for check with opened table DESCRIPTION @@ -1941,6 +2028,63 @@ int view_checksum(THD *thd, TABLE_LIST *view) HA_ADMIN_OK); } +/** + Check view + + @param thd thread handle + @param view view for check + @param check_opt check options + + @retval HA_ADMIN_OK OK + @retval HA_ADMIN_NOT_IMPLEMENTED it is not VIEW + @retval HA_ADMIN_WRONG_CHECKSUM check sum is wrong +*/ +int view_check(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt) +{ + int res; + DBUG_ENTER("view_check"); + if ((res= view_checksum(thd, view)) != HA_ADMIN_OK) + DBUG_RETURN(res); + if (((check_opt->sql_flags & TT_FOR_UPGRADE) && + !view->mariadb_version)) + { + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_NOTE, + ER_NO_MARIADB_SERVER_FIELD, + ER(ER_NO_MARIADB_SERVER_FIELD), + view->db, + view->table_name); + DBUG_RETURN(HA_ADMIN_NEEDS_REPAIR); + } + DBUG_RETURN(HA_ADMIN_OK); +} + + +/** + Repair view + + @param thd thread handle + @param view view for check + @param check_opt check options + + @retval HA_ADMIN_OK OK + @retval HA_ADMIN_NOT_IMPLEMENTED it is not VIEW + @retval HA_ADMIN_WRONG_CHECKSUM check sum is wrong +*/ + +int view_repair(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt) +{ + DBUG_ENTER("view_repair"); + bool swap_alg= + ((check_opt->sql_flags & TT_FROM_MYSQL) && + (!view->mariadb_version)); + bool wrong_checksum= view_checksum(thd, view); + if (wrong_checksum || swap_alg) + { + DBUG_RETURN(mariadb_fix_view(thd, view, wrong_checksum, swap_alg)); + } + DBUG_RETURN(HA_ADMIN_OK); +} + /* rename view diff --git a/sql/sql_view.h b/sql/sql_view.h index 2e9c77252e8..1026c57aaaf 100644 --- a/sql/sql_view.h +++ b/sql/sql_view.h @@ -44,6 +44,8 @@ bool check_key_in_view(THD *thd, TABLE_LIST * view); bool insert_view_fields(THD *thd, List *list, TABLE_LIST *view); int view_checksum(THD *thd, TABLE_LIST *view); +int view_check(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt); +int view_repair(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt); extern TYPELIB updatable_views_with_limit_typelib; diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 257001c80d1..d9faaf287c2 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -1145,6 +1145,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize); %token MULTIPOINT %token MULTIPOLYGON %token MUTEX_SYM +%token MYSQL_SYM %token MYSQL_ERRNO_SYM %token NAMES_SYM /* SQL-2003-N */ %token NAME_SYM /* SQL-2003-N */ @@ -7191,11 +7192,16 @@ opt_checksum_type: ; repair: - REPAIR opt_no_write_to_binlog table_or_tables + REPAIR opt_no_write_to_binlog table_or_view { LEX *lex=Lex; lex->sql_command = SQLCOM_REPAIR; lex->no_write_to_binlog= $2; + if (lex->no_write_to_binlog && lex->only_view) + { + my_parse_error(ER(ER_SYNTAX_ERROR)); + MYSQL_YYABORT; + } lex->check_opt.init(); lex->alter_info.reset(); /* Will be overriden during execution. */ @@ -7204,6 +7210,15 @@ repair: table_list opt_mi_repair_type { LEX* lex= thd->lex; + if ((lex->only_view && + ((lex->check_opt.flags & (T_QUICK | T_EXTEND)) || + (lex->check_opt.sql_flags & TT_USEFRM))) || + (!lex->only_view && + (lex->check_opt.sql_flags & TT_FROM_MYSQL))) + { + my_parse_error(ER(ER_SYNTAX_ERROR)); + MYSQL_YYABORT; + } DBUG_ASSERT(!lex->m_stmt); lex->m_stmt= new (thd->mem_root) Repair_table_statement(lex); if (lex->m_stmt == NULL) @@ -7225,6 +7240,7 @@ mi_repair_type: QUICK { Lex->check_opt.flags|= T_QUICK; } | EXTENDED_SYM { Lex->check_opt.flags|= T_EXTEND; } | USE_FRM { Lex->check_opt.sql_flags|= TT_USEFRM; } + | FROM MYSQL_SYM { Lex->check_opt.sql_flags|= TT_FROM_MYSQL; } ; analyze: @@ -7257,7 +7273,7 @@ binlog_base64_event: ; check: - CHECK_SYM table_or_tables + CHECK_SYM table_or_view { LEX *lex=Lex; @@ -7275,6 +7291,13 @@ check: table_list opt_mi_check_type { LEX* lex= thd->lex; + if (lex->only_view && + (lex->check_opt.flags & (T_QUICK | T_FAST | T_EXTEND | + T_CHECK_ONLY_CHANGED))) + { + my_parse_error(ER(ER_SYNTAX_ERROR)); + MYSQL_YYABORT; + } DBUG_ASSERT(!lex->m_stmt); lex->m_stmt= new (thd->mem_root) Check_table_statement(lex); if (lex->m_stmt == NULL) @@ -7382,6 +7405,7 @@ keycache: LEX *lex=Lex; lex->sql_command= SQLCOM_ASSIGN_TO_KEYCACHE; lex->ident= $6; + lex->only_view= FALSE; } ; @@ -7426,6 +7450,7 @@ preload: LEX *lex=Lex; lex->sql_command=SQLCOM_PRELOAD_KEYS; lex->alter_info.reset(); + lex->only_view= FALSE; } preload_list_or_parts {} @@ -13187,6 +13212,7 @@ keyword_sp: | MULTIPOINT {} | MULTIPOLYGON {} | MUTEX_SYM {} + | MYSQL_SYM {} | MYSQL_ERRNO_SYM {} | NAME_SYM {} | NAMES_SYM {} @@ -13786,7 +13812,18 @@ lock: table_or_tables: TABLE_SYM + { Lex->only_view= FALSE; } | TABLES + { Lex->only_view= FALSE; } + ; + +table_or_view: + TABLE_SYM + { Lex->only_view= FALSE; } + | TABLES + { Lex->only_view= FALSE; } + | VIEW_SYM + { Lex->only_view= TRUE; } ; table_lock_list: From 96e277aed81d41c15621c0842fddfe027d844c6e Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Sun, 12 Apr 2015 20:42:13 +1000 Subject: [PATCH 07/23] mysql_upgrade to pass binlog option to mysqlcheck when doing the --fix-view-algorithm method to upgrade from MySQL. --- client/mysql_upgrade.c | 1 + 1 file changed, 1 insertion(+) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index 7747a96eccf..88bd09d0b95 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -795,6 +795,7 @@ static int run_mysqlcheck_views(void) "--fix-view-algorithm", opt_verbose ? "--verbose": "", opt_silent ? "--silent": "", + opt_write_binlog ? "--write-binlog" : "--skip-write-binlog", "2>&1", NULL); } From 9b067a3e9fa253f90e8cb05b2c9d084900637a1d Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Sun, 12 Apr 2015 21:05:01 +1000 Subject: [PATCH 08/23] Corrections to mysqlcheck Allow tables and views to be repaired in same command. Make error messages represent if it is a REPAIR TABLE or REPAIR VIEW Honor write_binlog even for REPAIR VIEW .. FROM MYSQL opt_all_in_1 does a list of REPAIR TABLE and a list of REPAIR VIEW If a table list is passes this is corrected with the right command --- client/mysqlcheck.c | 115 +++++++++++++++++++++++++++++++++----------- 1 file changed, 88 insertions(+), 27 deletions(-) diff --git a/client/mysqlcheck.c b/client/mysqlcheck.c index 710674ed2f6..c3b8d01a722 100644 --- a/client/mysqlcheck.c +++ b/client/mysqlcheck.c @@ -216,7 +216,7 @@ static int process_selected_tables(char *db, char **table_names, int tables); static int process_all_tables_in_db(char *database); static int process_one_db(char *database); static int use_db(char *database); -static int handle_request_for_tables(char *tables, uint length); +static int handle_request_for_tables(char *tables, uint length, my_bool view); static int dbConnect(char *host, char *user,char *passwd); static void dbDisconnect(char *host); static void DBerror(MYSQL *mysql, const char *when); @@ -480,8 +480,39 @@ static int process_databases(char **db_names) } /* process_databases */ +/* returns: -1 for error, 1 for view, 0 for table */ +static int is_view(const char *table, uint length) +{ + char *query, *ptr; + MYSQL_RES *res; + MYSQL_FIELD *field; + int view; + DBUG_ENTER("is_view"); + + if (!(query =(char *) my_malloc((sizeof(char)*(length+110)), MYF(MY_WME)))) + DBUG_RETURN(-1); + ptr= strmov(query, "SHOW CREATE TABLE "); + ptr= strxmov(ptr, table, NullS); + if (mysql_query(sock, query)) + { + fprintf(stderr, "Failed to %s\n", query); + fprintf(stderr, "Error: %s\n", mysql_error(sock)); + DBUG_RETURN(-1); + } + res= mysql_store_result(sock); + field= mysql_fetch_field(res); + view= (strcmp(field->name,"View")==0) ? 1 : 0; + mysql_free_result(res); + my_free(query); + + DBUG_RETURN(view); +} + static int process_selected_tables(char *db, char **table_names, int tables) { + int view; + char *table; + uint table_len; DBUG_ENTER("process_selected_tables"); if (use_db(db)) @@ -511,12 +542,24 @@ static int process_selected_tables(char *db, char **table_names, int tables) *end++= ','; } *--end = 0; - handle_request_for_tables(table_names_comma_sep + 1, (uint) (tot_length - 1)); + table= table_names_comma_sep + 1; + table_len= tot_length - 1; + view= is_view(table, table_len); + if (view < 0) + DBUG_RETURN(1); + handle_request_for_tables(table, table_len, (view==1)); my_free(table_names_comma_sep); } else for (; tables > 0; tables--, table_names++) - handle_request_for_tables(*table_names, fixed_name_length(*table_names)); + { + table= *table_names; + table_len= fixed_name_length(*table_names); + view= is_view(table, table_len); + if (view < 0) + continue; + handle_request_for_tables(table, table_len, (view==1)); + } DBUG_RETURN(0); } /* process_selected_tables */ @@ -563,6 +606,7 @@ static int process_all_tables_in_db(char *database) MYSQL_ROW row; uint num_columns; my_bool system_database= 0; + my_bool view= FALSE; DBUG_ENTER("process_all_tables_in_db"); if (use_db(database)) @@ -592,8 +636,16 @@ static int process_all_tables_in_db(char *database) char *tables, *end; uint tot_length = 0; + char *views, *views_end; + uint tot_views_length = 0; + while ((row = mysql_fetch_row(res))) - tot_length+= fixed_name_length(row[0]) + 2; + { + if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) + tot_views_length+= fixed_name_length(row[0]) + 2; + else + tot_length+= fixed_name_length(row[0]) + 2; + } mysql_data_seek(res, 0); if (!(tables=(char *) my_malloc(sizeof(char)*tot_length+4, MYF(MY_WME)))) @@ -601,26 +653,36 @@ static int process_all_tables_in_db(char *database) mysql_free_result(res); DBUG_RETURN(1); } - for (end = tables + 1; (row = mysql_fetch_row(res)) ;) + if (!(views=(char *) my_malloc(sizeof(char)*tot_views_length+4, MYF(MY_WME)))) + { + my_free(tables); + mysql_free_result(res); + DBUG_RETURN(1); + } + + for (end = tables + 1, views_end= views + 1; (row = mysql_fetch_row(res)) ;) { if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) { if (!opt_fix_view_algorithm) continue; + views_end= fix_table_name(views_end, row[0]); + *views_end++= ','; } else { - if (opt_fix_view_algorithm) - continue; + end= fix_table_name(end, row[0]); + *end++= ','; } - - end= fix_table_name(end, row[0]); - *end++= ','; } *--end = 0; + *--views_end = 0; if (tot_length) - handle_request_for_tables(tables + 1, tot_length - 1); + handle_request_for_tables(tables + 1, tot_length - 1, FALSE); + if (tot_views_length) + handle_request_for_tables(views + 1, tot_views_length - 1, TRUE); my_free(tables); + my_free(views); } else { @@ -631,18 +693,16 @@ static int process_all_tables_in_db(char *database) { if (!opt_fix_view_algorithm) continue; + view= TRUE; } else - { - if (opt_fix_view_algorithm) - continue; - } + view= FALSE; if (system_database && (!strcmp(row[0], "general_log") || !strcmp(row[0], "slow_log"))) continue; /* Skip logging tables */ - handle_request_for_tables(row[0], fixed_name_length(row[0])); + handle_request_for_tables(row[0], fixed_name_length(row[0]), view); } } mysql_free_result(res); @@ -760,15 +820,17 @@ static int disable_binlog() return run_query(stmt); } -static int handle_request_for_tables(char *tables, uint length) +static int handle_request_for_tables(char *tables, uint length, my_bool view) { char *query, *end, options[100], message[100]; char table_name_buff[NAME_CHAR_LEN*2*2+1], *table_name; uint query_length= 0; const char *op = 0; + const char *tab_view; DBUG_ENTER("handle_request_for_tables"); options[0] = 0; + tab_view= view ? " VIEW " : " TABLE "; end = options; switch (what_to_do) { case DO_CHECK: @@ -781,12 +843,12 @@ static int handle_request_for_tables(char *tables, uint length) if (opt_upgrade) end = strmov(end, " FOR UPGRADE"); break; case DO_REPAIR: - op= ((opt_write_binlog || opt_fix_view_algorithm) ? - "REPAIR" : "REPAIR NO_WRITE_TO_BINLOG"); + op= (opt_write_binlog) ? + "REPAIR" : "REPAIR NO_WRITE_TO_BINLOG"; if (opt_quick) end = strmov(end, " QUICK"); if (opt_extended) end = strmov(end, " EXTENDED"); if (opt_frm) end = strmov(end, " USE_FRM"); - if (opt_fix_view_algorithm) end = strmov(end, " FROM MYSQL"); + if (opt_fix_view_algorithm && view) end = strmov(end, " FROM MYSQL"); break; case DO_ANALYZE: op= (opt_write_binlog) ? "ANALYZE" : "ANALYZE NO_WRITE_TO_BINLOG"; @@ -803,17 +865,15 @@ static int handle_request_for_tables(char *tables, uint length) if (opt_all_in_1) { /* No backticks here as we added them before */ - query_length= sprintf(query, "%s %s %s %s", op, - (opt_fix_view_algorithm ? "VIEW" : "TABLE"), - tables, options); + query_length= sprintf(query, "%s%s%s %s", op, + tab_view, tables, options); table_name= tables; } else { char *ptr, *org; - org= ptr= strmov(strmov(query, op), - (opt_fix_view_algorithm ? " VIEW " : " TABLE ")); + org= ptr= strmov(strmov(query, op), tab_view); ptr= fix_table_name(ptr, tables); strmake(table_name_buff, org, min((int) sizeof(table_name_buff)-1, (int) (ptr - org))); @@ -823,7 +883,8 @@ static int handle_request_for_tables(char *tables, uint length) } if (mysql_real_query(sock, query, query_length)) { - sprintf(message, "when executing '%s TABLE ... %s'", op, options); + sprintf(message, "when executing '%s%s... %s'", op, tab_view, options); + /* sprintf(message, "when executing '%s'", query); */ DBerror(sock, message); my_free(query); DBUG_RETURN(1); @@ -1093,7 +1154,7 @@ int main(int argc, char **argv) for (i = 0; i < tables4repair.elements ; i++) { char *name= (char*) dynamic_array_ptr(&tables4repair, i); - handle_request_for_tables(name, fixed_name_length(name)); + handle_request_for_tables(name, fixed_name_length(name), FALSE); } for (i = 0; i < tables4rebuild.elements ; i++) rebuild_table((char*) dynamic_array_ptr(&tables4rebuild, i)); From 4409e04d891fba62a3f4ed291c96ee34d645dbec Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Sun, 12 Apr 2015 21:40:07 +1000 Subject: [PATCH 09/23] correct server side error messages --- sql/handler.h | 2 -- sql/share/errmsg-utf8.txt | 6 ------ sql/sql_admin.cc | 16 ---------------- sql/sql_base.cc | 1 - sql/sql_view.cc | 8 ++++---- 5 files changed, 4 insertions(+), 29 deletions(-) diff --git a/sql/handler.h b/sql/handler.h index f05fce39cfc..642a922b544 100644 --- a/sql/handler.h +++ b/sql/handler.h @@ -42,7 +42,6 @@ // the following is for checking tables -#define HA_ADMIN_VIEW_REPAIR_IS_DONE 2 #define HA_ADMIN_ALREADY_DONE 1 #define HA_ADMIN_OK 0 #define HA_ADMIN_NOT_IMPLEMENTED -1 @@ -57,7 +56,6 @@ #define HA_ADMIN_NEEDS_UPGRADE -10 #define HA_ADMIN_NEEDS_ALTER -11 #define HA_ADMIN_NEEDS_CHECK -12 -#define HA_ADMIN_NEEDS_REPAIR -13 /* Bits in table_flags() to show what database can do */ diff --git a/sql/share/errmsg-utf8.txt b/sql/share/errmsg-utf8.txt index 428be309c2a..6fcb460e6c6 100644 --- a/sql/share/errmsg-utf8.txt +++ b/sql/share/errmsg-utf8.txt @@ -6565,9 +6565,3 @@ ER_QUERY_EXCEEDED_ROWS_EXAMINED_LIMIT ER_NO_SUCH_TABLE_IN_ENGINE 42S02 eng "Table '%-.192s.%-.192s' doesn't exist in engine" swe "Det finns ingen tabell som heter '%-.192s.%-.192s' i handlern" -ER_NO_MARIADB_SERVER_FIELD - eng "view '%-.192s.%-.192s' has no field mariadb server in its .frm file" -ER_VIEW_REPAIR_IS_DONE - eng "view is repaired" -ER_NEEDS_REPAIR - eng "needs repair" diff --git a/sql/sql_admin.cc b/sql/sql_admin.cc index 20c23afe228..65292a526fa 100644 --- a/sql/sql_admin.cc +++ b/sql/sql_admin.cc @@ -879,22 +879,6 @@ send_result_message: fatal_error=1; break; } - case HA_ADMIN_VIEW_REPAIR_IS_DONE: - { - protocol->store(STRING_WITH_LEN("status"), system_charset_info); - protocol->store(ER(ER_VIEW_REPAIR_IS_DONE), - strlen(ER(ER_VIEW_REPAIR_IS_DONE)), - system_charset_info); - break; - } - case HA_ADMIN_NEEDS_REPAIR: - { - protocol->store(STRING_WITH_LEN("status"), system_charset_info); - protocol->store(ER(ER_NEEDS_REPAIR), - strlen(ER(ER_NEEDS_REPAIR)), - system_charset_info); - break; - } default: // Probably HA_ADMIN_INTERNAL_ERROR { diff --git a/sql/sql_base.cc b/sql/sql_base.cc index 8be057eb08e..298c4e3150d 100644 --- a/sql/sql_base.cc +++ b/sql/sql_base.cc @@ -3023,7 +3023,6 @@ bool open_table(THD *thd, TABLE_LIST *table_list, MEM_ROOT *mem_root, else if (table_list->open_strategy == TABLE_LIST::OPEN_STUB) DBUG_RETURN(FALSE); - retry_share: mysql_mutex_lock(&LOCK_open); diff --git a/sql/sql_view.cc b/sql/sql_view.cc index 8ba1e33836f..8f2e6092ff2 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -882,7 +882,7 @@ int mariadb_fix_view(THD *thd, TABLE_LIST *view, bool wrong_checksum, "MERGE":"TEMPTABLE"); - DBUG_RETURN(HA_ADMIN_VIEW_REPAIR_IS_DONE); + DBUG_RETURN(HA_ADMIN_OK); } @@ -2049,11 +2049,11 @@ int view_check(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt) !view->mariadb_version)) { push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_NOTE, - ER_NO_MARIADB_SERVER_FIELD, - ER(ER_NO_MARIADB_SERVER_FIELD), + ER_TABLE_NEEDS_UPGRADE, + ER(ER_TABLE_NEEDS_UPGRADE), view->db, view->table_name); - DBUG_RETURN(HA_ADMIN_NEEDS_REPAIR); + DBUG_RETURN(HA_ADMIN_NEEDS_UPGRADE); } DBUG_RETURN(HA_ADMIN_OK); } From eaa3da8e775721130de3a86c009b74b9bd94b4bf Mon Sep 17 00:00:00 2001 From: Oleksandr Byelkin Date: Mon, 13 Apr 2015 20:41:49 +1000 Subject: [PATCH 10/23] Add mysql-test/std_data/mysql_upgrade/* for MDEV-6916 --- mysql-test/std_data/mysql_upgrade/event.MYD | 0 mysql-test/std_data/mysql_upgrade/event.MYI | Bin 0 -> 2048 bytes mysql-test/std_data/mysql_upgrade/event.frm | Bin 0 -> 10223 bytes mysql-test/std_data/mysql_upgrade/v1.frm | 15 +++++++++++++++ mysql-test/std_data/mysql_upgrade/v2.frm | 15 +++++++++++++++ mysql-test/std_data/mysql_upgrade/v3.frm | 15 +++++++++++++++ mysql-test/std_data/mysql_upgrade/v4.frm | 16 ++++++++++++++++ 7 files changed, 61 insertions(+) create mode 100644 mysql-test/std_data/mysql_upgrade/event.MYD create mode 100644 mysql-test/std_data/mysql_upgrade/event.MYI create mode 100644 mysql-test/std_data/mysql_upgrade/event.frm create mode 100644 mysql-test/std_data/mysql_upgrade/v1.frm create mode 100644 mysql-test/std_data/mysql_upgrade/v2.frm create mode 100644 mysql-test/std_data/mysql_upgrade/v3.frm create mode 100644 mysql-test/std_data/mysql_upgrade/v4.frm diff --git a/mysql-test/std_data/mysql_upgrade/event.MYD b/mysql-test/std_data/mysql_upgrade/event.MYD new file mode 100644 index 00000000000..e69de29bb2d diff --git a/mysql-test/std_data/mysql_upgrade/event.MYI b/mysql-test/std_data/mysql_upgrade/event.MYI new file mode 100644 index 0000000000000000000000000000000000000000..d5c16c3892ffacd8ab4f90a09232baf03e6b0da1 GIT binary patch literal 2048 zcmeH@u?@m75Jmsl0a74AfdnN?LCX#>00nzMg(w+?5fBqlQXx^X1>xV>fe;0W9-m~t z^WD$I{*OmT;9Uy`tZ;?{1QYIz!uE!(h!I+OgW_9Brqxb4r_NHd*xs%&7iHyKO6oKn z@avtj3!n?5H7`L9xQ1N5-R39{mqYeEe}ohCSl=R-oy@J}aU{(*nOH@va%}Jg5w7=G;}&DS<7%{`MSz@epPynO?(6*waAykKLF@L^k>8R5$$(@)G9Vd{3`hnf z1CjyBfMh^2AQ_MhTuKHM6`%wv918=KW4sGc;1ty3pG3Q-z*~;d)SNcIl-*yUrZ~SX zpQp;eyjY%UBmZCV`H}zCR`6~QFY~VWBW9p&>XPOaALJ6ZFE~!01!z7rsMeeyx6%b^ zNd_bXk^#wpWI!??8ITNIJ_dfv!}7(uS|CTkAR1ph;L`6@;RZZXUMmAU&OU)Gybiyr zCu$4PQr!Cs%G#>B_Toi$yZ_Yp{zkh_xLjvYn^uV4xD6ym!nJe4zwuchSPI)(U-N&xtN%0jMCfD;97 z>T3Xhz6p>o)StkY3SMU=A%*hlDjcb>cZ|Tb0zh%8T!v3ncuoKr1WHQ}9>8ZR6h2)B z<#$Y4E?~%s3UAzcMkK_rA_9*DfFS}{tRV2kT+&J&fv@I(r5pm^%mK@Jtnw{ZQI5`-Ceb~9;xy|lRrePl>H zXV}<{^;h@c#|&QS2>=<(3Scpt0=dQN9`xscg%VQuOBQZ^o>0jBeJ*s&#X;~y!90~O zKd;@?jfKk-)$*xi`8mDviCDQ%s<2U}{G3MlRG>UjCr_oxXS(G7Bub3tyHqjiu<7tjd9Nx4ox50I-%^S9du3>pD;cpYN%_*tbmX1)(u@hT_vRMd=Lok*l zVZuyyilr$W+p}z%Vrf;A=v>FY=CMIdZI@6(Cu{}* z*B!fsSG*fsPuiyCalvt2^DQMYUd+iqz!!Y$in z9>r?5WwzOtXPT_;*j|fO+qlL&jH_EjXVj~@j#hIG+Y-2LILxqE4XYx>Et|S^Y-Pvf zHf}NrZ&Kmt)qA|Dy`xt}$Tn#+yCo7(;kshBd0@*Rral9jZA@_g-hCb$FW-$P5OJF4 z+H6-dJq)(kyTq{tTGeXXNE2-^LTeh%&Z+AdHJ4%27M&EEVHyq@mya6}Da0(gm;_VB ze(V?))-m*Wg>vFJw!^mYqZ_*h#W|3pNds6!H^gL`Icsr3jo{Yd4Wr&*f@wUj8qtXr j6VHfMH!M5|uS#9R^ Date: Mon, 13 Apr 2015 20:52:19 +1000 Subject: [PATCH 11/23] correct phase numbering in test results --- mysql-test/r/mysql_upgrade.result | 58 ++++++++++++++++++------------- 1 file changed, 33 insertions(+), 25 deletions(-) diff --git a/mysql-test/r/mysql_upgrade.result b/mysql-test/r/mysql_upgrade.result index fb831082dfe..78e49362032 100644 --- a/mysql-test/r/mysql_upgrade.result +++ b/mysql-test/r/mysql_upgrade.result @@ -1,6 +1,7 @@ Run mysql_upgrade once -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -31,13 +32,14 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK Run it again - should say already completed This installation of MySQL is already upgraded to VERSION, use --force if you still need to run mysql_upgrade Force should run it regardless of wether it's been run before -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -68,13 +70,14 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK CREATE USER mysqltest1@'%' IDENTIFIED by 'sakila'; GRANT ALL ON *.* TO mysqltest1@'%'; Run mysql_upgrade with password protected account -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -105,7 +108,7 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK DROP USER mysqltest1@'%'; Version check failed. Got the following error when calling the 'mysql' command line client @@ -115,8 +118,9 @@ Run mysql_upgrade with a non existing server socket mysqlcheck: Got error: 2005: Unknown MySQL server host 'not_existing_host' (errno) when trying to connect FATAL ERROR: Upgrade failed set GLOBAL sql_mode='STRICT_ALL_TABLES,ANSI_QUOTES,NO_ZERO_DATE'; -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -147,7 +151,7 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK set GLOBAL sql_mode=default; # @@ -158,8 +162,9 @@ CREATE PROCEDURE testproc() BEGIN END; UPDATE mysql.proc SET character_set_client = NULL WHERE name LIKE 'testproc'; UPDATE mysql.proc SET collation_connection = NULL WHERE name LIKE 'testproc'; UPDATE mysql.proc SET db_collation = NULL WHERE name LIKE 'testproc'; -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -190,7 +195,7 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK CALL testproc(); DROP PROCEDURE testproc; @@ -204,8 +209,9 @@ WARNING: NULL values of the 'db_collation' column ('mysql.proc' table) have been GRANT USAGE ON *.* TO 'user3'@'%'; GRANT ALL PRIVILEGES ON `roelt`.`test2` TO 'user3'@'%'; Run mysql_upgrade with all privileges on a user -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -236,7 +242,7 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK SHOW GRANTS FOR 'user3'@'%'; Grants for user3@% @@ -245,7 +251,7 @@ GRANT ALL PRIVILEGES ON `roelt`.`test2` TO 'user3'@'%' DROP USER 'user3'@'%'; End of 5.1 tests The --upgrade-system-tables option was used, databases won't be touched. -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 1/4: Running 'mysql_fix_privilege_tables'... OK # # Bug#11827359 60223: MYSQL_UPGRADE PROBLEM WITH OPTION @@ -253,8 +259,9 @@ OK # # Droping the previously created mysql_upgrade_info file.. # Running mysql_upgrade with --skip-write-binlog.. -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -285,7 +292,7 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK # # MDEV-4332 Increase username length from 16 characters @@ -313,8 +320,9 @@ GRANT INSERT ON mysql.user TO very_long_user_name_number_2; GRANT UPDATE (User) ON mysql.db TO very_long_user_name_number_1; GRANT UPDATE (User) ON mysql.db TO very_long_user_name_number_2; CREATE PROCEDURE test.pr() BEGIN END; -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -345,7 +353,7 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK SELECT definer FROM mysql.proc WHERE db = 'test' AND name = 'pr'; definer From 28b173134ee1634a2489d3cef6faf2f3ea1f6ab4 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Mon, 13 Apr 2015 21:12:23 +1000 Subject: [PATCH 12/23] Allow REPAIR NO_WRITE_TO_BINLOG as per serg's review > + if (lex->no_write_to_binlog && lex->only_view) > + { > + my_parse_error(ER(ER_SYNTAX_ERROR)); > + MYSQL_YYABORT; Why? REPAIR NO_WRITE_TO_BINLOG VIEW makes perfect sense to me, why did you want to disallow it? --- sql/sql_yacc.yy | 5 ----- 1 file changed, 5 deletions(-) diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index d9faaf287c2..dfbc6c43399 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -7197,11 +7197,6 @@ repair: LEX *lex=Lex; lex->sql_command = SQLCOM_REPAIR; lex->no_write_to_binlog= $2; - if (lex->no_write_to_binlog && lex->only_view) - { - my_parse_error(ER(ER_SYNTAX_ERROR)); - MYSQL_YYABORT; - } lex->check_opt.init(); lex->alter_info.reset(); /* Will be overriden during execution. */ From fc277cd4ba6c506a6f6c71e04c462b24a3fcfb26 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Mon, 13 Apr 2015 22:17:57 +1000 Subject: [PATCH 13/23] Add --fix-tables option to mysql-check Mainly so that mysql_upgrade.c can use --skip-fix-tables Correct mysql_upgrade_view test output based on phases and previous error message changes. --- client/mysql_upgrade.c | 1 + client/mysqlcheck.c | 22 +++++++++++++++++++--- mysql-test/r/mysql_upgrade_view.result | 14 +++++++------- 3 files changed, 27 insertions(+), 10 deletions(-) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index 88bd09d0b95..d18f01dbb28 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -793,6 +793,7 @@ static int run_mysqlcheck_views(void) ds_args.str, "--all-databases", "--fix-view-algorithm", + "--skip-fix-tables", opt_verbose ? "--verbose": "", opt_silent ? "--silent": "", opt_write_binlog ? "--write-binlog" : "--skip-write-binlog", diff --git a/client/mysqlcheck.c b/client/mysqlcheck.c index c3b8d01a722..2f67452a2d5 100644 --- a/client/mysqlcheck.c +++ b/client/mysqlcheck.c @@ -43,7 +43,7 @@ static my_bool opt_alldbs = 0, opt_check_only_changed = 0, opt_extended = 0, opt_silent = 0, opt_auto_repair = 0, ignore_errors = 0, tty_password= 0, opt_frm= 0, debug_info_flag= 0, debug_check_flag= 0, opt_fix_table_names= 0, opt_fix_db_names= 0, opt_upgrade= 0, - opt_fix_view_algorithm= 0; + opt_fix_view_algorithm= 0, opt_fix_tables= 1; static my_bool opt_write_binlog= 1, opt_flush_tables= 0; static uint verbose = 0, opt_mysql_port=0; static int my_end_arg; @@ -200,6 +200,9 @@ static struct my_option my_long_options[] = {"fix-view-algorithm", 'y', "Fix view algorithm view field if it is not new MariaDB view.", &opt_fix_view_algorithm, &opt_fix_view_algorithm, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, + {"fix-tables", 'Y', + "Fix tables. Usually the default however mysql_upgrade will run with --skip-fix-tables.", + &opt_fix_tables, &opt_fix_tables, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0} }; @@ -369,6 +372,12 @@ static int get_options(int *argc, char ***argv) if ((ho_error=handle_options(argc, argv, my_long_options, get_one_option))) exit(ho_error); + if (what_to_do==DO_REPAIR && !(opt_fix_view_algorithm || opt_fix_tables)) + { + fprintf(stderr, "Error: %s doesn't support repair command without either fix-view-algorithm or fix-tables specified.\n", + my_progname); + exit(1); + } if (opt_fix_view_algorithm && what_to_do!=DO_REPAIR) { if (!what_to_do) @@ -641,9 +650,10 @@ static int process_all_tables_in_db(char *database) while ((row = mysql_fetch_row(res))) { - if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) + if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0) && + opt_fix_view_algorithm) tot_views_length+= fixed_name_length(row[0]) + 2; - else + else if (opt_fix_tables) tot_length+= fixed_name_length(row[0]) + 2; } mysql_data_seek(res, 0); @@ -671,6 +681,8 @@ static int process_all_tables_in_db(char *database) } else { + if (!opt_fix_tables) + continue; end= fix_table_name(end, row[0]); *end++= ','; } @@ -696,7 +708,11 @@ static int process_all_tables_in_db(char *database) view= TRUE; } else + { + if (!opt_fix_tables) + continue; view= FALSE; + } if (system_database && (!strcmp(row[0], "general_log") || !strcmp(row[0], "slow_log"))) diff --git a/mysql-test/r/mysql_upgrade_view.result b/mysql-test/r/mysql_upgrade_view.result index b6df411d37f..3ce1bf51544 100644 --- a/mysql-test/r/mysql_upgrade_view.result +++ b/mysql-test/r/mysql_upgrade_view.result @@ -16,13 +16,13 @@ show create view v4; View Create View character_set_client collation_connection v4 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v4` AS select `t1`.`a` AS `a` from `t1` latin1 latin1_swedish_ci MySQL upgrade detected -Phase 0: Fixing views -test.v1 view is repaired -test.v2 view is repaired -test.v3 view is repaired +Phase 1/4: Fixing views +test.v1 OK +test.v2 OK +test.v3 OK test.v4 OK -Phase 1/3: Fixing table and database names -Phase 2/3: Checking and upgrading tables +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables Processing databases information_schema mtr @@ -55,7 +55,7 @@ mysql.user OK performance_schema test test.t1 OK -Phase 3/3: Running 'mysql_fix_privilege_tables'... +Phase 4/4: Running 'mysql_fix_privilege_tables'... OK show create view v1; View Create View character_set_client collation_connection From 7229b19c67d12ff579c64f1184e951015aa2f9c9 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Mon, 13 Apr 2015 22:28:12 +1000 Subject: [PATCH 14/23] remove include sql_view.h from sql_table.cc - unneeded --- sql/sql_table.cc | 1 - 1 file changed, 1 deletion(-) diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 39e8e0d0d55..dfd085baa76 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -28,7 +28,6 @@ #include "sql_base.h" // open_table_uncached, lock_table_names #include "lock.h" // mysql_unlock_tables #include "strfunc.h" // find_type2, find_set -#include "sql_view.h" // view_check #include "sql_truncate.h" // regenerate_locked_table #include "sql_partition.h" // mem_alloc_error, // generate_partition_syntax, From 29721d7d5f85fe323d70f1856aa1e5294e14074a Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Mon, 13 Apr 2015 22:31:44 +1000 Subject: [PATCH 15/23] mariadb_fix_view need only check view->mariadb_version --- sql/sql_view.cc | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/sql/sql_view.cc b/sql/sql_view.cc index 8f2e6092ff2..c5eb5c5f7ef 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -818,8 +818,7 @@ int mariadb_fix_view(THD *thd, TABLE_LIST *view, bool wrong_checksum, LEX_STRING dir, file, path; DBUG_ENTER("mariadb_fix_view"); - if (view->algorithm == VIEW_ALGORITHM_UNDEFINED && - !wrong_checksum && view->mariadb_version) + if (view->mariadb_version) DBUG_RETURN(HA_ADMIN_OK); make_view_filename(&dir, dir_buff, sizeof(dir_buff), From 8a827d530a67d40332668d31683a45f583974935 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Mon, 13 Apr 2015 22:39:37 +1000 Subject: [PATCH 16/23] avoid calling runctiosn in DBUG_RETURN --- sql/sql_view.cc | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/sql/sql_view.cc b/sql/sql_view.cc index c5eb5c5f7ef..46998c215da 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -2077,9 +2077,11 @@ int view_repair(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt) ((check_opt->sql_flags & TT_FROM_MYSQL) && (!view->mariadb_version)); bool wrong_checksum= view_checksum(thd, view); + int ret; if (wrong_checksum || swap_alg) { - DBUG_RETURN(mariadb_fix_view(thd, view, wrong_checksum, swap_alg)); + ret= mariadb_fix_view(thd, view, wrong_checksum, swap_alg); + DBUG_RETURN(ret); } DBUG_RETURN(HA_ADMIN_OK); } From 622891c6e17b714d92534cb46bf0d573fa4e3ba1 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Mon, 13 Apr 2015 22:58:45 +1000 Subject: [PATCH 17/23] mariadb_fix_view to allow fixing of view->mariadb_version Reverts the wrong_checksum part of 29721d7d5f85fe323d70f1856aa1e5294e14074a --- sql/sql_view.cc | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/sql/sql_view.cc b/sql/sql_view.cc index 46998c215da..da7ab7c79bc 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -818,7 +818,7 @@ int mariadb_fix_view(THD *thd, TABLE_LIST *view, bool wrong_checksum, LEX_STRING dir, file, path; DBUG_ENTER("mariadb_fix_view"); - if (view->mariadb_version) + if (!wrong_checksum && view->mariadb_version) DBUG_RETURN(HA_ADMIN_OK); make_view_filename(&dir, dir_buff, sizeof(dir_buff), @@ -2073,12 +2073,10 @@ int view_check(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt) int view_repair(THD *thd, TABLE_LIST *view, HA_CHECK_OPT *check_opt) { DBUG_ENTER("view_repair"); - bool swap_alg= - ((check_opt->sql_flags & TT_FROM_MYSQL) && - (!view->mariadb_version)); + bool swap_alg= (check_opt->sql_flags & TT_FROM_MYSQL); bool wrong_checksum= view_checksum(thd, view); int ret; - if (wrong_checksum || swap_alg) + if (wrong_checksum || swap_alg || (!view->mariadb_version)) { ret= mariadb_fix_view(thd, view, wrong_checksum, swap_alg); DBUG_RETURN(ret); From 76c18f7e76dff6f5c5f8986e0480074a3100fdbe Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Mon, 13 Apr 2015 23:25:23 +1000 Subject: [PATCH 18/23] sql_print_information corrected as checksum/swap don't always occur --- sql/sql_view.cc | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/sql/sql_view.cc b/sql/sql_view.cc index da7ab7c79bc..24f01aeaa76 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -856,6 +856,8 @@ int mariadb_fix_view(THD *thd, TABLE_LIST *view, bool wrong_checksum, else view->algorithm= VIEW_ALGORITHM_MERGE; } + else + swap_alg= 0; if (wrong_checksum) { if (view->md5.length != 32) @@ -875,10 +877,14 @@ int mariadb_fix_view(THD *thd, TABLE_LIST *view, bool wrong_checksum, view->db, view->table_name); DBUG_RETURN(HA_ADMIN_INTERNAL_ERROR); } - sql_print_information("View '%-.192s'.'%-.192s': algorithm swapped to '%s'", - view->db, view->table_name, - (view->algorithm == VIEW_ALGORITHM_MERGE)? - "MERGE":"TEMPTABLE"); + sql_print_information("View '%-.192s'.'%-.192s': versioned to %llu%s%s", + view->db, view->table_name, view->mariadb_version, + (wrong_checksum ? ", and checksum corrected" : ""), + (swap_alg ? + ((view->algorithm == VIEW_ALGORITHM_MERGE) ? + ", and algorithm swapped to 'MERGE'" + : ", and algorithm swapped to 'TEMPTABLE'") + : "")); DBUG_RETURN(HA_ADMIN_OK); From c584058f8f227a2004f9fdf6fd0897e11fd53eda Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Tue, 14 Apr 2015 11:01:31 +1000 Subject: [PATCH 19/23] Update tests for mysql_upgrade_view Add bad checksum test Validate REPAIR VIEW {table} add mariadb-version to the frm Add tests for the binary logging of REPAIR VIEW --- mysql-test/r/mysql_upgrade_view.result | 133 +++++++++++++++++- .../std_data/mysql_upgrade/v1badcheck.frm | 15 ++ mysql-test/t/mysql_upgrade_view.test | 101 ++++++++++++- 3 files changed, 242 insertions(+), 7 deletions(-) create mode 100644 mysql-test/std_data/mysql_upgrade/v1badcheck.frm diff --git a/mysql-test/r/mysql_upgrade_view.result b/mysql-test/r/mysql_upgrade_view.result index 3ce1bf51544..aa4841c213a 100644 --- a/mysql-test/r/mysql_upgrade_view.result +++ b/mysql-test/r/mysql_upgrade_view.result @@ -1,7 +1,109 @@ -drop table if exists t1,v1,v2,v3,v4; -drop view if exists t1,v1,v2,v3,v4; -flush tables; +set sql_log_bin=0; +drop table if exists t1,v1,v2,v3,v4,v1badcheck; +drop view if exists t1,v1,v2,v3,v4,v1badcheck; create table t1(a int); +create table kv(k varchar(30) NOT NULL PRIMARY KEY,v varchar(50)); +flush tables; +Phase 1/4: Fixing views - skipped - not required +Phase 2/4: Fixing table and database names +Phase 3/4: Checking and upgrading tables +Processing databases +information_schema +mtr +mtr.global_suppressions OK +mtr.test_suppressions OK +mysql +mysql.columns_priv OK +mysql.db OK +mysql.event OK +mysql.func OK +mysql.help_category OK +mysql.help_keyword OK +mysql.help_relation OK +mysql.help_topic OK +mysql.host OK +mysql.ndb_binlog_index OK +mysql.plugin OK +mysql.proc OK +mysql.procs_priv OK +mysql.proxies_priv OK +mysql.servers OK +mysql.tables_priv OK +mysql.time_zone OK +mysql.time_zone_leap_second OK +mysql.time_zone_name OK +mysql.time_zone_transition OK +mysql.time_zone_transition_type OK +mysql.user OK +performance_schema +test +test.kv OK +test.t1 OK +Phase 4/4: Running 'mysql_fix_privilege_tables'... +OK +show create view v1; +View Create View character_set_client collation_connection +v1 CREATE ALGORITHM=MERGE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v1` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v2; +View Create View character_set_client collation_connection +v2 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +show create view v3; +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select `t1`.`a` AS `a` from `t1` utf8 utf8_general_ci +set sql_log_bin=1; +REPAIR VIEW v1,v2; +Table Op Msg_type Msg_text +test.v1 repair status OK +test.v2 repair status OK +REPAIR VIEW v1badcheck; +Table Op Msg_type Msg_text +test.v1badcheck repair status OK +REPAIR NO_WRITE_TO_BINLOG VIEW v3; +Table Op Msg_type Msg_text +test.v3 repair status OK +set sql_log_bin=0; +show binlog events from ; +Log_name Pos Event_type Server_id End_log_pos Info +master-bin.000001 # Query # # use `test`; REPAIR VIEW v1,v2 +master-bin.000001 # Query # # use `test`; REPAIR VIEW v1badcheck +LOAD DATA INFILE 'MYSQLD_DATADIR/test/v1.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +k v +algorithm 1 +md5 5e6eaf216e7b016fcedfd4e1113517af +SELECT k from kv where k ='mariadb-version'; +k +mariadb-version +truncate table kv; +LOAD DATA INFILE 'MYSQLD_DATADIR/test/v2.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +k v +algorithm 2 +md5 5e6eaf216e7b016fcedfd4e1113517af +SELECT k from kv where k ='mariadb-version'; +k +mariadb-version +truncate table kv; +LOAD DATA INFILE 'MYSQLD_DATADIR/test/v3.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +k v +algorithm 0 +md5 5e6eaf216e7b016fcedfd4e1113517af +SELECT k from kv where k ='mariadb-version'; +k +mariadb-version +truncate table kv; +LOAD DATA INFILE 'MYSQLD_DATADIR/test/v1badcheck.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +k v +algorithm 1 +md5 5e6eaf216e7b016fcedfd4e1113517af +SELECT k from kv where k ='mariadb-version'; +k +mariadb-version +truncate table kv; +drop view if exists v1,v2,v3,v1badcheck; +flush tables; create algorithm=temptable view v4 as select a from t1; show create view v1; View Create View character_set_client collation_connection @@ -54,6 +156,7 @@ mysql.time_zone_transition_type OK mysql.user OK performance_schema test +test.kv OK test.t1 OK Phase 4/4: Running 'mysql_fix_privilege_tables'... OK @@ -69,6 +172,30 @@ v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VI show create view v4; View Create View character_set_client collation_connection v4 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v4` AS select `t1`.`a` AS `a` from `t1` latin1 latin1_swedish_ci +LOAD DATA INFILE 'MYSQLD_DATADIR/test/v1.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +k v +algorithm 2 +md5 5e6eaf216e7b016fcedfd4e1113517af +SELECT k from kv where k ='mariadb-version'; +k +mariadb-version +truncate table kv; +drop view if exists v1,v2,v3; flush tables; +test.v1 OK +test.v2 OK +test.v3 OK +test.v4 OK +show binlog events from ; +Log_name Pos Event_type Server_id End_log_pos Info +master-bin.000001 # Query # # use `test`; REPAIR VIEW v1,v2 +master-bin.000001 # Query # # use `test`; REPAIR VIEW v1badcheck +master-bin.000001 # Query # # use `test`; REPAIR VIEW `v1` FROM MYSQL +master-bin.000001 # Query # # use `test`; REPAIR VIEW `v2` FROM MYSQL +master-bin.000001 # Query # # use `test`; REPAIR VIEW `v3` FROM MYSQL +master-bin.000001 # Query # # use `test`; REPAIR VIEW `v4` FROM MYSQL +flush tables; +drop table if exists kv; drop view v1,v2,v3,v4; drop table t1; diff --git a/mysql-test/std_data/mysql_upgrade/v1badcheck.frm b/mysql-test/std_data/mysql_upgrade/v1badcheck.frm new file mode 100644 index 00000000000..a1e3bfe5cbc --- /dev/null +++ b/mysql-test/std_data/mysql_upgrade/v1badcheck.frm @@ -0,0 +1,15 @@ +TYPE=VIEW +query=select `test`.`t1`.`a` AS `a` from `test`.`t1` +md5=00000000000000000000000000000000 +updatable=0 +algorithm=1 +definer_user=root +definer_host=localhost +suid=2 +with_check_option=0 +timestamp=2014-12-11 15:26:20 +create-version=1 +source=select a from t1 +client_cs_name=utf8 +connection_cl_name=utf8_general_ci +view_body_utf8=select `test`.`t1`.`a` AS `a` from `test`.`t1` diff --git a/mysql-test/t/mysql_upgrade_view.test b/mysql-test/t/mysql_upgrade_view.test index 42c0a7f3c75..9bd86abd724 100644 --- a/mysql-test/t/mysql_upgrade_view.test +++ b/mysql-test/t/mysql_upgrade_view.test @@ -1,11 +1,72 @@ +-- source include/have_log_bin.inc +set sql_log_bin=0; --disable_warnings -drop table if exists t1,v1,v2,v3,v4; -drop view if exists t1,v1,v2,v3,v4; +drop table if exists t1,v1,v2,v3,v4,v1badcheck; +drop view if exists t1,v1,v2,v3,v4,v1badcheck; --enable_warnings +create table t1(a int); +create table kv(k varchar(30) NOT NULL PRIMARY KEY,v varchar(50)); + let $MYSQLD_DATADIR= `select @@datadir`; +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v1.frm $MYSQLD_DATADIR/test/v1.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v1badcheck.frm $MYSQLD_DATADIR/test/v1badcheck.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v2.frm $MYSQLD_DATADIR/test/v2.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v3.frm $MYSQLD_DATADIR/test/v3.frm + +flush tables; + +--replace_result $MYSQLTEST_VARDIR var +--exec $MYSQL_UPGRADE --force 2>&1 + +# "Phase 1/4: Fixing views - skipped - not required" expected + +show create view v1; +show create view v2; +show create view v3; + +# Now force a mariadb version to be added + +set sql_log_bin=1; +REPAIR VIEW v1,v2; +REPAIR VIEW v1badcheck; +REPAIR NO_WRITE_TO_BINLOG VIEW v3; +set sql_log_bin=0; + +--source include/show_binlog_events.inc + +--replace_result $MYSQLD_DATADIR MYSQLD_DATADIR +eval LOAD DATA INFILE '$MYSQLD_DATADIR/test/v1.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +SELECT k from kv where k ='mariadb-version'; +truncate table kv; + +--replace_result $MYSQLD_DATADIR MYSQLD_DATADIR +eval LOAD DATA INFILE '$MYSQLD_DATADIR/test/v2.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +SELECT k from kv where k ='mariadb-version'; +truncate table kv; + +--replace_result $MYSQLD_DATADIR MYSQLD_DATADIR +eval LOAD DATA INFILE '$MYSQLD_DATADIR/test/v3.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +SELECT k from kv where k ='mariadb-version'; +truncate table kv; + +--replace_result $MYSQLD_DATADIR MYSQLD_DATADIR +eval LOAD DATA INFILE '$MYSQLD_DATADIR/test/v1badcheck.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +SELECT k from kv where k ='mariadb-version'; +truncate table kv; + +--disable_warnings +drop view if exists v1,v2,v3,v1badcheck; +--enable_warnings + +# Make it look like a MySQL directory now + --copy_file $MYSQLD_DATADIR/mysql/event.MYI $MYSQLD_DATADIR/mysql/ev_bk.MYI --copy_file $MYSQLD_DATADIR/mysql/event.MYD $MYSQLD_DATADIR/mysql/ev_bk.MYD --copy_file $MYSQLD_DATADIR/mysql/event.frm $MYSQLD_DATADIR/mysql/ev_bk.frm @@ -15,19 +76,20 @@ let $MYSQLD_DATADIR= `select @@datadir`; --copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.MYI $MYSQLD_DATADIR/mysql/event.MYI --copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.MYD $MYSQLD_DATADIR/mysql/event.MYD --copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.frm $MYSQLD_DATADIR/mysql/event.frm + --copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v1.frm $MYSQLD_DATADIR/test/v1.frm --copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v2.frm $MYSQLD_DATADIR/test/v2.frm --copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v3.frm $MYSQLD_DATADIR/test/v3.frm flush tables; -create table t1(a int); create algorithm=temptable view v4 as select a from t1; show create view v1; show create view v2; show create view v3; show create view v4; +# here we test the fixing views does occur --replace_result $MYSQLTEST_VARDIR var --exec $MYSQL_UPGRADE --force 2>&1 @@ -36,6 +98,37 @@ show create view v2; show create view v3; show create view v4; +--replace_result $MYSQLD_DATADIR MYSQLD_DATADIR +eval LOAD DATA INFILE '$MYSQLD_DATADIR/test/v1.frm' REPLACE INTO TABLE kv FIELDS TERMINATED BY '='; +SELECT k,v from kv where k in ('md5','algorithm'); +SELECT k from kv where k ='mariadb-version'; +truncate table kv; + +--disable_warnings +drop view if exists v1,v2,v3; +--enable_warnings + + +--remove_file $MYSQLD_DATADIR/mysql/event.MYI +--remove_file $MYSQLD_DATADIR/mysql/event.MYD +--remove_file $MYSQLD_DATADIR/mysql/event.frm + +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.MYI $MYSQLD_DATADIR/mysql/event.MYI +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.MYD $MYSQLD_DATADIR/mysql/event.MYD +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/event.frm $MYSQLD_DATADIR/mysql/event.frm + +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v1.frm $MYSQLD_DATADIR/test/v1.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v2.frm $MYSQLD_DATADIR/test/v2.frm +--copy_file $MYSQL_TEST_DIR/std_data/mysql_upgrade/v3.frm $MYSQLD_DATADIR/test/v3.frm +flush tables; + +# check of binlog +--exec $MYSQL_CHECK --write-binlog --fix-view-algorithm --skip-fix-tables --all-databases 2>&1 + +--source include/show_binlog_events.inc + +# back to mariadb default + --remove_file $MYSQLD_DATADIR/mysql/event.MYI --remove_file $MYSQLD_DATADIR/mysql/event.MYD --remove_file $MYSQLD_DATADIR/mysql/event.frm @@ -47,7 +140,7 @@ show create view v4; --remove_file $MYSQLD_DATADIR/mysql/ev_bk.frm flush tables; +drop table if exists kv; drop view v1,v2,v3,v4; drop table t1; -#select sleep(100); From 808608cb3f4e10ba81679c94b2a299a32cf5e448 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Tue, 14 Apr 2015 11:26:13 +1000 Subject: [PATCH 20/23] corrected mysql_upgrade to always list output for every phase --- client/mysql_upgrade.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index d18f01dbb28..8fd28f2ab41 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -740,9 +740,10 @@ static void print_conn_args(const char *tool_name) static int run_mysqlcheck_upgrade(void) { + int retch; verbose("Phase %d/%d: Checking and upgrading tables", phase++, phases_total); print_conn_args("mysqlcheck"); - return run_tool(mysqlcheck_path, + retch= run_tool(mysqlcheck_path, NULL, /* Send output from mysqlcheck directly to screen */ "--no-defaults", ds_args.str, @@ -754,6 +755,9 @@ static int run_mysqlcheck_upgrade(void) opt_write_binlog ? "--write-binlog" : "--skip-write-binlog", "2>&1", NULL); + if (retch || opt_systables_only) + verbose("Phase %d/%d: Skipping 'mysql_fix_privilege_tables'... not needed", phase++, phases_total); + return retch; } #define EVENTS_STRUCT_LEN 7000 From 97e0aeaf72cde117b8d9551f68d407fa13aafbe1 Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Tue, 14 Apr 2015 12:43:50 +1000 Subject: [PATCH 21/23] mysqlcheck fix-view-algorithm -> upgrade-views Change mysqlcheck option to upgrade-views={NO,YES,FROM_MYSQL} mysql_upgrade now runs upgrade-views=yes to perform a checksum of all views and add mariadb-version by default. upgrade-views=from_mysql if MySQL is detected as teh origin version. --- client/client_priv.h | 1 + client/mysql_upgrade.c | 13 ++++--- client/mysqlcheck.c | 51 ++++++++++++++++++++------ mysql-test/r/mysql_upgrade.result | 16 ++++---- mysql-test/r/mysql_upgrade_view.result | 8 +++- mysql-test/t/mysql_upgrade_view.test | 6 +-- 6 files changed, 65 insertions(+), 30 deletions(-) diff --git a/client/client_priv.h b/client/client_priv.h index e206804d057..a66c3883654 100644 --- a/client/client_priv.h +++ b/client/client_priv.h @@ -79,6 +79,7 @@ enum options_client OPT_SLAP_COMMIT, OPT_SLAP_DETACH, OPT_SLAP_NO_DROP, + OPT_UPGRADE_VIEWS, OPT_MYSQL_REPLACE_INTO, OPT_BASE64_OUTPUT_MODE, OPT_SERVER_ID, OPT_FIX_TABLE_NAMES, OPT_FIX_DB_NAMES, OPT_SSL_VERIFY_SERVER_CERT, OPT_AUTO_VERTICAL_OUTPUT, diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index 8fd28f2ab41..98021dda377 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -784,19 +784,22 @@ static my_bool is_mysql() static int run_mysqlcheck_views(void) { - if (!is_mysql()) + const char *upgrade_views="--upgrade-views=YES"; + if (is_mysql()) { - verbose("Phase %d/%d: Fixing views - skipped - not required", phase++, phases_total); - return 0; + upgrade_views="--upgrade-views=FROM_MYSQL"; + verbose("Phase %d/%d: Fixing views from mysql", phase++, phases_total); } - verbose("Phase %d/%d: Fixing views", phase++, phases_total); + else + verbose("Phase %d/%d: Fixing views", phase++, phases_total); + print_conn_args("mysqlcheck"); return run_tool(mysqlcheck_path, NULL, /* Send output from mysqlcheck directly to screen */ "--no-defaults", ds_args.str, "--all-databases", - "--fix-view-algorithm", + upgrade_views, "--skip-fix-tables", opt_verbose ? "--verbose": "", opt_silent ? "--silent": "", diff --git a/client/mysqlcheck.c b/client/mysqlcheck.c index 2f67452a2d5..dfc743d5493 100644 --- a/client/mysqlcheck.c +++ b/client/mysqlcheck.c @@ -43,7 +43,7 @@ static my_bool opt_alldbs = 0, opt_check_only_changed = 0, opt_extended = 0, opt_silent = 0, opt_auto_repair = 0, ignore_errors = 0, tty_password= 0, opt_frm= 0, debug_info_flag= 0, debug_check_flag= 0, opt_fix_table_names= 0, opt_fix_db_names= 0, opt_upgrade= 0, - opt_fix_view_algorithm= 0, opt_fix_tables= 1; + opt_fix_tables= 1; static my_bool opt_write_binlog= 1, opt_flush_tables= 0; static uint verbose = 0, opt_mysql_port=0; static int my_end_arg; @@ -58,6 +58,20 @@ static uint opt_protocol=0; enum operations { DO_CHECK=1, DO_REPAIR, DO_ANALYZE, DO_OPTIMIZE, DO_UPGRADE }; +typedef enum { + UPGRADE_VIEWS_NO=0, + UPGRADE_VIEWS_YES=1, + UPGRADE_VIEWS_FROM_MYSQL=2, + UPGRADE_VIEWS_COUNT +} enum_upgrade_views; +const char *upgrade_views_opts[]= +{"NO", "YES", "FROM_MYSQL", NullS}; +TYPELIB upgrade_views_typelib= + { array_elements(upgrade_views_opts) - 1, "", + upgrade_views_opts, NULL }; +static enum_upgrade_views opt_upgrade_views= UPGRADE_VIEWS_NO; +static char *opt_upgrade_views_str= NullS; + static struct my_option my_long_options[] = { {"all-databases", 'A', @@ -197,9 +211,12 @@ static struct my_option my_long_options[] = NO_ARG, 0, 0, 0, 0, 0, 0}, {"version", 'V', "Output version information and exit.", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, - {"fix-view-algorithm", 'y', - "Fix view algorithm view field if it is not new MariaDB view.", - &opt_fix_view_algorithm, &opt_fix_view_algorithm, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, + {"upgrade-views", OPT_UPGRADE_VIEWS, + "Repairs/Upgrades views. 'No' (default) doesn't do anything to views. " + "'Yes' repairs the checksum and adds a MariaDB version to the frm table defination (if missing)." + "Using 'from_mysql' will, when upgrading from MySQL, and ensure the view algorithms are the" + "same as what they where previously.", + &opt_upgrade_views_str, &opt_upgrade_views_str, 0, GET_STR, OPT_ARG, 0, 0, 0, 0, 0, 0}, {"fix-tables", 'Y', "Fix tables. Usually the default however mysql_upgrade will run with --skip-fix-tables.", &opt_fix_tables, &opt_fix_tables, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0}, @@ -342,6 +359,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), case 'V': print_version(); exit(0); break; + case OPT_UPGRADE_VIEWS: + if (argument == NULL) + opt_upgrade_views= UPGRADE_VIEWS_NO; + else + { + opt_upgrade_views= (enum_upgrade_views) + (find_type_or_exit(argument, &upgrade_views_typelib, opt->name)-1); + } + break; case OPT_MYSQL_PROTOCOL: opt_protocol= find_type_or_exit(argument, &sql_protocol_typelib, opt->name); @@ -372,19 +398,19 @@ static int get_options(int *argc, char ***argv) if ((ho_error=handle_options(argc, argv, my_long_options, get_one_option))) exit(ho_error); - if (what_to_do==DO_REPAIR && !(opt_fix_view_algorithm || opt_fix_tables)) + if (what_to_do==DO_REPAIR && !(opt_upgrade_views || opt_fix_tables)) { - fprintf(stderr, "Error: %s doesn't support repair command without either fix-view-algorithm or fix-tables specified.\n", + fprintf(stderr, "Error: %s doesn't support repair command without either upgrade-views or fix-tables specified.\n", my_progname); exit(1); } - if (opt_fix_view_algorithm && what_to_do!=DO_REPAIR) + if (opt_upgrade_views && what_to_do!=DO_REPAIR) { if (!what_to_do) what_to_do= DO_REPAIR; else { - fprintf(stderr, "Error: %s doesn't support non-repair command with option fix-view-algorithm.\n", + fprintf(stderr, "Error: %s doesn't support non-repair command with option upgrade-views.\n", my_progname); exit(1); } @@ -651,7 +677,7 @@ static int process_all_tables_in_db(char *database) while ((row = mysql_fetch_row(res))) { if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0) && - opt_fix_view_algorithm) + opt_upgrade_views) tot_views_length+= fixed_name_length(row[0]) + 2; else if (opt_fix_tables) tot_length+= fixed_name_length(row[0]) + 2; @@ -674,7 +700,7 @@ static int process_all_tables_in_db(char *database) { if ((num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) { - if (!opt_fix_view_algorithm) + if (!opt_upgrade_views) continue; views_end= fix_table_name(views_end, row[0]); *views_end++= ','; @@ -703,7 +729,7 @@ static int process_all_tables_in_db(char *database) /* Skip views if we don't perform renaming. */ if ((what_to_do != DO_UPGRADE) && (num_columns == 2) && (strcmp(row[1], "VIEW") == 0)) { - if (!opt_fix_view_algorithm) + if (!opt_upgrade_views) continue; view= TRUE; } @@ -864,7 +890,8 @@ static int handle_request_for_tables(char *tables, uint length, my_bool view) if (opt_quick) end = strmov(end, " QUICK"); if (opt_extended) end = strmov(end, " EXTENDED"); if (opt_frm) end = strmov(end, " USE_FRM"); - if (opt_fix_view_algorithm && view) end = strmov(end, " FROM MYSQL"); + if (opt_upgrade_views==UPGRADE_VIEWS_FROM_MYSQL && view) + end = strmov(end, " FROM MYSQL"); break; case DO_ANALYZE: op= (opt_write_binlog) ? "ANALYZE" : "ANALYZE NO_WRITE_TO_BINLOG"; diff --git a/mysql-test/r/mysql_upgrade.result b/mysql-test/r/mysql_upgrade.result index 78e49362032..502242a9845 100644 --- a/mysql-test/r/mysql_upgrade.result +++ b/mysql-test/r/mysql_upgrade.result @@ -1,5 +1,5 @@ Run mysql_upgrade once -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -37,7 +37,7 @@ OK Run it again - should say already completed This installation of MySQL is already upgraded to VERSION, use --force if you still need to run mysql_upgrade Force should run it regardless of wether it's been run before -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -75,7 +75,7 @@ OK CREATE USER mysqltest1@'%' IDENTIFIED by 'sakila'; GRANT ALL ON *.* TO mysqltest1@'%'; Run mysql_upgrade with password protected account -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -118,7 +118,7 @@ Run mysql_upgrade with a non existing server socket mysqlcheck: Got error: 2005: Unknown MySQL server host 'not_existing_host' (errno) when trying to connect FATAL ERROR: Upgrade failed set GLOBAL sql_mode='STRICT_ALL_TABLES,ANSI_QUOTES,NO_ZERO_DATE'; -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -162,7 +162,7 @@ CREATE PROCEDURE testproc() BEGIN END; UPDATE mysql.proc SET character_set_client = NULL WHERE name LIKE 'testproc'; UPDATE mysql.proc SET collation_connection = NULL WHERE name LIKE 'testproc'; UPDATE mysql.proc SET db_collation = NULL WHERE name LIKE 'testproc'; -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -209,7 +209,7 @@ WARNING: NULL values of the 'db_collation' column ('mysql.proc' table) have been GRANT USAGE ON *.* TO 'user3'@'%'; GRANT ALL PRIVILEGES ON `roelt`.`test2` TO 'user3'@'%'; Run mysql_upgrade with all privileges on a user -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -259,7 +259,7 @@ OK # # Droping the previously created mysql_upgrade_info file.. # Running mysql_upgrade with --skip-write-binlog.. -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -320,7 +320,7 @@ GRANT INSERT ON mysql.user TO very_long_user_name_number_2; GRANT UPDATE (User) ON mysql.db TO very_long_user_name_number_1; GRANT UPDATE (User) ON mysql.db TO very_long_user_name_number_2; CREATE PROCEDURE test.pr() BEGIN END; -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases diff --git a/mysql-test/r/mysql_upgrade_view.result b/mysql-test/r/mysql_upgrade_view.result index aa4841c213a..aa393190e82 100644 --- a/mysql-test/r/mysql_upgrade_view.result +++ b/mysql-test/r/mysql_upgrade_view.result @@ -4,7 +4,11 @@ drop view if exists t1,v1,v2,v3,v4,v1badcheck; create table t1(a int); create table kv(k varchar(30) NOT NULL PRIMARY KEY,v varchar(50)); flush tables; -Phase 1/4: Fixing views - skipped - not required +Phase 1/4: Fixing views +test.v1 OK +test.v1badcheck OK +test.v2 OK +test.v3 OK Phase 2/4: Fixing table and database names Phase 3/4: Checking and upgrading tables Processing databases @@ -118,7 +122,7 @@ show create view v4; View Create View character_set_client collation_connection v4 CREATE ALGORITHM=TEMPTABLE DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v4` AS select `t1`.`a` AS `a` from `t1` latin1 latin1_swedish_ci MySQL upgrade detected -Phase 1/4: Fixing views +Phase 1/4: Fixing views from mysql test.v1 OK test.v2 OK test.v3 OK diff --git a/mysql-test/t/mysql_upgrade_view.test b/mysql-test/t/mysql_upgrade_view.test index 9bd86abd724..1b491a71227 100644 --- a/mysql-test/t/mysql_upgrade_view.test +++ b/mysql-test/t/mysql_upgrade_view.test @@ -21,7 +21,7 @@ flush tables; --replace_result $MYSQLTEST_VARDIR var --exec $MYSQL_UPGRADE --force 2>&1 -# "Phase 1/4: Fixing views - skipped - not required" expected +# "Phase 1/4: Fixing views" expected (without from_mysql) show create view v1; show create view v2; @@ -89,7 +89,7 @@ show create view v2; show create view v3; show create view v4; -# here we test the fixing views does occur +# here we test the fixing views from mysql to occur --replace_result $MYSQLTEST_VARDIR var --exec $MYSQL_UPGRADE --force 2>&1 @@ -123,7 +123,7 @@ drop view if exists v1,v2,v3; flush tables; # check of binlog ---exec $MYSQL_CHECK --write-binlog --fix-view-algorithm --skip-fix-tables --all-databases 2>&1 +--exec $MYSQL_CHECK --write-binlog --upgrade-views=FROM_MYSQL --skip-fix-tables --all-databases 2>&1 --source include/show_binlog_events.inc From 4987080ddb42abf1a9111bd6a79e7bed746b66ff Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Tue, 14 Apr 2015 13:26:22 +1000 Subject: [PATCH 22/23] Don't run upgrade-views if not mysql or --upgrade-system-tables --- client/mysql_upgrade.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/client/mysql_upgrade.c b/client/mysql_upgrade.c index 98021dda377..97e2ad92239 100644 --- a/client/mysql_upgrade.c +++ b/client/mysql_upgrade.c @@ -790,6 +790,11 @@ static int run_mysqlcheck_views(void) upgrade_views="--upgrade-views=FROM_MYSQL"; verbose("Phase %d/%d: Fixing views from mysql", phase++, phases_total); } + else if (opt_systables_only) + { + verbose("Phase %d/%d: Fixing views - skipped - not required", phase++, phases_total); + return 0; + } else verbose("Phase %d/%d: Fixing views", phase++, phases_total); From 83ce3529b8b2ba5b8070d12aaecbb6c3e3fcaeca Mon Sep 17 00:00:00 2001 From: Daniel Black Date: Tue, 14 Apr 2015 13:26:55 +1000 Subject: [PATCH 23/23] quote table name in mysql_check:is_view. increment version too --- client/mysqlcheck.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/client/mysqlcheck.c b/client/mysqlcheck.c index dfc743d5493..43c7ff0d8a1 100644 --- a/client/mysqlcheck.c +++ b/client/mysqlcheck.c @@ -18,7 +18,7 @@ /* By Jani Tolonen, 2001-04-20, MySQL Development Team */ -#define CHECK_VERSION "2.7.1" +#define CHECK_VERSION "2.7.2-MariaDB" #include "client_priv.h" #include @@ -526,12 +526,14 @@ static int is_view(const char *table, uint length) if (!(query =(char *) my_malloc((sizeof(char)*(length+110)), MYF(MY_WME)))) DBUG_RETURN(-1); - ptr= strmov(query, "SHOW CREATE TABLE "); + ptr= strmov(query, "SHOW CREATE TABLE `"); ptr= strxmov(ptr, table, NullS); + ptr= strxmov(ptr, "`", NullS); if (mysql_query(sock, query)) { fprintf(stderr, "Failed to %s\n", query); fprintf(stderr, "Error: %s\n", mysql_error(sock)); + my_free(query); DBUG_RETURN(-1); } res= mysql_store_result(sock);