MySQL 5.6から5.7にアップグレードしたところ、WordPressプラグインテーブルにとんでもない438フィールドが含まれ、行サイズの上限である8126バイトを超えていることがわかりました。
mysql_upgrade
の実行時に受け取った警告は次のとおりです。
行サイズが大きすぎます(> 8126)。一部の列をTEXTまたはBLOBに変更するか、ROW_FORMAT = DYNAMICまたはROW_FORMAT = COMPRESSEDを使用すると役立つ場合があります。現在の行形式では、768バイトのBLOBプレフィックスがインラインで格納されます。
これは単なる警告でしたが、テーブルはまだ残っています。 同じ構造で新しいテーブルを作成することはできませんが、興味深いことに、古いテーブルを保持できますそしてそれを使用します(少なくともSELECT
から)。
私は同様のトピックについて RolandoMySQLDBA's および Bill Karwin's の回答を読みましたが、解決策はありません:
ROW_FORMAT=DYNAMIC
に変更するだけでは十分ではありません。テーブルには、最大サイズを超えるインラインUTF-8 VARCHAR
フィールドだけが含まれているためです。私はプラグイン開発者にエラーを報告し、彼らがテーブルをすぐに修正することを望んでいますが、それまでの間、私はこの無法者テーブルで立ち往生しています。
だから質問は:
MySQL 5.6からアップグレードしました。私はDYNAMIC
およびCOMPRESSED
形式を試しましたが、うまくいきませんでした。 integer + varcharフィールドのサイズを計算しました。合計は17,059バイトなので、この方法で成功することはできません。
プラグインは フォトギャラリー と呼ばれ、障害のあるテーブルはwp_bwg_theme
です。
SET GLOBAL innodb_file_format=Barracuda;
SET GLOBAL innodb_file_per_table=ON;
ALTER TABLE tbl ROW_FORMAT=DYNAMIC; -- Or COMPRESSED
それが5.6で必要だったと思います。 Barracudaとfile_per_tableは5.7のデフォルトであるため、これのほとんどはなくなります。ただし、アップグレードによってテーブルAntelopeが残されたり、file_per_tableが残されなかったりする場合があります。
したがって、これら3つのコマンドをスローして、問題が完全に「修正」されるかどうかを確認することをお勧めします。 (ええ、ある種のバックアップを最初にどこかに保管してください。)
あなたはutf8に言及しました。おそらくあなたもutf8mb4が欲しいですか?
ALTER TABLE tbl CONVERT TO utf8mb4;
(レプリケーションが問題になるかどうかは今はわかりません。おそらく上記の変更後は、5.7スレーブでは問題にならないでしょう。)
編集
しかし...(5.7の)デフォルトであることはではないは、アップグレード後に存在するファイルのそれらの値を得たことを意味します。
覗く information_schema.INNODB_SYS_TABLES
はfile_format
およびrow_format
です。列space
は、値が0より大きい場合にfile_per_tableを示します。
この問題に対処する抜本的な方法:InnoDBページサイズを変更します。デフォルトは16KBですが、32KBも可能です。私が間違っていない場合は、システム上のallテーブルを新しいページサイズに変換する必要があるため、それは重要な作業であり、その他の影響がある可能性があります。
VARCHAR
/DYNAMIC
でのCOMPRESSED
の処理
文字列がレコードの他のブロックに保存されるのに対して、レコードのメイン部分に保存されるのはいつですか?
「レコードが大きすぎます」:行が長すぎる場合、最も長い列がページ外ストレージに格納されます。つまり、行全体の構成によっては、列が完全にページ外になる場合もあれば、ページ上になる場合もあります。
VARCHAR
とTEXT
とBLOB
は、DYNAMIC
またはCOMPRESSED
と同じように処理されます。
DYNAMIC
形式は、長いデータ値の一部がページ外に格納される場合、通常はすべての値をページ外( "all or none")に格納するのが最も効率的であるという考えに基づいています。
COMPRESSED
= DYNAMIC
+圧縮。 KEY_BLOCK_SIZE
は、クラスター化インデックスに格納される列データの量、およびオーバーフローページに配置される量を制御します。
5.7参照 および 古い、より詳細、説明 ;その他のページ。
Rick Jamesの回答(彼の+1) を読んだ後、これに追加するのは、ROW_FORMAT=COMPRESSED
を使用する場合は、より大きなInnoDBバッファープールを構成することだけです。どうして ?
私は以前の投稿 innodb_file_format Barracuda で、アクセスするページの解凍に対応するためにバッファプールのサイズをどのように増やす必要があるかについて述べました。
自分の投稿 ...から盗用.
key_block_size=8
[.____を使用して圧縮を実行しました。]8
は50.00%
/16
です50.00%
/8G
は4G
ですinnodb_buffer_pool_size
を12G
にレイズします(8G
+ 4G
)key_block_size=4
[.____を使用して圧縮を実行しました。]4
は25.00%
/16
です25.00%
/8G
は2G
ですinnodb_buffer_pool_size
を10G
にレイズします(8G
+ 2G
)key_block_size=2
[.____を使用して圧縮を実行しました。]2
は12.50%
/16
です12.50%
/8G
は1G
ですinnodb_buffer_pool_size
を9G
にレイズします(8G
+ 1G
)key_block_size=1
[.____を使用して圧縮を実行しました。]1
は06.25%
/16
です06.25%
/8G
は0.5G
(512M
)ですinnodb_buffer_pool_size
を8704M
に累乗します(8G
(8192M
)+ 512M
)MORAL OF THE STORY:InnoDBバッファープールは、圧縮されたデータとインデックスページを処理するときに追加の呼吸スペースを必要とします。