Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve compatibility for ALTER TABLE algorithms #19162

Closed
kolbe opened this issue Aug 12, 2020 · 5 comments · Fixed by #19270
Closed

Improve compatibility for ALTER TABLE algorithms #19162

kolbe opened this issue Aug 12, 2020 · 5 comments · Fixed by #19270
Labels
feature/accepted This feature request is accepted by product managers help wanted Denotes an issue that needs help from a contributor. Must meet "help wanted" guidelines. type/feature-request Categorizes issue or PR as related to a new feature.

Comments

@kolbe
Copy link
Contributor

kolbe commented Aug 12, 2020

Feature Request

Is your feature request related to a problem? Please describe:

The changes implemented to address #8428 introduce incompatibilities with MySQL that make migrations difficult.

mysql> ALTER TABLE t1   MODIFY COLUMN e enum('A', 'B') NOT NULL DEFAULT 'A', ALGORITHM = inplace;
ERROR 1846 (0A000): ALGORITHM=INPLACE is not supported. Reason: Cannot alter table by INPLACE. Try ALGORITHM=INSTANT.

Describe the feature you'd like:

Our support of ALTER TABLE algorithms tries to match their names literally to the kind of operation being performed by TiDB, not to the kind of operation that a user of MySQL would expect.

We should add at least syntactic support for the same algorithms supported in MySQL. We could either do this by always allowing INSTANT/INPLACE for any ALTER TABLE statement in TiDB, or, if we feel there's a danger of surprise or worse, we could add a server option to give that behavior.

Describe alternatives you've considered:

A comment format that causes TiDB to ignore a statement but allow it to be executed by MySQL could be another option, though that would require modifications to a user's application or testing mechanisms.

Teachability, Documentation, Adoption, Migration Strategy:

@kolbe kolbe added the type/feature-request Categorizes issue or PR as related to a new feature. label Aug 12, 2020
@ghost
Copy link

ghost commented Aug 13, 2020

I think the fix can be straight forward: make these purely assertions that ALGORITHM=x means "this or better", whereby:

INSTANT > INPLACE > COPY

This can be documented as a MySQL incompatibility, but I think it's reasonable. MySQL supports COPY for everything, because that's how it started.. everything was a copy, and then it started adding optimizations. TiDB was designed better from the start where many of these things are optimized.

I did a quick test in MySQL, and you really can force all 3 behaviors on some operations (even though my "copy" was faster than instant). I think guaranteeing "this or better" is fine:

DROP TABLE IF EXISTS t1;
CREATE TABLE t1 (
 id BIGINT NOT NULL PRIMARY KEY auto_increment,
 pad1 VARBINARY(1024)
);

INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM dual;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;
INSERT INTO t1 SELECT NULL, RANDOM_BYTES(1024) FROM t1 a JOIN t1 b JOIN t1 c LIMIT 10000;

ALTER TABLE t1 ADD pad2 VARBINARY(1024), ALGORITHM=INSTANT;
ALTER TABLE t1 ADD pad3 VARBINARY(1024), ALGORITHM=INPLACE;
ALTER TABLE t1 ADD pad4 VARBINARY(1024), ALGORITHM=COPY;
..

mysql [localhost:8021] {msandbox} (test) > ALTER TABLE t1 ADD pad2 VARBINARY(1024), ALGORITHM=INSTANT;
Query OK, 0 rows affected (0.06 sec)
Records: 0  Duplicates: 0  Warnings: 0

mysql [localhost:8021] {msandbox} (test) > ALTER TABLE t1 ADD pad3 VARBINARY(1024), ALGORITHM=INPLACE;
Query OK, 0 rows affected (13.95 sec)
Records: 0  Duplicates: 0  Warnings: 0

mysql [localhost:8021] {msandbox} (test) > ALTER TABLE t1 ADD pad4 VARBINARY(1024), ALGORITHM=COPY;
Query OK, 81010 rows affected (1.69 sec)
Records: 81010  Duplicates: 0  Warnings: 0

@zz-jason zz-jason added the feature/accepted This feature request is accepted by product managers label Aug 13, 2020
@zz-jason
Copy link
Member

I mark this feature request as accepted. @bb7133 PTAL if we can improve this.

@bb7133
Copy link
Member

bb7133 commented Aug 13, 2020

I think the fix can be straight forward: make these purely assertions that ALGORITHM=x means "this or better”

I think this is valuable & reasonable, thanks @nullnotnil

@bb7133 bb7133 added difficulty/easy help wanted Denotes an issue that needs help from a contributor. Must meet "help wanted" guidelines. labels Aug 13, 2020
@bb7133
Copy link
Member

bb7133 commented Aug 18, 2020

INSTANT > INPLACE > COPY

For now, the COPY algorithm is applicable for all DDL statements but INPLACE/INSTANT is not:

tidb> alter table t add column c int, algorithm=copy;
Query OK, 0 rows affected, 1 warning (0.03 sec)

tidb> show warnings;
+-------+------+---------------------------------------------------------------------------------------------+
| Level | Code | Message                                                                                     |
+-------+------+---------------------------------------------------------------------------------------------+
| Error | 1846 | ALGORITHM=COPY is not supported. Reason: Cannot alter table by COPY. Try ALGORITHM=INSTANT. |
+-------+------+---------------------------------------------------------------------------------------------+
1 row in set (0.00 sec)

IMHO if a 'better' algorithm is chosen by TiDB, we raise a warning just like the message for COPY, @nullnotnil are you fine with it?

@ghost
Copy link

ghost commented Aug 18, 2020

IMHO if a 'better' algorithm is chosen by TiDB, we raise a warning just like the message for COPY, @nullnotnil are you fine with it?

LGTM

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feature/accepted This feature request is accepted by product managers help wanted Denotes an issue that needs help from a contributor. Must meet "help wanted" guidelines. type/feature-request Categorizes issue or PR as related to a new feature.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants