MySQL Invisible Indexes
This article discusses MySQL invisible indexes and the common usage.
MySQL 8 introduces invisible indexes. Invisible indexes are indexes that actually exist, but are not visible to the MySQL query optimizer. Even if used by FORCE INDEX
, the optimizer will not use invisible indexes.
Before dropping an index, you can hide the index first. If this doesn’t affect performance, then you can actually drop the index.
A invisible indexe is invisible to the MySQL query optimizer, but it exists and is kept up to date for write operations.
MySQL Invisible Index Usage
MySQL allows you to use VISIBLE
and INVISIBLE
identify whether an index is visible.
Create invisible indexe
To create a invisible indexe, use the CREATE INDEX
statement:
CREATE INDEX index_name
ON table_name(c1, c2, ...) INVISIBLE;
Modify the visibility of the index
To change the visibility of an existing index, use the ALTER TABLE
statement:
ALTER TABLE table_name
ALTER INDEX index_name [VISIBLE | INVISIBLE];
ALTER TABLE
You can easily toggle the visibility of existing indexes with the statement.
Note that you cannot set an index on a primary key column as a invisible indexe, or MySQL will give an error.
Use Invisible Indexes
The MySQL query optimizer does not use invisible indexes by default, but you can modify this behavior through the use_invisible_indexes
property in the system variable optimizer_switch
.
To view the current settings, use the following statement:
SELECT @@optimizer_switch;
index_merge=on,index_merge_union=on,index_merge_sort_union=on,index_merge_intersection=on,index_merge_sort_intersection=off,engine_condition_pushdown=off,index_condition_pushdown=on,derived_merge=on,derived_with_keys=on,firstmatch=on,loosescan=on,materialization=on,in_to_exists=on,semijoin=on,partial_match_rowid_merge=on,partial_match_table_scan=on,subquery_cache=on,mrr=off,mrr_cost_based=off,mrr_sort_keys=off,outer_join_with_cache=on,semijoin_with_cache=on,join_cache_incremental=on,join_cache_hashed=on,join_cache_bka=on,optimize_join_buffer_size=on,table_elimination=on,extended_keys=on,exists_to_in=on,orderby_uses_equalities=on,condition_pushdown_for_derived=on,split_materialized=on,condition_pushdown_for_subquery=on,rowid_filter=on,condition_pushdown_from_having=on,not_null_range_scan=off
To modify the default behavior for the current session, use the following statement:
SET SESSION optimizer_switch="use_invisible_indexes=on";
Conclusion
A MySQL invisible indexe is a real index that is invisible to the MySQL query optimizer.