SlideShare a Scribd company logo
MySQLを割と⼀⼈で300台管理する
技術
2017/09/05
yoku0825
db tech showcase 2017
\こんにちは/
yoku0825の中の⼈@GMOメディア
Oracle ACE-
でもオラクれない-
そしてポスグれない-
ちょっとマイエスキューエる-
⽣息域
Twitter: @yoku0825-
Blog: ⽇々の覚書-
MyNA ML: ⽇本MySQLユーザ会-
MySQL Casualʼs Slack: MySQL Casual-
1/63
MySQLが増えやすいわけ
フリーソフトウェア(GPLv2)
利⽤するのにお⾦はかからない-
データの複製がしやすい
遠い昔(3.23.15, 2000/05)からレプリケーションがある-
詰まったらSQLチューニングより増やして何とかする、という世論も
あったり
-
MySQL⼤好きなおじさんガイル
σ(゚∀゚ )-
2/63
結果
3/63
311個の
mysqld
(2017/08現在)
4/63
たぶんここまでは
そんなに数が多い
⽅ではない…
5/63
が
6/63
GMOメディア
7/63
会社の数だけDBのデザインパターンがある
(c) インターネット界隈のことを調べるお
http://takanoridayo.blog.shinobi.jp/Entry/426/
8/63
サービスの種類が 無駄に 多い
9/63
MySQLの⾯倒を⾒る体制
DBAチーム
現在4⼈体制
PostgreSQL, Oracleの⾯倒を⾒ている⼈もいる
ワーストの時期では稼働できたのが俺⼀⼈だった
最近チームがだいぶ変わった
10/63
MySQLの⾯倒を⾒る #とは
障害対応
MySQLに関するサポート
DBに特化した(広義の)インフラデザイン
DBに特化したショット作業
11/63
MySQLの⾯倒を⾒る #とは
障害対応
DBサーバーのシェルを使えるのはDBチームとインフラチームのみ-
AP起因でMySQLがぶん回ったりするものを含む-
H/W交換はお任せ、OSを再セットアップしてからが出番-
MySQLに関するサポート
「新しい開発環境のDBがほしいんですけど」-
「APサーバーが追加されたからユーザー追加してほしいんだけど」-
「クエリー遅いんですけど」-
12/63
MySQLの⾯倒を⾒る #とは
DBに特化した(広義の)インフラデザイン
バックアップの頻度, 保管先, ..etc. + その実装-
監視, リソースモニタリング, ..etc. + その実装-
mikasafabric for MySQL + MySQL Router-
メジャーバージョンアップの検証とか、Percona Serverとか
MariaDBとか
-
DBに特化したショット作業
吊るしの ALTER TABLE 以外を使ったテーブル定義の更新
< 5.6 だったり、テーブルが⼤きすぎてレプリケーションが詰まったりするケース
-
スロークエリーチューニング-
マイナーバージョンアップ-
13/63
ウッ…
14/63
無理
15/63
MySQLを割と
⼀⼈で300台⾯
倒を⾒るために
16/63
省⼒化
ただし悲惨な状態になってから
⼿を付けたものだけではない
17/63
省⼒化
管理台帳
死活(︖)監視
ログ監視
コンフィグテンプレートエンジン
スキーマテスト
mikasafabric for MySQL
後追いできるリソース監視
あとこまごましたこと
18/63
管理台帳
ここにExcelの台帳があるじゃろ︖
会社の外から⾒られないじゃろ︖-
スプレッドシートに変わるじゃろ︖
結局開くのに時間がかかるわ、他の機能に使いまわせないわ、古い情
報(マイナーバージョンアップしたのに古いバージョン番号とか)が
載ってたりするじゃろ︖
-
ある⽇それが嫌になったんじゃ
19/63
管理台帳
データはMySQLに保管
実体はPerlのスクリプトで、300インスタンスのMySQLに
次々ログインして SHOW VARIABLES とか SHOW SLAVE STATUS
とか諸々引っこ抜いてくる
定期的(2/week)に登録済のmysqldをチェック
バージョンアップ、レプリケーションの構成変更など、勝⼿に情報を
更新
-
マスター切り替えがあっても定期実⾏スクリプトを⼿で流し直してや
るだけで台帳が最新に
-
退役したサーバーは定期実⾏時にエラーになるので遅くとも1週間で
反映される
-
前回から変更されたサーバー変数やアカウントがあればチェックでき
る
-
20/63
管理台帳
21/63
管理台帳
⼀番気に⼊ってるのは、MySQLにデータが保管されている
「だけ」なので、mysqlコマンドラインクライアントでデー
タが引っこ抜けてパイプできること
mysql -e "SELECT * FROM instance_list" | grep ホスト名 とかす
ればWHERE句すら組み⽴てなくていい…︕
-
勝⼿にタブセパレートになるので、コメントに空⽩⽂字があっても
awkと相性がいい
pssh や tmux を使ったマルチペインのオペレーションがやりやすい
-
これができたおかげでバックアップスクリプトとか⾊々連携できた-
22/63
死活(︖)監視
⼿数が少ない時はあんまりプロアクティブに対応できない
リアクティブ対応で可能な限り拾えるように
即対応しなくていいものをアラートにしない-
いずれ障害になるであろうものは早めにアラートにする-
23/63
死活(︖)監視
ウチではNagiosが主流、ところによりZabbix
これ、監視サーバーの登録は他のチームなのでその辺の⾃動
化は彼らに任せておくとして
「監視項目の充実」と「監視項目の差異の吸収」
24/63
死活(︖)監視
Nagiosのmonitoring-pluginsの監視項目
mysql̲real̲connect
接続できたってMySQLが息してないことはいくらでもある…
-
SHOW SLAVE STATUS
Slave̲IO̲Running, Slave̲SQL̲Running, Seconds̲Behind̲Master
ただしオプション指定、マスターに向けてオプション指定するとCRITICALになる
マスターをごりごり切り替えるスタイルには不向きすぎる
-
25/63
アドオンした死活(︖)監視
SHOW PROCESSLIST
バックグラウンド以外で⻑時間動きっぱなしのクエリーがあれば検知
暴⾛SELECTでバッファプールを⾷い荒らす奴とか
Mroongaがクラッシュしてロックのタイムアウトが設定できなかった頃役に⽴った
-
AUTO_INCREMENT なカラムの使⽤量
あふれると即死なわりに意外と監視されていない-
オススメ-
information_schema.tables と information_schema.columns を
JOIN して得る
sys.schema_auto_increment_columns なら⼀発で取れる
-
26/63
アドオンした死活(︖)監視
SHOW STATUS, SHOW VARIABLES
Threads_connected / max_connections を監視
100%になると当然 Too many connections
Percona Serverだとエラーログに出るんだけど
監視ユーザーは Super 持ちなことが多くて意外と気付かない
-
read_only
マスターの場合はOFFであるべきで
スレーブの場合はONであるべき
意外とうっかりミスが拾えていい
-
27/63
アドオンした死活(︖)監視
SHOW SLAVE STATUS のMulti-Source Replication対応
意外と対応されてなかった。。-
マスター、スレーブの⾃動判定
胸に⼿を当てて考えてみたら SHOW SLAVE STATUS の出⼒結果の有無で
判断してる
-
じゃあスクリプトにもそれやらせればいいんじゃないか-
28/63
アドオンした死活(︖)監視
問題があった時のログを詳細に残す
WARNING, CRITICALならその時の⽣ログ(判定につかったステート
メントの結果の戻り)をそのままsyslogに吐かせる
-
これはNagiosの制限が悪いのだ…-
Songmu/horenso も便利-
See also, 後追いできるリソース監視
29/63
死活(︖)監視を充実させると
多少雑にサイジングしてもワーニングのうちに回収できるケ
ースが増える
サイジングにかける時間を減らせる-
予め必要そうな情報を残すようにしておく
障害 ⇒ 再現待ち ⇒ 情報収集 ⇒ 対処 のサイクルを短くする-
⼀度踏んだ轍をどんどん追加すると起こったあとに対処する
よりもよっぽど楽
30/63
ログ監視
エラーログを監視しているところは少ない(俺調べ)
が、まあ拾っておくと幸せになれるものもいくつかある
フィルタリングして即Slackに放り投げているので、ポーリング監視
に⽐べてレスポンスは圧倒的に速い
-
31/63
ログ監視
[Note] Slave: received end packet from server due to
dump thread being killed on master
server̲uuidカブりとかで出るやつ(I/Oスレッドが無限に再起動する
やつ)
-
mysqld_safe Number of processes running now: 0
OOM Killerに亭主を殺されたり、SEGVでmysqldが死んだりした時は
まずこれが出る。mysqld̲safeを使ってると瞬間的に再起動されち
ゃってNagiosに引っかからないことがあるので。
-
[Warning] Unsafe statement written to the binary log
using statement format since BINLOG_FORMAT =
STATEMENT.
binlog_format = STATEMENT でレプリケーションアンセーフな関数使
っちゃった時に
-
今はもう binlog_format = STATEMENT 撲滅したので⼆度と出ることは
ないような気もする
-
32/63
ログ監視
33/63
ログ監視
しばしば「おう、お前こんなログ吐くのな」というものと出
会える
⼈間、思いも⾄らないものは監視できないけど、MySQLが吐くログの
うち害がないもの以外…という条件で通知させていると稀によくある
-
フィルタリングの仕組みを合わせて整備しておかないとあっという間
にあふれる
-
mysqld̲safeだけならかなり前から syslog オプションがあ
るのでそっちで拾うのもいい
34/63
コンフィグテンプレートエンジン
MySQL 8.0.3でInnoDB関連のパラメーターをある程度⾃動
で設定する innodb-dedicated-server が導⼊されるらしいで
すが
よく考えればコンフィグは⾃動でほげっているので今とそん
なに変わることはないのであった
今Perlで書いてるんだけどよく考えればこういうのPHPうっ
てつけなんじゃ
35/63
コンフィグテンプレートエンジン
<?php
$opt= getopt("", array("datadir:", "basedir:", "tmpdir:", "slave
", "port:"));
$ipaddr= getHostByName(getHostName());
$server_id= ip2long($ipaddr) & 65535;
$memsize_kb= exec("head -1 /proc/meminfo | awk '{print $2}'");
?>
[mysqld]
..
server-id= <?=$server_id?>
<?= isset($opt["slave"]) ? "read_only" : ""?>
report-host= <?=gethostname()?>
innodb_buffer_pool_size= <?=(int) ($memsize_kb * 0.6)?>K
innodb_log_file_size= <?=(int) ($memsize_kb * 0.6 * 0.2)?>K
..
36/63
コンフィグテンプレートエンジン
メジャーバージョン単位でテンプレートを作っておく
罠いパラメーターは⼀度回避すれば⼆度と⾷らわない-
パラメーター名の変更とかに追従できる-
RC2になったら8.0のテンプレートも作ろうかな-
凝ったことはしない
職⼈芸が必要そうなところとかまで⾃動⼊⼒しようとするとテストと
か死ぬ
-
今まで⼿⼊⼒してたものの8割カバーできれば⼗⼆分
37/63
コンフィグテンプレートエンジン
report-host
[mysql] セクションの prompt
server-id
各種ファイル名のパスとか
やろうやろうと思っていたメモリー関連のサイジングもそろ
そろ⼿を付けたい
38/63
スキーマテスト
「ちゃんとFKを張りましょう」
「全てのカラムにNOT NULLをつけて正規形にしてLEFT
JOINで表現しましょう」
「命名規則はこうです」
39/63
スキーマテスト
「アイエエエエエエ︕︖ FKナイ︕︖ ナンデ︕︖」
あるいは「なんでここ ON DELETE CASCADE になってんの」-
消えちゃったじゃん…-
NULLABLEなカラム
_⼈⼈⼈⼈⼈⼈_
> PKがない <
 ̄Y^Y^Y^Y^Y^Y ̄
40/63
スキーマテスト
「ちゃんとFKを張りましょう」
「全てのカラムにNOT NULLをつけて正規形にしてLEFT
JOINで表現しましょう」
「命名規則はこうです」
…とちゃんと合意が取れてても、typoだったりうっかりだっ
たりってことはある
41/63
スキーマテスト
アプリのCIの中に「DBのスキーマをリストアし、スキーマ
を評価する」テストを追加
リストア先はDockerコンテナ、CIのたびに1コンテナ起動してテスト
が終わると停⽌する
-
information_schema の tables, columns, statistics を⼒押
しする
変わりどころでは key_column_usage, referential_constraints あた
りでFKのルールも評価する
-
名前空間のルールを決めておくと機械的に評価が可能
同じ名前のカラムは原則FKが張ってある、とか-
ルールから逸脱した部分だけ書けばいい-
42/63
スキーマテスト
webapp/
|-- database
| `-- core
| |-- init.sql
| `-- schema.sql
|-- gradle
|-- lib
`-- src
|-- e2e_test
| |-- screenshot
| `-- test
|-- integration_test
| |-- groovy
| |-- java
| `-- resources
|-- main
| |-- frontend
| |-- java
| |-- public
| |-- resources
| `-- templates
`-- test
|-- groovy
`-- resources
43/63
mikasafabric for MySQL
1つのシステムをロードバランサ、スイッチ、サーバ、
ミドルウェア、ログ集約サーバなど完全に冗⻑化してお
き、1週間毎に冗⻑化されたシステム、A、Bをそれぞ
れ⼊れ替える。
式年遷宮Infrastracture · さよならインターネット
(c) kenjiskywalker-
44/63
mikasafabric for MySQL
マスターとスレーブが気軽に⼊れ替えられる構成
アプリケーションからは127.0.0.1のmysqlrouterに接続しているよ
うにしか⾒えない
-
mysqlrouterから本物のマスター/スレーブにルーティングされるの
で、アプリケーションからは透過的にフェイルオーバーできる
-
⼿動のpromoteなら2〜3秒でスイッチオーバーが完了する-
スレーブをバージョンアップ ⇒ スイッチオーバー ⇒ スレーブになっ
たもともとのマスターをバージョンアップ
-
45/63
mikasafabric for MySQL
ap01
mysqlrouter
AP
127.0.0.1:3306
ap02
mysqlrouter
AP
fabric-host
mysqlfabric
mysqld
構成情報
db01
mysqld
db02
mysqld
死活監視&Failover
マスター問い合わせ
127.0.0.1:3306
46/63
mikasafabric for MySQL
もともとは Master/Slave 1台ずつでSlaveがホットスタン
バイ(=PXCやInnoDB Clusterよりも規模が⼩さいHA構成)
のやつを管理するためにMySQL Fabricにパッチを当ててい
た
現在、最⼤でフツーのAsync Mater/Slave 構成20台くらい
をさばかせている
負荷が⾼い環境だと深刻なファイルディスクリプターリーク
があってだな…(Python詳しい⼈誰か)
「datadirをtypoした︕」とかしょーもない理由でMySQLを
再起動できる快感
47/63
後追いできるリソース監視
基本はCPU使⽤率やアプリ側の監視でスタートするけど
調査の過程で「あー、この項目のポーリングしてればよかっ
た」ってことがよくある
かといって常⽇頃⾒るわけでもないので、わざわざ収集しておくのも
結構しんどい
-
See also, アドオンした死活(︖)監視 ⇒ 問題があった時
のログを詳細に残す
48/63
PMP for Cacti
49/63
PMM
50/63
現在の状況
51/63
後追いできるリソース監視
yoku0825/anemoeater
スローログを遡って分割して投⼊することでグラフを表⽰
Dockerコンテナと組み合わせて「⾒たくなったら起動」「⾒終わった
ら停⽌」の運⽤レス可視化
-
スローログさえ残っていればいつでも任意の時点のグラフを
⾒られる
52/63
後追いできるリソース監視
ytkit/yt-binlog-groupby · yoku0825/ytkit
バイナリーログをGROUP BYするためのスクリプト(time, table,
statement)に対応
-
バイナリーログさえ残っていればいつでも任意の時間帯でどのテーブ
ルがホットスポットになっていたかわかる
-
53/63
後追いできるリソース監視
あと SHOW GLOBAL STATUS, SHOW GRANTS, SHOW VARIABLES,
SHOW TABLE STATUS とか
p_s.events_statements_summary_by_digest とか取って保管
してみるとかしてる
普段はただデータを保管(MySQLに突っ込んでる)するだ
けで、⾒たくなったら re:dashのコンテナー起動してSQL叩
いてグラフにする
拡張がすごく楽(SELECTで値を取ってINSERTするだけだ
から)
実際に⾒たくなった時に「どう⾒るか」を考える-
54/63
たとえばクエリーダイジェストごとのrows̲examined
55/63
たとえばテーブルサイズ
56/63
あとこまごましたこと
バイナリーログ, リレーログ, エラーログ, スローログの名前
は指定する
ホスト名に依存させない-
ファイル名を固定することで、psshやtmuxとの相性が良くなって効
率アップ
-
57/63
あとこまごましたこと
⼀括でログインして tail -f とかできる
58/63
あとこまごましたこと
テーブルサイズは⼤きくしすぎない, 無駄なスレーブを作ら
ない
ログテーブル、パーティショニングじゃなくてテーブルごと、⽉ごと
にテーブル分けるのだってまだまだメリットがある
-
テーブルサイズが⼗分⼩さくて数秒で終わるなら、あるいは数⼗分で
も遅れていいスレーブだけなら、サービスを⽌めずにInnoDBのオン
ラインALTER TABLEで本当にオンライン
-
59/63
あとこまごましたこと
バージョンはなるべく新しい⽅がいい
特にモニタリング⽅⾯-
4.0とか5.0とかもう耐えられない
ざくざくサポートを切ると作りこみが楽
-
OSのバージョンも統⼀できるとコマンド違わなくて楽-
60/63
まとめ
管理台帳
死活(︖)監視
ログ監視
コンフィグテンプレートエンジン
スキーマテスト
mikasafabric for MySQL
後追いできるリソース監視
あとこまごましたこと
61/63
⼿を抜くため
の⼿間を惜し
まない
62/63
Questions
and/or
Suggestions?
63/63

More Related Content

MySQLを割と一人で300台管理する技術