You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Percona has implemented several changes related to *MySQL*’s fast index creation
4
-
feature. Fast index creation was implemented in *MySQL* as a way to speed up the
5
-
process of adding or dropping indexes on tables with many rows.
3
+
## What fast index creation is
6
4
7
-
This feature implements a session variable that enables extended fast index
8
-
creation. Besides optimizing DDL directly,
9
-
[expand_fast_index_creation](#expanded-fast-index-creation) may also optimize index access for
10
-
subsequent DML statements because using it results in much less fragmented
11
-
indexes.
5
+
In *InnoDB*, secondary indexes are separate B-tree structures from the clustered
6
+
index (the primary key). When the server creates a new secondary index on
7
+
an existing table, the server can use two conceptually different approaches:
12
8
13
-
## The **mysqldump** command
9
+
1. Row-by-row maintenance — For each row, insert that row’s entries into the
10
+
new secondary index as you go. Those inserts arrive in primary-key order, not
11
+
in secondary-key order, so the growing B-tree suffers many random-looking
12
+
page splits and a large amount of write amplification. If the server is
13
+
also copying the table (rebuild `ALTER TABLE`), the same pattern applies:
14
+
every row copied into the new table must update every secondary index
15
+
immediately.
14
16
15
-
A new option, `--innodb-optimize-keys`, was implemented in **mysqldump**. It
16
-
changes the way *InnoDB* tables are dumped, so that secondary and foreign keys
17
+
18
+
2. Fast index creation (sorted / bulk build) — The server scans the table’s
19
+
clustered index in primary-key order, generates secondary-key tuples, sorts
20
+
them (often using external merge sort), and builds the secondary index from
21
+
that ordered stream. Work is staged in temporary files under the configured
22
+
`tmpdir`, then merged into a compact B-tree. That path avoids the worst
23
+
random-insert behavior of the row-by-row approach and usually completes with
24
+
less I/O and a less fragmented index.
25
+
26
+
So fast index creation means: build the secondary index from a sorted
27
+
stream after reading the table (or a copy) in clustered index order, instead of
28
+
growing the index by arbitrary-order inserts during the same phase as the data
29
+
copy.
30
+
31
+
Dropping an index is already a cheap metadata change in many cases; the
32
+
performance win is dominated by creating indexes on large tables.
33
+
34
+
## How expanded fast index creation differs from Oracle MySQL {{vers}}
35
+
36
+
The figure below contrasts a typical Oracle MySQL workflow with Percona Server
37
+
when expanded fast index creation is in use (including
38
+
`mysqldump --innodb-optimize-keys` during restore).
39
+
40
+

41
+
42
+
The following compares Percona Server for MySQL with Oracle MySQL {{vers}} on
43
+
code paths that still rebuild the table. InnoDB classifies each `ALTER TABLE`
44
+
operation by algorithm (`INSTANT`, `INPLACE`, `COPY`, and so on); those
45
+
classifications can change between releases, so treat the [InnoDB online DDL
With expanded fast index creation enabled, the server does not only make index
187
+
maintenance cheaper in memory: the server materializes each secondary index in
188
+
temporary files (sorted runs and merge passes) and only then merges the
189
+
result into the final *InnoDB* index. That can consume far more transient
190
+
space than a rough “indexes fit in the tablespace” estimate suggests.
44
191
45
-
## Caveats
192
+
Size the filesystem using the secondary index footprint you are
193
+
rebuilding, not the primary table size alone. You typically need
194
+
well above the on-disk size of those secondary indexes as free
195
+
space under `tmpdir`, on top of anything else the same `ALTER TABLE`or
196
+
`OPTIMIZE TABLE` already needs. For example, a table with about 500 GB
197
+
of data and about 200 GB of secondary indexes may still require
198
+
significantly more than 200 GB of free `tmpdir` space while those
199
+
indexes are being built.
46
200
47
-
*InnoDB* fast index creation uses temporary files in tmpdir for all indexes
48
-
being created. So make sure you have enough tmpdir space when using
49
-
[expand_fast_index_creation](#expanded-fast-index-creation). It is a session variable, so you can
50
-
temporarily switch it off if you are short on tmpdir space and/or don’t want
51
-
this optimization to be used for a specific table.
201
+
If `tmpdir` fills during the operation, the statement fails and rolls
202
+
back. You lose the work done up to the failure and must free or enlarge
203
+
storage (orpoint`tmpdir` at a larger volume), or run with
204
+
`expand_fast_index_creation` disabled for that job, before retrying.
52
205
53
-
There’s also a number of cases when this optimization is not applicable:
206
+
[`expand_fast_index_creation`](#expanded-fast-index-creation) is a session or
207
+
global variable: you can set`expand_fast_index_creation` to `OFF` for a single session if `tmpdir` is
208
+
too small for a specific table or maintenance window.
209
+
210
+
There’s also a number of cases when the expanded fast index creation optimization is not applicable:
54
211
55
212
*`UNIQUE` indexes in`ALTER TABLE` are ignored to enforce uniqueness where
56
213
necessary when copying the data to a temporary table;
57
214
215
+
58
216
*`ALTER TABLE`and`OPTIMIZE TABLE` always process tables containing
59
217
foreign keys as if [expand_fast_index_creation](#expanded-fast-index-creation) is OFF to avoid
60
218
dropping keys that are part of a FOREIGN KEYconstraint;
61
219
220
+
62
221
*`ALTER TABLE`and`OPTIMIZE TABLE` always process partitioned tables as if
63
222
[expand_fast_index_creation](#expanded-fast-index-creation) is OFF;
64
223
65
-
***mysqldump --innodb-optimize-keys** ignores foreign keys because
66
-
*InnoDB* requires a full table rebuild on foreign key changes. So adding them
224
+
225
+
* mysqldump --innodb-optimize-keys ignores foreign keys because
226
+
*InnoDB* requires a full table rebuild onforeign key changes. So adding foreign keys
67
227
back with a separate `ALTER TABLE` after restoring the data from a dump
68
228
would actually make the restore slower;
69
229
70
-
***mysqldump --innodb-optimize-keys** ignores indexes on
71
-
`AUTO_INCREMENT` columns, because they must be indexed, so it is impossible
72
-
to temporarily drop the corresponding index;
73
230
74
-
***mysqldump --innodb-optimize-keys** ignores the first UNIQUE index on
231
+
* mysqldump --innodb-optimize-keys ignores indexes on
232
+
`AUTO_INCREMENT` columns, because those columns must be indexed, so temporarily dropping the corresponding index is impossible;
233
+
234
+
235
+
* mysqldump --innodb-optimize-keys ignores the first UNIQUE index on
75
236
non-nullable columns when the table has no `PRIMARY KEY` defined, because in
76
-
this case*InnoDB* picks such an index as the clustered one.
237
+
that layout*InnoDB* picks such an index as the clustered one.
77
238
78
239
## System variables
79
240
@@ -86,12 +247,28 @@ this case *InnoDB* picks such an index as the clustered one.
86
247
| Scope: | Local/Global |
87
248
| Dynamic: | Yes |
88
249
| Data type | Boolean |
89
-
| Default value | ON/OFF |
250
+
| Default value | OFF |
251
+
252
+
When set to `ON`, *InnoDB* may drop eligible non-unique secondary indexes for the
253
+
data-copy phase of rebuild-style `ALTER TABLE`and`OPTIMIZE TABLE`, then
254
+
recreate those indexes with the sorted bulk build described [above](#what-fast-index-creation-is).
255
+
256
+
## Related documentation
257
+
258
+
### Percona Server for MySQL documentation
259
+
260
+
* [Percona Server for MySQL feature comparison](feature-comparison.md) — how expanded fast index creation compares to MySQL {{vers}}
261
+
262
+
* [Percona Server for MySQL variables](percona-server-system-variables.md) — full list of Percona-specific system variables, including `expand_fast_index_creation`
263
+
264
+
* [Extended mysqldump](extended-mysqldump.md) — Percona `mysqldump` enhancements, including `--innodb-optimize-keys`
90
265
91
-
!!! admonition "See also"
266
+
* [InnoDB page fragmentation counters](innodb-fragmentation-count.md) — monitoring index fragmentation
92
267
93
-
[Improved InnoDB fast index creation :octicons-link-external-16:](https://www.mysqlperformanceblog.com/2011/11/06/improved-innodb-fast-index-creation/)
268
+
### MySQL Reference Manual
94
269
95
-
[Thinking about running OPTIMIZE on your InnoDB Table? Stop! :octicons-link-external-16:](https://www.mysqlperformanceblog.com/2010/12/09/thinking-about-running-optimize-on-your-innodb-table-stop/)
270
+
* [InnoDB and online DDL :octicons-link-external-16:](https://dev.mysql.com/doc/refman/{{vers}}/en/innodb-online-ddl.html)
0 commit comments