mirror of
https://github.com/percona/percona-toolkit.git
synced 2025-09-10 21:19:59 +00:00
PT-2340 - Support MySQL 8.4
- Updated documentation
This commit is contained in:
@@ -2656,9 +2656,7 @@ bookmark lookup into the film_actor table.
|
||||
=back
|
||||
|
||||
For more information on how to read EXPLAIN output, please see
|
||||
L<http://dev.mysql.com/doc/en/explain.html>, and this talk titled
|
||||
"MySQL query optimizer internals and upcoming features in v. 5.2":
|
||||
from Timour Katchaounov, one of the MySQL developers: L<http://goo.gl/VIWvo>
|
||||
L<http://dev.mysql.com/doc/en/explain.html>.
|
||||
|
||||
=head1 MODULES
|
||||
|
||||
@@ -2693,13 +2691,11 @@ trying to figure out how this works, but otherwise this section will probably
|
||||
not make your life richer.
|
||||
|
||||
The tree can be built by examining the id, select_type, and table columns of
|
||||
each row. Here's what I know about them:
|
||||
each row.
|
||||
|
||||
The id column is the sequential number of the select. This does not indicate
|
||||
nesting; it just comes from counting SELECT from the left of the SQL statement.
|
||||
It's like capturing parentheses in a regular expression. A UNION RESULT row
|
||||
doesn't have an id, because it isn't a SELECT. The source code actually refers
|
||||
to UNIONs as a fake_lex, as I recall.
|
||||
It's like capturing parentheses in a regular expression.
|
||||
|
||||
If two adjacent rows have the same id value, they are joined with the standard
|
||||
single-sweep multi-join method.
|
||||
@@ -2749,7 +2745,7 @@ access to the temporary table that holds the result of the subquery whose id is
|
||||
N. If it says <unionN,..N> it's the same thing, but it refers to the results it
|
||||
UNIONs together.
|
||||
|
||||
Finally, order matters. If a row's id is less than the one before it, I think
|
||||
Finally, order matters. If a row's id is less than the one before it,
|
||||
that means it is dependent on something other than the one before it. For
|
||||
example,
|
||||
|
||||
@@ -2765,7 +2761,7 @@ example,
|
||||
| 3 | SUBQUERY | film_actor |
|
||||
| 2 | SUBQUERY | film |
|
||||
|
||||
If the results were in order 2-3-4, I think that would mean 3 is a subquery of
|
||||
If the results were in order 2-3-4, that would mean 3 is a subquery of
|
||||
2, 4 is a subquery of 3. As it is, this means 4 is a subquery of the nearest
|
||||
previous recent row with a smaller id, which is 1. Likewise for 3 and 2.
|
||||
|
||||
@@ -2802,8 +2798,8 @@ following:
|
||||
| NULL | UNION RESULT | <union5,6> |
|
||||
| NULL | UNION RESULT | <union1,4> |
|
||||
|
||||
This would be a lot easier to work with if it looked like this (I've
|
||||
bracketed the id on rows I moved):
|
||||
This would be a lot easier to work with if it looked like this (we've
|
||||
bracketed the id on rows we moved):
|
||||
|
||||
| id | select_type | table |
|
||||
+------+--------------+------------+
|
||||
@@ -2819,7 +2815,7 @@ bracketed the id on rows I moved):
|
||||
|
||||
In fact, why not re-number all the ids, so the PRIMARY row becomes 2, and so on?
|
||||
That would make it even easier to read. Unfortunately that would also have the
|
||||
effect of destroying the meaning of the id column, which I think is important to
|
||||
effect of destroying the meaning of the id column, which is important to
|
||||
preserve in the final tree. Also, though it makes it easier to read, it doesn't
|
||||
make it easier to manipulate programmatically; so it's fine to leave them
|
||||
numbered as they are.
|
||||
@@ -2831,7 +2827,7 @@ the slice of rows that should be child nodes in the tree: you just look for the
|
||||
first row whose ID is the same as the first number in the table.
|
||||
|
||||
The next question is how to find the last row that should be a child node of a
|
||||
UNION or DERIVED. I'll start with DERIVED, because the solution makes UNION
|
||||
UNION or DERIVED. We'll start with DERIVED, because the solution makes UNION
|
||||
easy.
|
||||
|
||||
Consider how MySQL numbers the SELECTs sequentially according to their position
|
||||
@@ -2871,14 +2867,14 @@ Here's the output of EXPLAIN:
|
||||
| NULL | UNION RESULT | <union3,5> |
|
||||
| 2 | DERIVED | film |
|
||||
|
||||
The siblings all have id 1, and the middle one I care about is derived3.
|
||||
(Notice MySQL doesn't execute them in the order I defined them, which is fine).
|
||||
Now notice that MySQL prints out the rows in the opposite order I defined the
|
||||
subqueries: 6, 3, 2. It always seems to do this, and there might be other
|
||||
The siblings all have id 1, and the middle one we care about is derived3.
|
||||
(Notice MySQL doesn't execute them in the order they are defined, which is fine).
|
||||
Now notice that MySQL prints out the rows in the opposite order the subqueries
|
||||
were defined: 6, 3, 2. It always seems to do this, and there might be other
|
||||
methods of finding the scope boundaries including looking for the lower boundary
|
||||
of the next largest sibling, but this is a good enough heuristic. I am forced
|
||||
to rely on it for non-DERIVED subqueries, so I rely on it here too. Therefore,
|
||||
I decide that everything greater than or equal to 3 belongs to the DERIVED
|
||||
of the next largest sibling, but this is a good enough heuristic. We are forced
|
||||
to rely on it for non-DERIVED subqueries, so we rely on it here too. Therefore,
|
||||
we decide that everything greater than or equal to 3 belongs to the DERIVED
|
||||
scope.
|
||||
|
||||
The rule for UNION is simple: they consume the entire enclosing scope, and to
|
||||
@@ -2894,8 +2890,8 @@ the enclosing scope's boundaries, and the rest is easy. Notice in the example
|
||||
above, the UNION is over <union3,5>, which includes the row with id 4 -- it
|
||||
includes every row between 3 and 5.
|
||||
|
||||
Finally, there are non-derived subqueries to deal with as well. In this case I
|
||||
can't look at siblings to find the end of the scope as I did for DERIVED. I
|
||||
Finally, there are non-derived subqueries to deal with as well. In this case we
|
||||
can't look at siblings to find the end of the scope as we did for DERIVED. We
|
||||
have to trust that MySQL executes depth-first. Here's an example:
|
||||
|
||||
explain
|
||||
@@ -2950,16 +2946,14 @@ select 4 came first. In other words, if EXPLAIN looked like this,
|
||||
| 4 | DEPENDENT SUBQUERY | actor |
|
||||
|
||||
I would be forced to assume upon seeing select 3 that select 4 is a subquery
|
||||
of it, rather than just being the next sibling in the enclosing scope. If this
|
||||
is ever wrong, then the algorithm is wrong, and I don't see what could be done
|
||||
about it.
|
||||
of it, rather than just being the next sibling in the enclosing scope.
|
||||
|
||||
UNION is a little more complicated than just "the entire scope is a UNION,"
|
||||
because the UNION might itself be inside an enclosing scope that's only
|
||||
indicated by the first item inside the UNION. There are only three kinds of
|
||||
enclosing scopes: UNION, DERIVED, and SUBQUERY. A UNION can't enclose a UNION,
|
||||
and a DERIVED has its own "scope markers," but a SUBQUERY can wholly enclose a
|
||||
UNION, like this strange example on the empty table t1:
|
||||
and a DERIVED has its own "scope markers," but a SUBQUERY in earlier versions
|
||||
could wholly enclose a UNION, like this strange example on the empty table t1:
|
||||
|
||||
explain select * from t1 where not exists(
|
||||
(select t11.i from t1 t11) union (select t12.i from t1 t12));
|
||||
@@ -2974,12 +2968,8 @@ UNION, like this strange example on the empty table t1:
|
||||
|
||||
The UNION's backward references might make it look like the UNION encloses the
|
||||
subquery, but studying the query makes it clear this isn't the case. So when a
|
||||
UNION's first row says SUBQUERY, it is this special case.
|
||||
|
||||
By the way, I don't fully understand this query plan; there are 4 numbered
|
||||
SELECT in the plan, but only 3 in the query. The parens around the UNIONs are
|
||||
meaningful. Removing them will make the EXPLAIN different. Please tell me how
|
||||
and why this works if you know.
|
||||
UNION's first row says SUBQUERY, it is this special case that we cannot repeat
|
||||
starting from MySQL 5.7.
|
||||
|
||||
Armed with this knowledge, it's possible to use recursion to turn the
|
||||
parent-child relationship between all the rows into a tree representing the
|
||||
@@ -3011,8 +3001,7 @@ The execution plan looks like a depth-first traversal of this tree:
|
||||
|
||||
The JOIN might not be a JOIN. It might be a subquery, for example. This comes
|
||||
from the type column of EXPLAIN. The documentation says this is a "join type,"
|
||||
but I think "access type" is more accurate, because it's "how MySQL accesses
|
||||
rows."
|
||||
but "access type" may be more accurate, because it's "how MySQL accesses rows."
|
||||
|
||||
pt-visual-explain decorates the tree significantly more than just turning
|
||||
rows into nodes. Each node may get a series of transformations that turn it
|
||||
@@ -3217,6 +3206,12 @@ dsn: user; copy: yes
|
||||
|
||||
User for login if not current user.
|
||||
|
||||
=item * s
|
||||
|
||||
dsn: mysql_ssl; copy: yes
|
||||
|
||||
Create SSL connection
|
||||
|
||||
=back
|
||||
|
||||
=head1 ENVIRONMENT
|
||||
|
Reference in New Issue
Block a user