MySQL のクエリとトランザクションのサイズ
場合によっては、トランザクションのサイズを把握することが重要になる場合があります。特に、クラスターの最適な動作を保証するためにデフォルトでトランザクションのサイズが制限されている HA ソリューションへの移行を計画している場合は重要です。
今日は、トランザクションのサイズを把握するためのさまざまな可能性を見ていきます。
まず、トランザクションを 2 つのタイプに分割する必要があります。
- データを生成するもの (挿入、削除、更新、DML などの書き込み)
- 準備ができているデータのみ (選択、DQL)
高可用性を実装するには、最初のカテゴリのみが重要です。
DMLのサイズ
DML トランザクションのサイズを知る唯一の方法は、バイナリ ログを解析する (または binlog イベントをクエリする) ことです。
binlog ファイルから binlog イベントを確認し、そのサイズを計算する必要があります。これを説明するために、特定の GTID で識別されるトランザクションを見つけてみましょう。 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541914
SQL > \pager grep 'Gtid\|COMMIT' ;
Pager has been set to 'grep 'Gtid\|COMMIT' ;'.
SQL > show BINLOG EVENTS in 'binlog.000064' ;
| binlog.000064 | 213 | Gtid | 1 | 298 | SET @@SESSION.GTID_NEXT= '17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541914' |
| binlog.000064 | 53904723 | Xid | 1 | 53904754 | COMMIT /* xid=75 */ |
SQL > \pager
Pager has been disabled.
SQL > select format_bytes(53904754-213);
+----------------------------+
| format_bytes(53904754-213) |
+----------------------------+
| 51.41 MiB |
+----------------------------+
1 row in set (0.0005 sec)
このトランザクションにより 51MB の binlog イベントが生成されたことがわかります。
この方法は、目的のトランザクションを見つけるために複数の binlog ファイルを解析する必要がある場合には、複雑になる可能性があります。
うまくいけば、 Performance_Schema
再び私たちの生活が楽になります。実際、テーブルを解析して binary_log_transaction_compression_stats
トランザクションのサイズに関する情報を得ることができます。バイナリログ圧縮を使用しない場合でも、次のようになります。
select format_bytes(UNCOMPRESSED_BYTES_COUNTER/TRANSACTION_COUNTER) size,
format_bytes(COMPRESSED_BYTES_COUNTER/TRANSACTION_COUNTER) compressed,
TRANSACTION_COUNTER
from performance_schema.binary_log_transaction_compression_stats;
+-----------+------------+---------------------+
| size | compressed | TRANSACTION_COUNTER |
+-----------+------------+---------------------+
| 51.38 MiB | 51.38 MiB | 1 |
+-----------+------------+---------------------+
TRANSACTION_COUNTER
列が 1 より大きい場合、値は平均となるため、この 列は非常に重要です。
したがって、1 つのトランザクションの正確なサイズを本当に知る必要がある場合は、DML を実行する前に、まずそのテーブルを切り詰める必要があります。
この例を見てみましょう。
SQL> select format_bytes(UNCOMPRESSED_BYTES_COUNTER/TRANSACTION_COUNTER) size,
format_bytes(COMPRESSED_BYTES_COUNTER/TRANSACTION_COUNTER) compressed,
TRANSACTION_COUNTER
from performance_schema.binary_log_transaction_compression_stats;
+-----------+------------+---------------------+
| size | compressed | TRANSACTION_COUNTER |
+-----------+------------+---------------------+
| 17.13 MiB | 17.13 MiB | 6 |
+-----------+------------+---------------------+
1 row in set (0.0004 sec)
SQL > truncate table performance_schema.binary_log_transaction_compression_stats;
Query OK, 0 rows affected (0.0018 sec)
SQL > update sbtest1 set k=k+4;
Query OK, 132188 rows affected (1.3213 sec)
Rows matched: 132188 Changed: 132188 Warnings: 0
SQL > select format_bytes(UNCOMPRESSED_BYTES_COUNTER/TRANSACTION_COUNTER) size,
format_bytes(COMPRESSED_BYTES_COUNTER/TRANSACTION_COUNTER) compressed,
TRANSACTION_COUNTER
from performance_schema.binary_log_transaction_compression_stats;
+-----------+------------+---------------------+
| size | compressed | TRANSACTION_COUNTER |
+-----------+------------+---------------------+
| 51.38 MiB | 51.38 MiB | 1 |
+-----------+------------+---------------------+
1 row in set (0.0017 sec)
バイナリ ログからすべてのトランザクション サイズをリストするMySQL シェル プラグインを使用する可能性はまだあります 。
JS > check.showTrxSizeSort()
Transactions in binary log binlog.000064 orderer by size (limit 10):
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541926
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541925
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541921
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541916
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541915
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541918
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541917
51 mb - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541914
257 bytes - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541924
257 bytes - 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541923
しかし、トランザクションの GTID を知るにはどうすればよいでしょうか?
MySQL は、サーバーから返された情報をサポートしている場合、GTID をクライアントに返す可能性があります。MySQL Shell はその機能をサポートしています。
これを有効にするには、次を使用します session_track_gtids
。
SQL > set session_track_gtids='OWN_GTID';
Query OK, 0 rows affected (0.0001 sec)
SQL > update sbtest1 set k=k+1;
Query OK, 132183 rows affected (5.6854 sec)
Rows matched: 132183 Changed: 132183 Warnings: 0
GTIDs: 17f6a975-e2b4-11ec-b714-c8cb9e32df8e:7541914
ご覧のとおり、MySQL Shell はトランザクションの GTID を返しました (auto_commit を使用して更新)。
DQLのサイズ
しかし、SELECT のサイズを知る可能性はあるでしょうか?
SELECT のサイズを決定するには、次のようにサーバーからクライアントに送信されるバイト数を計算します。
SQL > select variable_value
from performance_schema.status_by_thread
join performance_schema.threads using(thread_id)
where processlist_id=CONNECTION_ID()
and variable_name='Bytes_sent' into @before;
SQL > select * from sbtest1;
SQL > select format_bytes(variable_value - @before) query_size
from performance_schema.status_by_thread
join performance_schema.threads using(thread_id)
where processlist_id=CONNECTION_ID()
and variable_name='Bytes_sent' ;
+------------+
| query_size |
+------------+
| 26.08 MiB |
+------------+
1 row in set (0.0010 sec)
まとめ
ご覧のとおり、MySQL Server は Performance_Schema
バイナリ ログを介して多くの情報を提供します。その情報を解析すると、DML トランザクションまたは DQL のサイズを取得できます。
MySQL をお楽しみください!