ちょっと硬派なコンピュータフリークのBlogです。

カスタム検索

2011-10-06

加速的に膨張する宇宙のように進化するMySQL!最新開発版MySQL 5.6.3 m6新機能解説

最新の開発版であるMySQL 5.6.3-m6がリリースされた。清く正しいMySQLerの皆さんはすでにダウンロードして、評価を楽しんでくれていることだろう。はっきり言ってこのバージョンは凄い。明らかに前バージョンのMySQL 5.6.2から搭載されている新機能の数は膨大である。それはMySQL 5.6.3のリリースノートを見てもらえば一目瞭然だ。凄いボリュームだからだ。

今回はそんな膨大な新機能を搭載したMySQL 5.6.3について、要点を解説しようと思う。MySQL 5.6.3は開発版なので今直ぐ本番環境へ投入したい!というはやる気持ちはグッと我慢して頂きたいが、ぜひ評価はしていただきたいと思う。

パラレルSQLスレッド

MySQLのレプリケーションでは、大量のクエリを実行すると何かとスレーブが遅れがちであった。スレーブでは単一のSQLスレッドだけがクエリを実行するからである。その問題を少しでも軽減してくれるのがパラレルSQLスレッドだ。文字通りスレーブでSQLスレッドによるクエリの実行が並列化される。SQLスレッドによるクエリの実行を並列化するには、slave_parallel_workersオプションを設定しよう。

ただし、今回の実装には次のような制限があるので注意が必要だ。
  • 並列化の単位はデータベースごと。同じデータベースに対するクエリは並列化されない。
  • マスターとトランザクションの実行順序が異なる可能性がある。クラッシュしたらリカバリが大変かも。

使いどころには工夫が必要だが、ツボにはまると嬉しいことは間違いないだろう。

BKA JOIN

MySQL 5.6.3-m6ではオプティマイザがいくつか強化されている。BKA JOINはそのうちのひとつだ。

かつてMySQL ABがMySQL 5.1の次期バージョンをMySQL 6.0として開発していたときに搭載予定であったBKA JOIN(Batched Key Access JOIN)がついに搭載された。(6.0開発中止の経緯についてはこのエントリを参照のこと。)BKA JOINは変形NLJ(Nested Loop JOIN)とも言うべきもので、内部表からのレコードのフェッチをひとつずつではなくまとめて行う。先に駆動表から結合するキーの値をいくつかピックアップし、それを内部表に対してまとめて渡す。(Index Condition Pushdownする。)すると、内部表ではMRR(Multi Range Read)最適化によってアクセスがソートされ、必要なレコードを最適な順序でフェッチすることになり、JOINが高速化するというわけだ。

InnoDBやMyISAMでは、MRRによる高速化が見込めるのははセカンダリインデックスによるアクセス時だけである。(主キーでアクセスする場合には別段変わらない。)従って内部表のセカンダリインデックスを使って結合する場合には高速化が見込めるだろう。BKAが使われているかどうかは、EXPLAINでExtraフィールドを見れば分かる。以下はEXPLAINの実行例である。(両方のテーブルにおいてNameカラムにインデックスをはってある。)

mysql> explain select * from Country, City where City.Name like 'A%' and Country.Name = City.Name\G
*************************** 1. row ***************************
           id: 1
  select_type: SIMPLE
        table: City
         type: range
possible_keys: Name
          key: Name
      key_len: 35
          ref: NULL
         rows: 258
        Extra: Using index condition; Using MRR
*************************** 2. row ***************************
           id: 1
  select_type: SIMPLE
        table: Country
         type: ref
possible_keys: Name
          key: Name
      key_len: 52
          ref: world.City.Name
         rows: 1
        Extra: Using index condition; Using join buffer (Batched Key Access)
2 rows in set (0.00 sec)

FROM句のサブクエリの最適化

これまで、FROM句のサブクエリは必ず先にマテリアライゼーション(実体化)が行われていた。外部クエリはマテリアライズされたテンポラリテーブルに対して行うという形式をとっていた。これが改善され、FROM句のサブクエリのマテリアライズは、実際にレコードが必要になるまで行われないようになった。これによって、外部クエリの条件によって、FROM句のサブクエリにおいて行の絞り込みが出来るようになった。以下の例では、derivedテーブルへのアクセスにおいてキーが使われている様子が示されている。

mysql> explain select * from Country, (select Id, Name from City) c where c.Id = Country.Capital;
+----+-------------+------------+-------+---------------+-----------+---------+-----------------------+------+-------------+
| id | select_type | table      | type  | possible_keys | key       | key_len | ref                   | rows | Extra       |
+----+-------------+------------+-------+---------------+-----------+---------+-----------------------+------+-------------+
|  1 | PRIMARY     | Country    | ALL   | NULL          | NULL      | NULL    | NULL                  |  242 | Using where |
|  1 | PRIMARY     |  | ref   | auto_key0     | auto_key0 | 4       | world.Country.Capital |   17 |             |
|  2 | DERIVED     | City       | index | NULL          | Name      | 35      | NULL                  | 4345 | Using index |
+----+-------------+------------+-------+---------------+-----------+---------+-----------------------+------+-------------+
3 rows in set (0.00 sec)

また、以前はEXPLAINを実行するだけでもマテリアライゼーションが行われていたが、MySQL 5.6.3では行われなくなった。

SELECT以外のクエリへのEXPLAINの対応

これまでのMySQLのバージョンでは、EXPLAINで実行計画を調べることが出来るのはSELECTだけであった。しかし、MySQL 5.6.3では他の種類のステートメントもEXPLAINでサポートされたのである。これまで、UPDATEなどの実行計画を調べるときはわざわざ同じWHERE句を持つSELECTに書き換えてEXPLAINを実行する必要があったが、MySQL 5.6.3以降ではUPDATE、DELTE、INSERT、REPLACEについて直接EXPLAINを実行できる。便利だ。

Optimizer Trace

これはMySQL 5.6.3で初登場した新機能だ。Optimizerがどのような判断をしたかということが、トレースできるようになっている。トレースはJSON形式で出力される。詳細はMySQL Internalsのページを見て頂きたい。使い方は以下のとおり。

SET optimizer_trace='enabled=on';
select * from Country, City where City.Name like 'A%' and Country.Name = City.Name; -- 任意のクエリを実行
SELECT * FROM INFORMATION_SCHEMA.OPTIMIZER_TRACE;
SET optimizer_trace='enabled=off';

リリースノートにも書いてあるが、この機能は今後仕様が変更される公算が高い。評価したい人は「お試し」として使うようにしよう。(Optimizer Traceの現在の仕様を元にツール等を作りこむのはもう少し先にしよう。)

Performance Schema強化

MySQL 5.6.3ではパフォーマンススキーマも強化された。以前からlabs.mysql.comで公開していた機能を取り込んだものになる。パフォーマンススキーマについては、以前MySQL Casual #2で発表したときの資料があるので、そちらを参照して頂きたい。

InnoDB超進化!

MySQLがどれだけ性能を向上させられたかというテーマを語るとき、その中心になるのがInnoDBだ。MySQL 5.6.3ではInnoDBも超^256進化している。まさにそれが欲しかった!という機能が追加されているといえよう。
  • ログの最大サイズが4GBから512GBへ拡張。
  • ページチェックサムの高速化。(新しいアルゴリズムを用いるためフォーマットのバリエーションが増えた)
  • 終了時にバッファプールの内容を保存することができるようになった。起動時に読み込んでキャッシュを高速にあたためることが可能。
  • デッドロックの検知が高速化。
  • スレッドスケジューリングの効率化。
  • バッファプールのフラッシュが高速化。
  • UNDOログ(ロールバックセグメント)専用の独立したテーブルスペースを作成可能。
などなど。

ネットワークのボトルネック解消

Bug #54790として登録されていたLinuxにおけるソケットI/Oに関するボトルネックの問題が解消した。松信さんがブログエントリにまとめてくれているので、詳細はそちらを参照のこと。ベンチマーク結果付きである。熱い!

ベンチマークは5.5.16と5.6.3の比較になっているが、性能差を全てこのバグによるものだと考えるのはちょっと無理がある。MySQL 5.6.3では他にもたくさんの改善がなされており、性能差は総合力の差によるものだろう。

まとめ

以上、主な新機能について解説を行ったが、MySQL 5.6.3の新機能はまだまだこれだけではない。長大なリリースノート(英語)があるので、詳細についてはそちらを見ていただきたいと思う。

というわけで、MySQL 5.6.3は怒涛の進化をしたということをお分かりいただけただろうか。宇宙は加速的に膨張しているらしいが、MySQLも加速的に進化を遂げており、その勢いは留まることを知らない!本エントリを読み終えた方は、今すぐダウンロードして進化したMySQL 5.6.3を体験して頂きたい。

Enjoy!!

Download

0 コメント:

コメントを投稿