HomebrewからDockerにMySQL環境を移行する

morimorihogeです。ぼちぼち開発現場でもDockerが当たり前に使われている現場が増えてきた印象です。Moby DockかわいいよMoby Dock。 Touch Bar搭載の新型MacBook Pro Retinaに移行したころに、新Macに触る良いテンションの勢いでHomebrew環境のMySQLをDockerに移行してみた時のメモです。 既にQiitaなんかでも同様の事例が多数あると思いますが、備忘録までに。 ※ずいぶん前(2016末)に途中まで下書きして寝かせてしまった内容なので、ここ最近では改善されている部分があるかもしれません(主にパフォーマンス面など) 概要 この手順は意識高いDocker勢で推奨されているData Volume Containerを使った方式ではなくVOLUMEオプションを使った方式です。利点、欠点は以下の通りなのでData Volume Containerが良い人は適宜カスタマイズしてください。 利点 MySQLのDATA_DIRやmy.cnf等の設定ファイルがMac側で直接触れるため、編集・参照しやすい データ類がMacのファイルとして存在するため、バックアップ/リストアしやすい(TimeMachine的にも相性がよさそう) 「うおーなんかよくわからんContainerばっかりになってきたから全部消すか」とかで全containerをdocker rmしてしまってもデータはMac側にあるので安心 欠点 Docker for Macは遅いという話がちょいちょい見受けられるので、速度を求める人にはつらそう。参考: Docker for Macが遅い問題をdocker-syncで解決する VOLUME接続しているのでMySQL containerのデータがDockerに閉じなくなってしまうので、コンテナ至上主義者的には許せない人がいそう 一方、以下の点についてはHomebrew環境と同様に利用可能です。 HomebrewでインストールするMySQLと同様に、localhost:3306でアクセスできる Mac自体を再起動した後も、当然普通に自動起動できる(いちいちdocker runしなくてよい) なお、基本的にここでやってることはDocker HubのMySQLオフィシャルイメージのサイトに書いてあることをやっているだけなので、特にテクい技術は使っていません。あしからず。 旧環境のMySQLをdump 普通にmysqldumpでどうぞ。僕の場合はDBが多数ありすぎたので古いものはアーカイブするために、一度個別のテーブルごとファイルに出しました。 mysqldump -uroot -p”${password}” db_1 > db_1.dump mysqldump -uroot -p”${password}” db_2 > db_2.dump mysqldump -uroot -p”${password}” db_3 > db_3.dump mysqldump -uroot -p”${password}” db_4 > db_4.dump mysqldump -uroot -p”${password}” db_5 > db_5.dump みたいなスクリプトをdump.shとかの名前で保存して mkdir backups cd backups bash ../dump.sh とかで出ます。この辺は普段からMySQL使っている人たちには今更だと思います。 旧環境のmy.cnfを持ってくる MySQLで大事なのはmy.cnfの設定です。innoDBのチューニング設定やutf8mb4対応向けのconfigなど、デフォルトのmy.cnfだと使用に耐えない部分をカスタマイズした泥臭いmy.cnfを新環境にコピーしておきます。 Docker向けのデータ領域を作成する VOLUMEオプションで接続する用のファイル置き場を作成します。 なんとなく僕は~/docker/#{サービス名}/#{VOLUMEで繋ぐディレクトリ}という感じでファイルを置くようにしているので、以下の様なディレクトリツリーでmkdirしました。 VOLUMEの接続用ディレクトリはどんな名前でも構いませんが、containerにdocker execでbash接続したとき等に迷わないのでcontainer内のどのパスに接続されているのかがある程度分かりやすい名前が良いと思います。 $ tree -L 2 ~/docker docker └── mysql ├── etc_mysql_conf.d └── var_lib_mysql 上記見てもらえればなんとなくわかるかと思いますが、これからdocker pullするmysqlというコンテナについて、 Mac側の~/docker/mysql/etc_mysql_conf.dをcontainerの/etc/mysql/conf.dに接続 Mac側の~/docker/mysql/var_lib_mysqlをcontainerの/var/lib/mysqlに接続 という形で接続していきます。 MySQLサーバコンテナを起動する というわけで、MySQLのサーバコンテナを起動します。ここで、サーバコンテナは後々よく指定することになるので–nameオプションで名前をつけると便利です。ここではmysql-serverという名前で立ち上げます。 その他、先ほど作成した~/docker/mysql以下のディレクトリに対してVOLUMEオプションで繋ぎこみ、port 3306をlocalhostに接続する設定を追加し、MySQL 5.7 containerを以下のコマンドで起動します(他のバージョンがほしい人は適宜修正して下さい)。 docker run –name mysql-server \ -v ~/docker/mysql/etc_mysql_conf.d:/etc/mysql/conf.d \ -v ~/docker/mysql/var_lib_mysql:/var/lib/mysql \ -e MYSQL_ROOT_PASSWORD=’root_password’ \ -p 3306:3306 \ -d mysql:5.7 これで、MySQLのconfig及びデータファイルはMac側のファイルシステムにそのまま置きつつMySQL containerを起動することができます。 docker run オプションに関するざっとした解説は以下の通りです。 –name : 起動したコンテナに任意の名前を付ける。この後別containerから参照するときに使うので、サービス系のcontainerには任意名を付けると良いです -v, –volume : Docker HostとContainerのファイルシステムを共有する。通常VirtualBox等でDocker HostのVMを起動している場合、Host OS側のファイルシステムはNFSやSamba共有しないと参照できないが、Docker for MacはHypervisor.frameworkを使うxhyveを利用しているので、 ホスト側Macのディレクトリをそのままvolumeオプションで繋ぐことができる。複数のvolumeを接続したい場合、例の様に複数-vオプションを付ければ良い -e, –env : containerに環境変数を割り当てることができる。公開されているDocker Imageで、パスワードやアクセスキーなど、コンテナ起動時に設定したい情報は-eオプションで設定するように作られていることが多い -p, –publish : containerのポートをDocker Hostのポートにbindingし、Docker Host側からcontainerにポート経由でアクセスできるようにする。Docker Host側(今回はMac)のwell knownポートを使う場合はroot権限が必要 -d : 引数を持たないオプション。コンテナをバックグラウンド実行する。起動しっぱなしになるサービス系のコンテナではこれを付けると良い これであとはlocalhost:3306にアクセスすればMySQLにアクセスすることができます。 サーバコンテナを自動起動させる 開発機の場合、カジュアルに再起動したりするため、毎回docker runコマンドを実行するのはおっくうです。そこで、–restart alwaysオプションを付けます。 このオプションを付けることで、Docker Daemonが起動したら直ちに当該containerが起動しますし、何らかの原因でcontainerが終了しても勝手に再起動してきます。 containerの設定中にこのオプションを付けてしまうと起動 -> 停止を繰り返して面倒なことになりますが、ある程度安定して実行できる環境整備が終わったらこのオプションを付ければ、再起動しても勝手にサービスが上がってくるようになるのでDockerを意識しないで使うことができるようになります。 サーバコンテナの設定を確認する トラブルシューティング用途でcontainerの設定を見たくなることがありますが、そんなときはdocker execを使い、 docker exec -it mysql-server bash とすればシェルが取れます。-itオプションを忘れないようにしましょう。 バックアップを取り込む 無事安定してMySQLコンテナが起動するようになったら、取り込みを行いましょう。ここからは既にlocalhost:3306で普通にMySQL接続できる状態になっていますので、GUIツールなどに慣れてる人はTCP経由で取り込むことも可能です。 いや、俺は最後までDockerでやるんだ!という人は、 … Continue reading HomebrewからDockerにMySQL環境を移行する