Commit 193725b8 authored by Aleksey Midenkov's avatar Aleksey Midenkov

MDEV-7318 RENAME INDEX

This patch adds support of RENAME INDEX operation to the ALTER TABLE
statement. Code which determines if ALTER TABLE can be done in-place
for "simple" storage engines like MyISAM, Heap and etc. was updated to
handle ALTER TABLE ... RENAME INDEX as an in-place operation. Support
for in-place ALTER TABLE ... RENAME INDEX for InnoDB was covered by
MDEV-13301.

Syntax changes
==============

A new type of <alter_specification> is added:

<rename index clause> ::= RENAME ( INDEX | KEY ) <oldname> TO <newname>

Where <oldname> and <newname> are identifiers for old name and new
name of the index.

Semantic changes
================

The result of "ALTER TABLE t1 RENAME INDEX a TO b" is a table which
contents and structure are identical to the old version of 't1' with
the only exception index 'a' being called 'b'.

Neither <oldname> nor <newname> can be "primary". The index being
renamed should exist and its new name should not be occupied
by another index on the same table.

Related to: WL#6555, MDEV-13301
parent fa8ad754
......@@ -2849,5 +2849,398 @@ DROP VIEW v1;
DROP TABLE t3,t1,t2;
SET DEFAULT_STORAGE_ENGINE= @save_default_engine;
#
# MDEV-7318 RENAME INDEX
#
#
# 1) Tests for syntax and semantics of ALTER TABLE RENAME
# KEY/INDEX result.
#
# 1.a) Both RENAME KEY and RENAME INDEX variants should be
# allowed and produce expected results.
create table t1 (pk int primary key, i int, j int, key a(i));
alter table t1 rename key a to b;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `b` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 rename index b to c;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
# 1.b) It should be impossible to rename index that doesn't
# exists, dropped or added within the same ALTER TABLE.
alter table t1 rename key d to e;
ERROR 42000: Key 'd' doesn't exist in table 't1'
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 drop key c, rename key c to d;
ERROR 42000: Key 'c' doesn't exist in table 't1'
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 add key d(j), rename key d to e;
ERROR 42000: Key 'd' doesn't exist in table 't1'
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
# 1.c) It should be impossible to rename index to a name
# which is already used by another index, or is used
# by index which is added within the same ALTER TABLE.
alter table t1 add key d(j);
alter table t1 rename key c to d;
ERROR 42000: Duplicate key name 'd'
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`i`),
KEY `d` (`j`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 drop key d;
alter table t1 add key d(j), rename key c to d;
ERROR 42000: Duplicate key name 'd'
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
# 1.d) It should be possible to rename index to a name
# which belongs to index which is dropped within the
# same ALTER TABLE.
alter table t1 add key d(j);
alter table t1 drop key c, rename key d to c;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`j`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
# 1.e) We disallow renaming from/to PRIMARY as it might
# lead to some other key becoming "primary" internally,
# which will be interpreted as dropping/addition of
# primary key.
alter table t1 rename key primary to d;
ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'primary to d' at line 1
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`j`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
# Even using 'funny' syntax.
alter table t1 rename key `primary` to d;
ERROR 42000: Incorrect index name 'primary'
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`j`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 rename key c to primary;
ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'primary' at line 1
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`j`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 rename key c to `primary`;
ERROR 42000: Incorrect index name 'primary'
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`pk` int(11) NOT NULL,
`i` int(11) DEFAULT NULL,
`j` int(11) DEFAULT NULL,
PRIMARY KEY (`pk`),
KEY `c` (`j`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
drop table t1;
#
# 2) More complex tests for semantics of ALTER TABLE.
#
# 2.a) Check that standalone RENAME KEY works as expected
# for unique and non-unique indexes.
create table t1 (a int, unique u(a), b int, key k(b));
alter table t1 rename key u to uu;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`a` int(11) DEFAULT NULL,
`b` int(11) DEFAULT NULL,
UNIQUE KEY `uu` (`a`),
KEY `k` (`b`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 rename key k to kk;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`a` int(11) DEFAULT NULL,
`b` int(11) DEFAULT NULL,
UNIQUE KEY `uu` (`a`),
KEY `kk` (`b`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
# 2.b) Check how that this clause can be mixed with other
# clauses which don't affect key or its columns.
alter table t1 rename key kk to kkk, add column c int;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`a` int(11) DEFAULT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
UNIQUE KEY `uu` (`a`),
KEY `kkk` (`b`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 rename key uu to uuu, add key c(c);
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`a` int(11) DEFAULT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
UNIQUE KEY `uuu` (`a`),
KEY `kkk` (`b`),
KEY `c` (`c`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 rename key kkk to k, drop key uuu;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`a` int(11) DEFAULT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
KEY `k` (`b`),
KEY `c` (`c`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
alter table t1 rename key k to kk, rename to t2;
show create table t2;
Table Create Table
t2 CREATE TABLE `t2` (
`a` int(11) DEFAULT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
KEY `kk` (`b`),
KEY `c` (`c`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
drop table t2;
#
# 3) Test coverage for handling of RENAME INDEX clause in
# various storage engines and using different ALTER
# algorithm.
#
# 3.a) Test coverage for simple storage engines (MyISAM/Heap).
create table t1 (i int, key k(i)) engine=myisam;
insert into t1 values (1);
create table t2 (i int, key k(i)) engine=memory;
insert into t2 values (1);
# MyISAM and Heap should be able to handle key renaming in-place.
alter table t1 algorithm=inplace, rename key k to kk;
alter table t2 algorithm=inplace, rename key k to kk;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`i` int(11) DEFAULT NULL,
KEY `kk` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
show create table t2;
Table Create Table
t2 CREATE TABLE `t2` (
`i` int(11) DEFAULT NULL,
KEY `kk` (`i`)
) ENGINE=MEMORY DEFAULT CHARSET=latin1
# So by default in-place algorithm should be chosen.
# (ALTER TABLE should report 0 rows affected).
alter table t1 rename key kk to kkk;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
alter table t2 rename key kk to kkk;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`i` int(11) DEFAULT NULL,
KEY `kkk` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
show create table t2;
Table Create Table
t2 CREATE TABLE `t2` (
`i` int(11) DEFAULT NULL,
KEY `kkk` (`i`)
) ENGINE=MEMORY DEFAULT CHARSET=latin1
# Copy algorithm should work as well.
alter table t1 algorithm=copy, rename key kkk to kkkk;
alter table t2 algorithm=copy, rename key kkk to kkkk;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`i` int(11) DEFAULT NULL,
KEY `kkkk` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
show create table t2;
Table Create Table
t2 CREATE TABLE `t2` (
`i` int(11) DEFAULT NULL,
KEY `kkkk` (`i`)
) ENGINE=MEMORY DEFAULT CHARSET=latin1
# When renaming is combined with other in-place operation
# it still works as expected (i.e. works in-place).
alter table t1 algorithm=inplace, rename key kkkk to k, alter column i set default 100;
alter table t2 algorithm=inplace, rename key kkkk to k, alter column i set default 100;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`i` int(11) DEFAULT 100,
KEY `k` (`i`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
show create table t2;
Table Create Table
t2 CREATE TABLE `t2` (
`i` int(11) DEFAULT 100,
KEY `k` (`i`)
) ENGINE=MEMORY DEFAULT CHARSET=latin1
# Combining with non-inplace operation results in the whole ALTER
# becoming non-inplace.
alter table t1 algorithm=inplace, rename key k to kk, add column j int;
ERROR 0A000: ALGORITHM=INPLACE is not supported for this operation. Try ALGORITHM=COPY
alter table t2 algorithm=inplace, rename key k to kk, add column j int;
ERROR 0A000: ALGORITHM=INPLACE is not supported for this operation. Try ALGORITHM=COPY
drop table t1, t2;
# 3.b) Basic tests for InnoDB. More tests can be found in
# innodb.innodb_rename_index*
create table t1 (i int, key k(i)) engine=innodb;
insert into t1 values (1);
# Basic rename, inplace algorithm should be chosen
alter table t1 algorithm=inplace, rename key k to kk;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`i` int(11) DEFAULT NULL,
KEY `kk` (`i`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
# copy algorithm should work as well.
alter table t1 algorithm=copy, rename key kk to kkk;
affected rows: 1
info: Records: 1 Duplicates: 0 Warnings: 0
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`i` int(11) DEFAULT NULL,
KEY `kkk` (`i`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
drop table t1;
#
# 4) Additional coverage for complex cases in which code
# in ALTER TABLE comparing old and new table version
# got confused.
#
# Once InnoDB starts to support in-place index renaming the result
# of below statements should stay the same. Information about
# indexes returned by SHOW CREATE TABLE (from .FRM) and by
# InnoDB (from InnoDB data-dictionary) should be consistent.
#
create table t1 ( a int, b int, c int, d int,
primary key (a), index i1 (b), index i2 (c) ) engine=innodb;
alter table t1 add index i1 (d), rename index i1 to x;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `x` (`b`),
KEY `i2` (`c`),
KEY `i1` (`d`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
select i.name as k, f.name as c from information_schema.innodb_sys_tables as t,
information_schema.innodb_sys_indexes as i,
information_schema.innodb_sys_fields as f
where t.name='test/t1' and t.table_id = i.table_id and i.index_id = f.index_id
order by k, c;
k c
i1 d
i2 c
PRIMARY a
x b
drop table t1;
create table t1 (a int, b int, c int, d int,
primary key (a), index i1 (b), index i2 (c)) engine=innodb;
alter table t1 add index i1 (d), rename index i1 to i2, drop index i2;
show create table t1;
Table Create Table
t1 CREATE TABLE `t1` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i2` (`b`),
KEY `i1` (`d`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
select i.name as k, f.name as c from information_schema.innodb_sys_tables as t,
information_schema.innodb_sys_indexes as i,
information_schema.innodb_sys_fields as f
where t.name='test/t1' and t.table_id = i.table_id and i.index_id = f.index_id
order by k, c;
k c
i1 d
i2 b
PRIMARY a
drop table t1;
#
# End of 10.5 tests
#
......@@ -2273,6 +2273,186 @@ DROP VIEW v1;
DROP TABLE t3,t1,t2;
SET DEFAULT_STORAGE_ENGINE= @save_default_engine;
--echo #
--echo # MDEV-7318 RENAME INDEX
--echo #
--echo #
--echo # 1) Tests for syntax and semantics of ALTER TABLE RENAME
--echo # KEY/INDEX result.
--echo #
--echo # 1.a) Both RENAME KEY and RENAME INDEX variants should be
--echo # allowed and produce expected results.
create table t1 (pk int primary key, i int, j int, key a(i));
alter table t1 rename key a to b;
show create table t1;
alter table t1 rename index b to c;
show create table t1;
--echo # 1.b) It should be impossible to rename index that doesn't
--echo # exists, dropped or added within the same ALTER TABLE.
--error ER_KEY_DOES_NOT_EXITS
alter table t1 rename key d to e;
show create table t1;
--error ER_KEY_DOES_NOT_EXITS
alter table t1 drop key c, rename key c to d;
show create table t1;
--error ER_KEY_DOES_NOT_EXITS
alter table t1 add key d(j), rename key d to e;
show create table t1;
--echo # 1.c) It should be impossible to rename index to a name
--echo # which is already used by another index, or is used
--echo # by index which is added within the same ALTER TABLE.
alter table t1 add key d(j);
--error ER_DUP_KEYNAME
alter table t1 rename key c to d;
show create table t1;
alter table t1 drop key d;
--error ER_DUP_KEYNAME
alter table t1 add key d(j), rename key c to d;
show create table t1;
--echo # 1.d) It should be possible to rename index to a name
--echo # which belongs to index which is dropped within the
--echo # same ALTER TABLE.
alter table t1 add key d(j);
alter table t1 drop key c, rename key d to c;
show create table t1;
--echo # 1.e) We disallow renaming from/to PRIMARY as it might
--echo # lead to some other key becoming "primary" internally,
--echo # which will be interpreted as dropping/addition of
--echo # primary key.
--error ER_PARSE_ERROR
alter table t1 rename key primary to d;
show create table t1;
--echo # Even using 'funny' syntax.
--error ER_WRONG_NAME_FOR_INDEX
alter table t1 rename key `primary` to d;
show create table t1;
--error ER_PARSE_ERROR
alter table t1 rename key c to primary;
show create table t1;
--error ER_WRONG_NAME_FOR_INDEX
alter table t1 rename key c to `primary`;
show create table t1;
drop table t1;
--echo #
--echo # 2) More complex tests for semantics of ALTER TABLE.
--echo #
--echo # 2.a) Check that standalone RENAME KEY works as expected
--echo # for unique and non-unique indexes.
create table t1 (a int, unique u(a), b int, key k(b));
alter table t1 rename key u to uu;
show create table t1;
alter table t1 rename key k to kk;
show create table t1;
--echo # 2.b) Check how that this clause can be mixed with other
--echo # clauses which don't affect key or its columns.
alter table t1 rename key kk to kkk, add column c int;
show create table t1;
alter table t1 rename key uu to uuu, add key c(c);
show create table t1;
alter table t1 rename key kkk to k, drop key uuu;
show create table t1;
alter table t1 rename key k to kk, rename to t2;
show create table t2;
drop table t2;
--echo #
--echo # 3) Test coverage for handling of RENAME INDEX clause in
--echo # various storage engines and using different ALTER
--echo # algorithm.
--echo #
--echo # 3.a) Test coverage for simple storage engines (MyISAM/Heap).
create table t1 (i int, key k(i)) engine=myisam;
insert into t1 values (1);
create table t2 (i int, key k(i)) engine=memory;
insert into t2 values (1);
--echo # MyISAM and Heap should be able to handle key renaming in-place.
alter table t1 algorithm=inplace, rename key k to kk;
alter table t2 algorithm=inplace, rename key k to kk;
show create table t1;
show create table t2;
--echo # So by default in-place algorithm should be chosen.
--echo # (ALTER TABLE should report 0 rows affected).
--enable_info
alter table t1 rename key kk to kkk;
alter table t2 rename key kk to kkk;
--disable_info
show create table t1;
show create table t2;
--echo # Copy algorithm should work as well.
alter table t1 algorithm=copy, rename key kkk to kkkk;
alter table t2 algorithm=copy, rename key kkk to kkkk;
show create table t1;
show create table t2;
--echo # When renaming is combined with other in-place operation
--echo # it still works as expected (i.e. works in-place).
alter table t1 algorithm=inplace, rename key kkkk to k, alter column i set default 100;
alter table t2 algorithm=inplace, rename key kkkk to k, alter column i set default 100;
show create table t1;
show create table t2;
--echo # Combining with non-inplace operation results in the whole ALTER
--echo # becoming non-inplace.
--error ER_ALTER_OPERATION_NOT_SUPPORTED
alter table t1 algorithm=inplace, rename key k to kk, add column j int;
--error ER_ALTER_OPERATION_NOT_SUPPORTED
alter table t2 algorithm=inplace, rename key k to kk, add column j int;
drop table t1, t2;
--echo # 3.b) Basic tests for InnoDB. More tests can be found in
--echo # innodb.innodb_rename_index*
create table t1 (i int, key k(i)) engine=innodb;
insert into t1 values (1);
--echo # Basic rename, inplace algorithm should be chosen
--enable_info
alter table t1 algorithm=inplace, rename key k to kk;
--disable_info
show create table t1;
--echo # copy algorithm should work as well.
--enable_info
alter table t1 algorithm=copy, rename key kk to kkk;
--disable_info
show create table t1;
drop table t1;
--echo #
--echo # 4) Additional coverage for complex cases in which code
--echo # in ALTER TABLE comparing old and new table version
--echo # got confused.
--echo #
--echo # Once InnoDB starts to support in-place index renaming the result
--echo # of below statements should stay the same. Information about
--echo # indexes returned by SHOW CREATE TABLE (from .FRM) and by
--echo # InnoDB (from InnoDB data-dictionary) should be consistent.
--echo #
create table t1 ( a int, b int, c int, d int,
primary key (a), index i1 (b), index i2 (c) ) engine=innodb;
alter table t1 add index i1 (d), rename index i1 to x;
show create table t1;
select i.name as k, f.name as c from information_schema.innodb_sys_tables as t,
information_schema.innodb_sys_indexes as i,
information_schema.innodb_sys_fields as f
where t.name='test/t1' and t.table_id = i.table_id and i.index_id = f.index_id
order by k, c;
drop table t1;
create table t1 (a int, b int, c int, d int,
primary key (a), index i1 (b), index i2 (c)) engine=innodb;
alter table t1 add index i1 (d), rename index i1 to i2, drop index i2;
show create table t1;
select i.name as k, f.name as c from information_schema.innodb_sys_tables as t,
information_schema.innodb_sys_indexes as i,
information_schema.innodb_sys_fields as f
where t.name='test/t1' and t.table_id = i.table_id and i.index_id = f.index_id
order by k, c;
drop table t1;
--echo #
--echo # End of 10.5 tests
--echo #
......@@ -98,3 +98,12 @@ disconnect con1;
connection default;
UNLOCK TABLES;
DROP TABLE t1;
#
# MDEV-7318 RENAME INDEX
#
CREATE TABLE t (c1 INT, c2 INT, KEY i2 (c2)) ENGINE=INNODB;
SET DEBUG_DBUG= '+d,ib_rename_index_fail1';
ALTER TABLE t RENAME INDEX i2 to x, ALGORITHM=INPLACE;
ERROR 40001: Deadlock found when trying to get lock; try restarting transaction
SET DEBUG_DBUG= '-d,ib_rename_index_fail1';
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
ALTER TABLE t RENAME INDEX i1 TO GEN_CLUST_INDEX;
ERROR 42000: Incorrect index name 'GEN_CLUST_INDEX'
ALTER TABLE t RENAME INDEX i1 TO i1;
ALTER TABLE t RENAME INDEX aa TO aa;
ERROR 42000: Key 'aa' doesn't exist in table 't'
# combination: aaaa
ALTER TABLE t ADD INDEX i4(f), DROP INDEX i4, RENAME INDEX i4 TO i4;
ERROR 42000: Key 'i4' doesn't exist in table 't'
# combination: aabb
ALTER TABLE t ADD INDEX aa(f), DROP INDEX aa, RENAME INDEX i2 TO i2;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX aa, RENAME INDEX bb TO bb;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX bb TO bb;
ERROR 42000: Key 'bb' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i2 TO i2;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i2` (`c`),
KEY `i3` (`d`),
KEY `i4` (`e`),
KEY `i1` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i1 f
test/t i2 c
test/t i3 d
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
# combination: abcc
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX cc TO cc;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX i3 TO i3;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX cc TO cc;
ERROR 42000: Key 'cc' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i3 TO i3;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i1` (`b`),
KEY `i3` (`d`),
KEY `i4` (`e`),
KEY `aa` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t aa f
test/t i1 b
test/t i3 d
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
# combination: abaa
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i1, RENAME INDEX aa TO aa;
ERROR 42000: Key 'aa' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i1 TO i1;
ERROR 42000: Duplicate key name 'i1'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX bb, RENAME INDEX i1 TO i1;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX aa TO aa;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
# combination: baaa
ALTER TABLE t ADD INDEX i2(f), DROP INDEX i1, RENAME INDEX i1 TO i1;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t ADD INDEX bb(f), DROP INDEX i1, RENAME INDEX i1 TO i1;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i2(f), DROP INDEX aa, RENAME INDEX aa TO aa;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX bb(f), DROP INDEX aa, RENAME INDEX aa TO aa;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX aa(f), RENAME INDEX aa TO bb;
ERROR 42000: Key 'aa' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), RENAME INDEX bb TO aa;
ERROR 42000: Key 'bb' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), RENAME INDEX i2 TO aa;
ERROR 42000: Duplicate key name 'aa'
ALTER TABLE t ADD INDEX i1(f), RENAME INDEX i1 TO bb;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `bb` (`b`),
KEY `i2` (`c`),
KEY `i3` (`d`),
KEY `i4` (`e`),
KEY `i1` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t bb b
test/t i1 f
test/t i2 c
test/t i3 d
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
# combination: abba
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i2 TO i1;
ERROR 42000: Key 'i2' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i2 TO aa;
ERROR 42000: Key 'i2' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX bb, RENAME INDEX bb TO i1;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX bb TO aa;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
# combination: cabc
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX i2 TO i3;
ERROR 42000: Duplicate key name 'i3'
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX i2 TO i3;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX bb TO i3;
ERROR 42000: Key 'bb' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX bb TO i3;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX i2 TO cc;
ERROR 42000: Duplicate key name 'cc'
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX i2 TO cc;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX bb TO cc;
ERROR 42000: Key 'bb' doesn't exist in table 't'
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX bb TO cc;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t DROP INDEX i1, RENAME INDEX i1 TO bb;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t DROP INDEX aa, RENAME INDEX i2 TO aa;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t DROP INDEX aa, RENAME INDEX aa TO i2;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t DROP INDEX i1, RENAME INDEX i4 TO i1;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i2` (`c`),
KEY `i3` (`d`),
KEY `i1` (`e`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i1 e
test/t i2 c
test/t i3 d
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
# combination: accb
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX i3 TO i2;
ERROR 42000: Key 'i3' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX i3 TO bb;
ERROR 42000: Key 'i3' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX cc TO i2;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX cc TO bb;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX cc TO i2;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX cc TO bb;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
# combination: aaab
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i1 TO i2;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i1 TO bb;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i1 TO i2;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX aa, RENAME INDEX aa TO bb;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
# combination: abcd
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX cc TO i4;
ERROR 42000: Key 'cc' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX cc TO dd;
ERROR 42000: Key 'cc' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX cc TO i4;
ERROR 42000: Key 'cc' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX cc TO dd;
ERROR 42000: Key 'cc' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i3 TO i4;
ERROR 42000: Duplicate key name 'i4'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i3 TO dd;
ERROR 42000: Duplicate key name 'i1'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i3 TO i4;
ERROR 42000: Duplicate key name 'i4'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i3 TO dd;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i1` (`b`),
KEY `dd` (`d`),
KEY `i4` (`e`),
KEY `aa` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t aa f
test/t dd d
test/t i1 b
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
# combination: abab
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i1 TO i2;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i2` (`b`),
KEY `i3` (`d`),
KEY `i4` (`e`),
KEY `i1` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i1 f
test/t i2 b
test/t i3 d
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
ALTER TABLE t ADD INDEX i1(f), DROP INDEX bb, RENAME INDEX i1 TO bb;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX aa TO i2;
ERROR 42000: Key 'aa' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX aa TO bb;
ERROR 42000: Can't DROP INDEX `bb`; check that it exists
# combination: acbc
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX i2 TO cc;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX i2 TO cc;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX bb TO cc;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX bb TO cc;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX bb TO i3;
ERROR 42000: Key 'bb' doesn't exist in table 't'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i3, RENAME INDEX bb TO i3;
ERROR 42000: Key 'bb' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX i2 TO i3;
ERROR 42000: Duplicate key name 'i1'
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i3, RENAME INDEX i2 TO i3;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i1` (`b`),
KEY `i3` (`c`),
KEY `i4` (`e`),
KEY `aa` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t aa f
test/t i1 b
test/t i3 c
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
# combination: cacb
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX cc TO i2;
ERROR 42000: Key 'cc' doesn't exist in table 't'
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX cc TO i2;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX cc TO bb;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX cc TO bb;
ERROR 42000: Key 'cc' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX i3 TO i2;
ERROR 42000: Duplicate key name 'i2'
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX i3 TO i2;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX i3 TO bb;
ERROR 42000: Can't DROP INDEX `aa`; check that it exists
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX i3 TO bb;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i2` (`c`),
KEY `bb` (`d`),
KEY `i4` (`e`),
KEY `i3` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t bb d
test/t i2 c
test/t i3 f
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
# combination: ccab
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX i1 TO i2;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX i1 TO bb;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX aa TO i2;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX aa TO bb;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX i3(f), DROP INDEX cc, RENAME INDEX aa TO i2;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX i3(f), DROP INDEX cc, RENAME INDEX aa TO bb;
ERROR 42000: Can't DROP INDEX `cc`; check that it exists
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i3, RENAME INDEX i1 TO i2;
ERROR 42000: Duplicate key name 'i2'
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i3, RENAME INDEX i1 TO bb;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `bb` (`b`),
KEY `i2` (`c`),
KEY `i4` (`e`),
KEY `i3` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t bb b
test/t i2 c
test/t i3 f
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
ALTER TABLE t RENAME INDEX i1 TO x;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `x` (`b`),
KEY `i2` (`c`),
KEY `i3` (`d`),
KEY `i4` (`e`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i2 c
test/t i3 d
test/t i4 e
test/t PRIMARY a
test/t x b
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
ALTER TABLE t RENAME INDEX i1 TO i2;
ERROR 42000: Duplicate key name 'i2'
ALTER TABLE t RENAME INDEX foo TO i1;
ERROR 42000: Key 'foo' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i9 (f), RENAME INDEX i1 TO i8;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i8` (`b`),
KEY `i2` (`c`),
KEY `i3` (`d`),
KEY `i4` (`e`),
KEY `i9` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i2 c
test/t i3 d
test/t i4 e
test/t i8 b
test/t i9 f
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
ALTER TABLE t ADD INDEX i1 (f), RENAME INDEX i1 TO i9;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i9` (`b`),
KEY `i2` (`c`),
KEY `i3` (`d`),
KEY `i4` (`e`),
KEY `i1` (`f`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i1 f
test/t i2 c
test/t i3 d
test/t i4 e
test/t i9 b
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
INSERT INTO t SET a = 1;
ALTER TABLE t ADD INDEX foo (f), RENAME INDEX i1 TO foo;
ERROR 42000: Duplicate key name 'foo'
ALTER TABLE t ADD INDEX i1 (f), RENAME INDEX i1 TO foo, DROP INDEX i1;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t ADD INDEX i1 (f), RENAME INDEX i1 TO foo, DROP INDEX foo;
ERROR 42000: Can't DROP INDEX `foo`; check that it exists
ALTER TABLE t ADD INDEX foo (f), RENAME INDEX foo TO bar, DROP INDEX foo;
ERROR 42000: Can't DROP INDEX `foo`; check that it exists
ALTER TABLE t RENAME INDEX i1 TO x, RENAME INDEX i2 TO x;
ERROR 42000: Duplicate key name 'x'
ALTER TABLE t RENAME INDEX i1 TO x, RENAME INDEX i1 TO y;
ERROR 42000: Key 'i1' doesn't exist in table 't'
ALTER TABLE t RENAME INDEX i1 TO x, RENAME INDEX i1 TO x;
ERROR 42000: Key 'i1' doesn't exist in table 't'
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`a` int(11) NOT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
`d` int(11) DEFAULT NULL,
`e` int(11) DEFAULT NULL,
`f` int(11) DEFAULT NULL,
PRIMARY KEY (`a`),
KEY `i1` (`b`),
KEY `i2` (`c`),
KEY `i3` (`d`),
KEY `i4` (`e`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i1 b
test/t i2 c
test/t i3 d
test/t i4 e
test/t PRIMARY a
DROP TABLE t;
CREATE TABLE t (
c1 INT NOT NULL,
c2 INT NOT NULL,
c3 INT,
c4 INT,
PRIMARY KEY (c1),
INDEX i1 (c3),
INDEX i2 (c4)
) ENGINE=INNODB;
INSERT INTO t SET c1=1, c2=2;
ALTER TABLE t DROP PRIMARY KEY, ADD PRIMARY KEY (c2), RENAME INDEX i1 TO x;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`c1` int(11) NOT NULL,
`c2` int(11) NOT NULL,
`c3` int(11) DEFAULT NULL,
`c4` int(11) DEFAULT NULL,
PRIMARY KEY (`c2`),
KEY `x` (`c3`),
KEY `i2` (`c4`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i2 c4
test/t PRIMARY c2
test/t x c3
ALTER TABLE t RENAME INDEX i2 TO y, ROW_FORMAT=REDUNDANT;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`c1` int(11) NOT NULL,
`c2` int(11) NOT NULL,
`c3` int(11) DEFAULT NULL,
`c4` int(11) DEFAULT NULL,
PRIMARY KEY (`c2`),
KEY `x` (`c3`),
KEY `y` (`c4`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=REDUNDANT
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t PRIMARY c2
test/t x c3
test/t y c4
DROP TABLE t;
CREATE TABLE t (
c1 INT NOT NULL,
c2 INT,
c3 INT,
INDEX i1 (c2),
INDEX i2 (c3)
) ENGINE=INNODB;
INSERT INTO t SET c1=1;
ALTER TABLE t ADD PRIMARY KEY (c1), RENAME INDEX i1 TO x;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`c1` int(11) NOT NULL,
`c2` int(11) DEFAULT NULL,
`c3` int(11) DEFAULT NULL,
PRIMARY KEY (`c1`),
KEY `x` (`c2`),
KEY `i2` (`c3`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
table_name index_name column_name
test/t i2 c3
test/t PRIMARY c1
test/t x c2
DROP TABLE t;
CREATE TABLE t (a INT, INDEX iiiii (a)) ENGINE=INNODB;
INSERT INTO t SET a=NULL;
ALTER TABLE t RENAME INDEX iiiii TO i;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
ALTER TABLE t RENAME INDEX i TO iiiii;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
ALTER TABLE t RENAME INDEX iiiii TO i;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
ALTER TABLE t RENAME INDEX i TO iiiii;
affected rows: 0
info: Records: 0 Duplicates: 0 Warnings: 0
DROP TABLE t;
......@@ -132,3 +132,15 @@ DROP TABLE t1;
# Wait till all disconnects are completed
--source include/wait_until_count_sessions.inc
--echo #
--echo # MDEV-7318 RENAME INDEX
--echo #
CREATE TABLE t (c1 INT, c2 INT, KEY i2 (c2)) ENGINE=INNODB;
SET DEBUG_DBUG= '+d,ib_rename_index_fail1';
-- error ER_LOCK_DEADLOCK
ALTER TABLE t RENAME INDEX i2 to x, ALGORITHM=INPLACE;
SET DEBUG_DBUG= '-d,ib_rename_index_fail1';
DROP TABLE t;
--source include/have_innodb.inc
#
# Test "ALTER TABLE ... RENAME INDEX" in InnoDB
#
let create =
CREATE TABLE t (
a INT,
b INT,
c INT,
d INT,
e INT,
f INT,
PRIMARY KEY (a),
INDEX i1 (b),
INDEX i2 (c),
INDEX i3 (d),
INDEX i4 (e)
) ENGINE=INNODB;
let insert = INSERT INTO t SET a = 1;
let show_table =
SHOW CREATE TABLE t;
let show_sys =
SELECT
t.name AS table_name,
i.name AS index_name,
f.name AS column_name
FROM
information_schema.innodb_sys_tables t,
information_schema.innodb_sys_indexes i,
information_schema.innodb_sys_fields f
WHERE
t.name LIKE '%/t' AND
t.table_id = i.table_id AND
i.index_id = f.index_id
ORDER BY 1, 2, 3;
-- eval $create
# Add a row, so that affected rows would be nonzero for ALGORITHM=COPY.
# ALGORITHM=INPLACE will report 0 affected row in the result file.
# We will have enable_info/disable_info around every successful ALTER
# to enable the affected rows: output in the result file.
-- eval $insert
-- error ER_WRONG_NAME_FOR_INDEX
ALTER TABLE t RENAME INDEX i1 TO GEN_CLUST_INDEX;
# Test all combinations of ADD w, DROP x, RENAME y TO z.
#
# Use the following names for wxyz (with 1 to 4 of wxyz being the same):
# aaaa abcd aabb abab abba abcc acbc accb cacb cabc ccab aaab aaba abaa baaa
#
# Some cases should trivially succeed or fail. Test them in isolation:
# no-op: y=z (RENAME y TO y)
# rules out the combinations ..\(.\)\1
# a.k.a. aaaa aabb abcc abaa baaa
# We use the index names i1 to i4 for existing indexes abcd.
# Non-existing index names will be aa,bb,cc,dd.
# Index creation on non-existing columns will not be tested.
ALTER TABLE t RENAME INDEX i1 TO i1;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t RENAME INDEX aa TO aa;
-- echo # combination: aaaa
# drop/add existing, null rename and drop the same
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i4(f), DROP INDEX i4, RENAME INDEX i4 TO i4;
-- echo # combination: aabb
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX aa, RENAME INDEX i2 TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX aa, RENAME INDEX bb TO bb;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX bb TO bb;
-- enable_info
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i2 TO i2;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- echo # combination: abcc
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX cc TO cc;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX i3 TO i3;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX cc TO cc;
# rename existing (succeeds)
-- enable_info
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i3 TO i3;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- echo # combination: abaa
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i1, RENAME INDEX aa TO aa;
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i1 TO i1;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1(f), DROP INDEX bb, RENAME INDEX i1 TO i1;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX aa TO aa;
-- echo # combination: baaa
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i2(f), DROP INDEX i1, RENAME INDEX i1 TO i1;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX bb(f), DROP INDEX i1, RENAME INDEX i1 TO i1;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i2(f), DROP INDEX aa, RENAME INDEX aa TO aa;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX bb(f), DROP INDEX aa, RENAME INDEX aa TO aa;
# refuse: w=z (ADD w, RENAME y TO w)
# rules out the combinations \(.\)..\1
# a.k.a. aaaa abba cabc aaba abaa
# the case w=y (ADD w, RENAME w to z) may succeed, as seen below
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), RENAME INDEX aa TO bb;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), RENAME INDEX bb TO aa;
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX aa(f), RENAME INDEX i2 TO aa;
# rename existing, add one with the same name
-- enable_info
ALTER TABLE t ADD INDEX i1(f), RENAME INDEX i1 TO bb;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- echo # combination: abba
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i2 TO i1;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i2 TO aa;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1(f), DROP INDEX bb, RENAME INDEX bb TO i1;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX bb TO aa;
-- echo # combination: cabc
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX i2 TO i3;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX i2 TO i3;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX bb TO i3;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX bb TO i3;
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX i2 TO cc;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX i2 TO cc;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX bb TO cc;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX bb TO cc;
# refuse: x=y (DROP x, RENAME x TO z)
# rules out the combinations .\(.\)\1.
# a.k.a. aaaa abba accb aaab baaa
# rename and drop the same
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t DROP INDEX i1, RENAME INDEX i1 TO bb;
# drop non-existing
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t DROP INDEX aa, RENAME INDEX i2 TO aa;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t DROP INDEX aa, RENAME INDEX aa TO i2;
# this one will succeed (drop, replace with an existing one)
-- enable_info
ALTER TABLE t DROP INDEX i1, RENAME INDEX i4 TO i1;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- echo # combination: accb
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX i3 TO i2;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX i3 TO bb;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX cc TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX cc TO bb;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX cc TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX cc TO bb;
-- echo # combination: aaab
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i1 TO i2;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i1 TO bb;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i1, RENAME INDEX i1 TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX aa, RENAME INDEX aa TO bb;
# Remaining combinations: abcd abab acbc cacb ccab
-- echo # combination: abcd
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX cc TO i4;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX cc TO dd;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX cc TO i4;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX cc TO dd;
# add existing, rename to existing
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i3 TO i4;
# add existing
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i3 TO dd;
# rename to existing
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i3 TO i4;
-- enable_info
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX i3 TO dd;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- echo # combination: abab
-- enable_info
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i2, RENAME INDEX i1 TO i2;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1(f), DROP INDEX bb, RENAME INDEX i1 TO bb;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i2, RENAME INDEX aa TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX bb, RENAME INDEX aa TO bb;
-- echo # combination: acbc
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX i2 TO cc;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX i2 TO cc;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1(f), DROP INDEX cc, RENAME INDEX bb TO cc;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX aa(f), DROP INDEX cc, RENAME INDEX bb TO cc;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX bb TO i3;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i3, RENAME INDEX bb TO i3;
# add existing
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX i1(f), DROP INDEX i3, RENAME INDEX i2 TO i3;
-- enable_info
ALTER TABLE t ADD INDEX aa(f), DROP INDEX i3, RENAME INDEX i2 TO i3;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- echo # combination: cacb
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX cc TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX cc TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX aa, RENAME INDEX cc TO bb;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX cc(f), DROP INDEX i1, RENAME INDEX cc TO bb;
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX i3 TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX i3 TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i3(f), DROP INDEX aa, RENAME INDEX i3 TO bb;
-- enable_info
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i1, RENAME INDEX i3 TO bb;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- echo # combination: ccab
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX i1 TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX i1 TO bb;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX aa TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX cc(f), DROP INDEX cc, RENAME INDEX aa TO bb;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i3(f), DROP INDEX cc, RENAME INDEX aa TO i2;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i3(f), DROP INDEX cc, RENAME INDEX aa TO bb;
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i3, RENAME INDEX i1 TO i2;
-- enable_info
ALTER TABLE t ADD INDEX i3(f), DROP INDEX i3, RENAME INDEX i1 TO bb;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
# A simple successful ALTER
-- enable_info
ALTER TABLE t RENAME INDEX i1 TO x;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- error ER_DUP_KEYNAME
ALTER TABLE t RENAME INDEX i1 TO i2;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t RENAME INDEX foo TO i1;
# Test ADD INDEX, RENAME INDEX
-- enable_info
ALTER TABLE t ADD INDEX i9 (f), RENAME INDEX i1 TO i8;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- enable_info
ALTER TABLE t ADD INDEX i1 (f), RENAME INDEX i1 TO i9;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
-- eval $create
-- eval $insert
-- error ER_DUP_KEYNAME
ALTER TABLE t ADD INDEX foo (f), RENAME INDEX i1 TO foo;
# Test ADD INDEX, RENAME INDEX, DROP INDEX
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t ADD INDEX i1 (f), RENAME INDEX i1 TO foo, DROP INDEX i1;
-- error ER_CANT_DROP_FIELD_OR_KEY
ALTER TABLE t ADD INDEX i1 (f), RENAME INDEX i1 TO foo, DROP INDEX foo;
-- error ER_CANT_DROP_FIELD_OR_KEY
# "ALTER TABLE t ADD INDEX foo (d), DROP INDEX foo;" alone fails with the
# same error code, but we have that test here anyway
ALTER TABLE t ADD INDEX foo (f), RENAME INDEX foo TO bar, DROP INDEX foo;
# Test RENAME INDEX, RENAME INDEX
-- error ER_DUP_KEYNAME
ALTER TABLE t RENAME INDEX i1 TO x, RENAME INDEX i2 TO x;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t RENAME INDEX i1 TO x, RENAME INDEX i1 TO y;
-- error ER_KEY_DOES_NOT_EXITS
ALTER TABLE t RENAME INDEX i1 TO x, RENAME INDEX i1 TO x;
# show that the table did not change after all the erroneous ALTERs
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
# now test the rebuild case (new clustered index)
CREATE TABLE t (
c1 INT NOT NULL,
c2 INT NOT NULL,
c3 INT,
c4 INT,
PRIMARY KEY (c1),
INDEX i1 (c3),
INDEX i2 (c4)
) ENGINE=INNODB;
INSERT INTO t SET c1=1, c2=2;
-- enable_info
ALTER TABLE t DROP PRIMARY KEY, ADD PRIMARY KEY (c2), RENAME INDEX i1 TO x;
-- disable_info
-- eval $show_table
-- eval $show_sys
-- enable_info
ALTER TABLE t RENAME INDEX i2 TO y, ROW_FORMAT=REDUNDANT;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
# a case where the PK does not exist prior to the ALTER TABLE command
CREATE TABLE t (
c1 INT NOT NULL,
c2 INT,
c3 INT,
INDEX i1 (c2),
INDEX i2 (c3)
) ENGINE=INNODB;
INSERT INTO t SET c1=1;
-- enable_info
ALTER TABLE t ADD PRIMARY KEY (c1), RENAME INDEX i1 TO x;
-- disable_info
-- eval $show_table
-- eval $show_sys
DROP TABLE t;
# Test repeated RENAMEs with alternating names
CREATE TABLE t (a INT, INDEX iiiii (a)) ENGINE=INNODB;
INSERT INTO t SET a=NULL;
-- enable_info
ALTER TABLE t RENAME INDEX iiiii TO i;
ALTER TABLE t RENAME INDEX i TO iiiii;
ALTER TABLE t RENAME INDEX iiiii TO i;
ALTER TABLE t RENAME INDEX i TO iiiii;
-- disable_info
DROP TABLE t;
# Below is a shell script to generate the full set of ALTER TABLE
# DROP/ADD/RENAME combinations. The generated .sql file is 3.3MB and
# executes in about 7 minutes.
#
##!/bin/sh
#
#create="
#CREATE TABLE t (
# a INT,
# b INT,
# c INT,
# d INT,
# PRIMARY KEY (a),
# INDEX i1 (b),
# INDEX i2 (c)
#) ENGINE=INNODB;
#"
#
#echo "DROP TABLE IF EXISTS t;"
#for r in "" ", DROP PRIMARY KEY, ADD PRIMARY KEY (a)" ", ROW_FORMAT=REDUNDANT" ; do
# for i1 in i1 i1noexist; do
# for i2 in i2 i2noexist; do
# for i3 in i3 i3noexist; do
# for i4 in i4 i4noexist; do
# for a in $i1 $i2 $i3 $i4; do
# for b in $i1 $i2 $i3 $i4; do
# for c in $i1 $i2 $i3 $i4; do
# for d in $i1 $i2 $i3 $i4; do
# echo "$create"
# echo "ALTER TABLE t ADD INDEX $a (d), RENAME INDEX $b TO $c, DROP INDEX $d $r;"
# echo "DROP TABLE t;"
# done
# done
# done
# done
# done
# done
# done
# done
#done
......@@ -4585,7 +4585,8 @@ handler::check_if_supported_inplace_alter(TABLE *altered_table,
ALTER_DROP_CHECK_CONSTRAINT |
ALTER_PARTITIONED |
ALTER_VIRTUAL_GCOL_EXPR |
ALTER_RENAME;
ALTER_RENAME |
ALTER_RENAME_INDEX;
/* Is there at least one operation that requires copy algorithm? */
if (ha_alter_info->handler_flags & ~inplace_offline_operations)
......
......@@ -25,6 +25,7 @@ Alter_info::Alter_info(const Alter_info &rhs, MEM_ROOT *mem_root)
:drop_list(rhs.drop_list, mem_root),
alter_list(rhs.alter_list, mem_root),
key_list(rhs.key_list, mem_root),
alter_rename_key_list(rhs.alter_rename_key_list, mem_root),
create_list(rhs.create_list, mem_root),
check_constraint_list(rhs.check_constraint_list, mem_root),
flags(rhs.flags), partition_flags(rhs.partition_flags),
......@@ -46,6 +47,7 @@ Alter_info::Alter_info(const Alter_info &rhs, MEM_ROOT *mem_root)
list_copy_and_replace_each_value(drop_list, mem_root);
list_copy_and_replace_each_value(alter_list, mem_root);
list_copy_and_replace_each_value(key_list, mem_root);
list_copy_and_replace_each_value(alter_rename_key_list, mem_root);
list_copy_and_replace_each_value(create_list, mem_root);
/* partition_names are not deeply copied currently */
}
......
......@@ -19,6 +19,7 @@
class Alter_drop;
class Alter_column;
class Alter_rename_key;
class Key;
/**
......@@ -87,6 +88,8 @@ class Alter_info
List<Alter_column> alter_list;
// List of keys, used by both CREATE and ALTER TABLE.
List<Key> key_list;
// List of keys to be renamed.
List<Alter_rename_key> alter_rename_key_list;
// List of columns, used by both CREATE and ALTER TABLE.
List<Create_field> create_list;
......@@ -123,6 +126,7 @@ class Alter_info
drop_list.empty();
alter_list.empty();
key_list.empty();
alter_rename_key_list.empty();
create_list.empty();
check_constraint_list.empty();
flags= 0;
......
......@@ -355,6 +355,21 @@ class Alter_column :public Sql_alloc {
};
class Alter_rename_key : public Sql_alloc
{
public:
LEX_CSTRING old_name;
LEX_CSTRING new_name;
Alter_rename_key(LEX_CSTRING old_name_arg, LEX_CSTRING new_name_arg)
: old_name(old_name_arg), new_name(new_name_arg) {}
Alter_rename_key *clone(MEM_ROOT *mem_root) const
{ return new (mem_root) Alter_rename_key(*this); }
};
class Key :public Sql_alloc, public DDL_options {
public:
enum Keytype { PRIMARY, UNIQUE, MULTIPLE, FULLTEXT, SPATIAL, FOREIGN_KEY};
......
......@@ -6601,7 +6601,7 @@ static int compare_uint(const uint *s, const uint *t)
enum class Compare_keys : uint32_t
{
Equal,
Equal= 0,
EqualButKeyPartLength,
EqualButComment,
NotEqual
......@@ -7998,6 +7998,7 @@ mysql_prepare_alter_table(THD *thd, TABLE *table,
List<Create_field> new_create_list;
/* New key definitions are added here */
List<Key> new_key_list;
List<Alter_rename_key> rename_key_list(alter_info->alter_rename_key_list);
List_iterator<Alter_drop> drop_it(alter_info->drop_list);
List_iterator<Create_field> def_it(alter_info->create_list);
List_iterator<Alter_column> alter_it(alter_info->alter_list);
......@@ -8446,6 +8447,39 @@ mysql_prepare_alter_table(THD *thd, TABLE *table,
continue;
}
/* If this index is to stay in the table check if it has to be renamed. */
List_iterator<Alter_rename_key> rename_key_it(rename_key_list);
Alter_rename_key *rename_key;
while ((rename_key= rename_key_it++))
{
if (!my_strcasecmp(system_charset_info, key_name, rename_key->old_name.str))
{
if (!my_strcasecmp(system_charset_info, key_name, primary_key_name))
{
my_error(ER_WRONG_NAME_FOR_INDEX, MYF(0), rename_key->old_name.str);
goto err;
}
else if (!my_strcasecmp(system_charset_info, rename_key->new_name.str,
primary_key_name))
{
my_error(ER_WRONG_NAME_FOR_INDEX, MYF(0), rename_key->new_name.str);
goto err;
}
key_name= rename_key->new_name.str;
rename_key_it.remove();
/*
If the user has explicitly renamed the key, we should no longer
treat it as generated. Otherwise this key might be automatically
dropped by mysql_prepare_create_table() and this will confuse
code in fill_alter_inplace_info().
*/
key_info->flags&= ~HA_GENERATED_KEY;
break;
}
}
if (key_info->algorithm == HA_KEY_ALG_LONG_HASH)
{
setup_keyinfo_hash(key_info);
......@@ -8772,6 +8806,13 @@ mysql_prepare_alter_table(THD *thd, TABLE *table,
}
}
if (rename_key_list.elements)
{
my_error(ER_KEY_DOES_NOT_EXITS, MYF(0), rename_key_list.head()->old_name.str,
table->s->table_name.str);
goto err;
}
if (!create_info->comment.str)
{
create_info->comment.str= table->s->comment.str;
......
......@@ -7732,6 +7732,16 @@ alter_list_item:
if (unlikely(Lex->add_alter_list($3, $5)))
MYSQL_YYABORT;
}
| RENAME key_or_index field_ident TO_SYM field_ident
{
LEX *lex=Lex;
Alter_rename_key *ak= new (thd->mem_root)
Alter_rename_key($3, $5);
if (ak == NULL)
MYSQL_YYABORT;
lex->alter_info.alter_rename_key_list.push_back(ak);
lex->alter_info.flags|= ALTER_RENAME_INDEX;
}
| CONVERT_SYM TO_SYM charset charset_name_or_default opt_collate
{
if (!$4)
......
......@@ -3330,6 +3330,14 @@ innobase_check_index_keys(
}
}
for (const Alter_inplace_info::Rename_key_pair& pair :
info->rename_keys) {
if (0 == strcmp(key.name.str,
pair.old_key->name.str)) {
goto name_ok;
}
}
my_error(ER_WRONG_NAME_FOR_INDEX, MYF(0),
key.name.str);
return(ER_WRONG_NAME_FOR_INDEX);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment