1
0
mirror of https://github.com/MariaDB/server.git synced 2025-12-07 17:42:39 +03:00

MDEV-13838: Wrong result after altering a partitioned table

Reverted incorrect changes done on MDEV-7367 and MDEV-9469. Fixes properly
also related bugs:

MDEV-13668: InnoDB unnecessarily rebuilds table when renaming a column and adding index
MDEV-9469: 'Incorrect key file' on ALTER TABLE
MDEV-9548: Alter table (renaming and adding index) fails with "Incorrect key file for table"
MDEV-10535: ALTER TABLE causes standalone/wsrep cluster crash
MDEV-13640: ALTER TABLE CHANGE and ADD INDEX on auto_increment column fails with "Incorrect key file for table..."

Root cause for all these bugs is the fact that MariaDB .frm file
can contain virtual columns but InnoDB dictionary does not and
previous fixes were incorrect or unnecessarily forced table
rebuilt. In index creation key_part->fieldnr can be bigger than
number of columns in InnoDB data dictionary. We need to skip not
stored fields when calculating correct column number for InnoDB
data dictionary.

dict_table_get_col_name_for_mysql
        Remove

innobase_match_index_columns
        Revert incorrect change done on MDEV-7367

innobase_need_rebuild
        Remove unnecessary rebuild force when column is renamed.

innobase_create_index_field_def
        Calculate InnoDB column number correctly and remove
        unnecessary column name set.

innobase_create_index_def, innobase_create_key_defs
        Remove unneeded fields parameter. Revert unneeded memset.

prepare_inplace_alter_table_dict
        Remove unneeded col_names parameter

index_field_t
        Remove unneeded col_name member.

row_merge_create_index
        Remove unneeded col_names parameter and resolution.

Effected tests:
         innodb-alter-table : Add test case for MDEV-13668
         innodb-alter : Remove MDEV-13668, MDEV-9469 FIXMEs
                        and restore original tests
         innodb-wl5980-alter : Remove MDEV-13668,  MDEV-9469 FIXMEs
                        and restore original tests
This commit is contained in:
Jan Lindström
2017-10-10 10:19:10 +03:00
parent 2db5e4d1f9
commit fc9ff69578
18 changed files with 178 additions and 346 deletions

View File

@@ -185,3 +185,44 @@ ticket CREATE TABLE `ticket` (
KEY `org_id` (`org_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1
DROP TABLE ticket;
CREATE TABLE t (
id bigint(20) unsigned NOT NULL auto_increment,
d date NOT NULL,
a bigint(20) unsigned NOT NULL,
b smallint(5) unsigned DEFAULT NULL,
PRIMARY KEY (id,d)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_general_cs STATS_SAMPLE_PAGES=2
PARTITION BY RANGE COLUMNS(d)
(
PARTITION p20170914 VALUES LESS THAN ('2017-09-15') ENGINE = InnoDB,
PARTITION p99991231 VALUES LESS THAN (MAXVALUE) ENGINE = InnoDB);
insert into t(d,a,b) values ('2017-09-15',rand()*10000,rand()*10);
insert into t(d,a,b) values ('2017-09-15',rand()*10000,rand()*10);
replace into t(d,a,b) select '2017-09-15',rand()*10000,rand()*10 from t t1, t t2, t t3, t t4;
select count(*) from t where d ='2017-09-15';
count(*)
18
ALTER TABLE t CHANGE b c smallint(5) unsigned , ADD KEY idx_d_a (d, a);
SHOW CREATE TABLE t;
Table Create Table
t CREATE TABLE `t` (
`id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,
`d` date NOT NULL,
`a` bigint(20) unsigned NOT NULL,
`c` smallint(5) unsigned DEFAULT NULL,
PRIMARY KEY (`id`,`d`),
KEY `idx_d_a` (`d`,`a`)
) ENGINE=InnoDB AUTO_INCREMENT=19 DEFAULT CHARSET=latin1 COLLATE=latin1_general_cs STATS_SAMPLE_PAGES=2
/*!50500 PARTITION BY RANGE COLUMNS(d)
(PARTITION p20170914 VALUES LESS THAN ('2017-09-15') ENGINE = InnoDB,
PARTITION p99991231 VALUES LESS THAN (MAXVALUE) ENGINE = InnoDB) */
analyze table t;
Table Op Msg_type Msg_text
test.t analyze status OK
select count(*) from t where d ='2017-09-15';
count(*)
18
select count(*) from t force index(primary) where d ='2017-09-15';
count(*)
18
DROP TABLE t;

View File

@@ -540,9 +540,6 @@ ERROR 42000: Key column 'c2' doesn't exist in table
ALTER TABLE t1n ADD INDEX(c2), CHANGE c2 c4 INT, ALGORITHM=COPY;
ERROR 42000: Key column 'c2' doesn't exist in table
ALTER TABLE t1n ADD INDEX(c4), CHANGE c2 c4 INT, ALGORITHM=INPLACE;
ERROR 0A000: ALGORITHM=INPLACE is not supported. Reason: InnoDB presently supports one FULLTEXT index creation at a time. Try ALGORITHM=COPY.
ALTER TABLE t1n CHANGE c2 c4 INT, LOCK=NONE;
ALTER TABLE t1n ADD INDEX(c4), LOCK=NONE;
SHOW CREATE TABLE t1n;
Table Create Table
t1n CREATE TABLE `t1n` (
@@ -559,9 +556,6 @@ ALTER TABLE t1n DROP INDEX c4;
ALTER TABLE t1n CHANGE c4 c1 INT, ADD INDEX(c1), ALGORITHM=INPLACE;
ERROR 42S21: Duplicate column name 'c1'
ALTER TABLE t1n CHANGE c4 c11 INT, ADD INDEX(c11), ALGORITHM=INPLACE;
ERROR 0A000: ALGORITHM=INPLACE is not supported. Reason: InnoDB presently supports one FULLTEXT index creation at a time. Try ALGORITHM=COPY.
ALTER TABLE t1n CHANGE c4 c11 INT, LOCK=NONE;
ALTER TABLE t1n ADD INDEX(c11), LOCK=NONE;
SHOW CREATE TABLE t1n;
Table Create Table
t1n CREATE TABLE `t1n` (
@@ -640,10 +634,11 @@ CHANGE foo_id FTS_DOC_ID BIGINT UNSIGNED NOT NULL;
ALTER TABLE t1o DROP INDEX ct, DROP INDEX FTS_DOC_ID_INDEX,
CHANGE FTS_DOC_ID foo_id BIGINT UNSIGNED NOT NULL;
ALTER TABLE t1o ADD UNIQUE INDEX FTS_DOC_ID_INDEX(foo_id);
call mtr.add_suppression("Error: no matching column for .FTS_DOC_ID. in index .ct.--temporary-- of table .test...t1o");
ALTER TABLE t1o CHANGE foo_id FTS_DOC_ID BIGINT UNSIGNED NOT NULL,
ADD FULLTEXT INDEX(ct);
ERROR HY000: Incorrect key file for table 't1o'; try to repair it
ALTER TABLE t1o CHANGE FTS_DOC_ID foo_id BIGINT UNSIGNED NOT NULL,
ALGORITHM=INPLACE;
ERROR 0A000: ALGORITHM=INPLACE is not supported. Reason: Cannot drop or rename FTS_DOC_ID. Try ALGORITHM=COPY.
DROP TABLE sys_indexes;
CREATE TABLE sys_indexes SELECT i.* FROM INFORMATION_SCHEMA.INNODB_SYS_INDEXES i
INNER JOIN sys_tables st ON i.TABLE_ID=st.TABLE_ID;
@@ -651,9 +646,16 @@ SELECT i.NAME,i.POS,i.MTYPE,i.PRTYPE,i.LEN
FROM INFORMATION_SCHEMA.INNODB_SYS_COLUMNS i
INNER JOIN sys_tables st ON i.TABLE_ID=st.TABLE_ID;
NAME POS MTYPE PRTYPE LEN
FTS_DOC_ID 0 6 1800 8
c2 1 6 1027 4
ct 2 5 524540 10
cu 3 5 524540 10
SELECT si.NAME,i.POS,i.NAME FROM INFORMATION_SCHEMA.INNODB_SYS_FIELDS i
INNER JOIN sys_indexes si ON i.INDEX_ID=si.INDEX_ID;
NAME POS NAME
PRIMARY 0 FTS_DOC_ID
FTS_DOC_ID_INDEX 0 FTS_DOC_ID
ct 0 ct
SELECT i.* FROM INFORMATION_SCHEMA.INNODB_SYS_FOREIGN_COLS i
INNER JOIN sys_foreign sf ON i.ID = sf.ID;
ID FOR_COL_NAME REF_COL_NAME POS

View File

@@ -1010,9 +1010,6 @@ ERROR 42000: Key column 'c2' doesn't exist in table
ALTER TABLE t1n ADD INDEX(c2), CHANGE c2 c4 INT, ALGORITHM=COPY;
ERROR 42000: Key column 'c2' doesn't exist in table
ALTER TABLE t1n ADD INDEX(c4), CHANGE c2 c4 INT, ALGORITHM=INPLACE;
ERROR 0A000: ALGORITHM=INPLACE is not supported. Reason: InnoDB presently supports one FULLTEXT index creation at a time. Try ALGORITHM=COPY.
ALTER TABLE t1n CHANGE c2 c4 INT, LOCK=NONE;
ALTER TABLE t1n ADD INDEX(c4), LOCK=NONE;
### files in MYSQL_DATA_DIR/test
FTS_AUX_INDEX_1.ibd
FTS_AUX_INDEX_2.ibd
@@ -1113,9 +1110,6 @@ tt.ibd
ALTER TABLE t1n CHANGE c4 c1 INT, ADD INDEX(c1), ALGORITHM=INPLACE;
ERROR 42S21: Duplicate column name 'c1'
ALTER TABLE t1n CHANGE c4 c11 INT, ADD INDEX(c11), ALGORITHM=INPLACE;
ERROR 0A000: ALGORITHM=INPLACE is not supported. Reason: InnoDB presently supports one FULLTEXT index creation at a time. Try ALGORITHM=COPY.
ALTER TABLE t1n CHANGE c4 c11 INT, LOCK=NONE;
ALTER TABLE t1n ADD INDEX(c11), LOCK=NONE;
### files in MYSQL_DATA_DIR/test
FTS_AUX_INDEX_1.ibd
FTS_AUX_INDEX_2.ibd
@@ -1201,13 +1195,9 @@ tt.isl
t1c.ibd
t1p.ibd
tt.ibd
call mtr.add_suppression("Error: no matching column for .FTS_DOC_ID. in index .ct.--temporary-- of table .test...t1o");
ALTER TABLE t1o ADD FULLTEXT INDEX(ct),
CHANGE c1 FTS_DOC_ID BIGINT UNSIGNED NOT NULL,
ALGORITHM=INPLACE;
ERROR HY000: Incorrect key file for table 't1o'; try to repair it
ALTER TABLE t1o CHANGE c1 FTS_DOC_ID BIGINT UNSIGNED NOT NULL, LOCK=NONE;
ALTER TABLE t1o ADD FULLTEXT INDEX(ct), ALGORITHM=INPLACE;
### files in MYSQL_DATA_DIR/test
FTS_AUX_INDEX_1.ibd
FTS_AUX_INDEX_2.ibd
@@ -1249,6 +1239,9 @@ tt.isl
t1c.ibd
t1p.ibd
tt.ibd
ALTER TABLE t1o CHANGE FTS_DOC_ID foo_id BIGINT UNSIGNED NOT NULL,
LOCK=NONE;
ERROR 0A000: LOCK=NONE is not supported. Reason: Cannot drop or rename FTS_DOC_ID. Try LOCK=SHARED.
SELECT sc.pos FROM information_schema.innodb_sys_columns sc
INNER JOIN information_schema.innodb_sys_tables st
ON sc.TABLE_ID=st.TABLE_ID
@@ -1352,9 +1345,6 @@ tt.isl
tt.ibd
ALTER TABLE t1o CHANGE foo_id FTS_DOC_ID BIGINT UNSIGNED NOT NULL,
ADD FULLTEXT INDEX(ct);
ERROR HY000: Incorrect key file for table 't1o'; try to repair it
ALTER TABLE t1o CHANGE foo_id FTS_DOC_ID BIGINT UNSIGNED NOT NULL, LOCK=NONE;
ALTER TABLE t1o ADD FULLTEXT INDEX(ct), ALGORITHM=INPLACE;
### files in MYSQL_DATA_DIR/test
FTS_AUX_INDEX_1.ibd
FTS_AUX_INDEX_2.ibd