Edited at

docker-compose+MySQL5.7(8.0も)+初期化+永続化


概要

dockerは業務経験あったけどdocker-compose使ったことないしMySQLの環境構築も慣れてなかったのでやってみました。

で、どうせなら初期データもあったほうがいいよね!といった感じです。

こうすればできる!というところを目指してやった備忘録として残します。


環境


  • Mac OSX HighSierra

  • docker


    • version 18.09.0, build 4d60db4



  • docker-compose


    • version 1.23.1, build b02f1306



  • docker, docker-composeについてはメジャーバージョンが変わらなければ基本大丈夫かと思います。多分・・・


解説すること、しないこと


  • すること


    • 表題のことをする手順



  • しないこと


    • MySQL/docker/docker-compose環境構築の方法や仕組みなど




手順


  • 環境構築します。mysql:5.7のdockerイメージもpullしておきます。

  • docker-composeを実行するディレクトリを作成し、docker-compose.ymlを作ります


docker-compose.yml

version: '3' # 多分なんでもいいと思います

services:
db:
image: mysql:5.7
ports:
- "3306:3306"
volumes:
# 初期データを投入するSQLが格納されているdir
- ./db/mysql_init:/docker-entrypoint-initdb.d
# 永続化するときにマウントするdir
- ./db/mysql_data:/var/lib/mysql
environment:
MYSQL_ROOT_PASSWORD: root
MYSQL_USER: test
MYSQL_PASSWORD: test


  • volumesでマウントするディレクトリを、docker-compose.ymlのレイヤー下に作成します。こんな構造のディレクトリになると思います。

(docker-compose実行dir)

┗ docker-compose.yml
┗ db/
┗ mysql_init/
┗ mysql_data/


  • 作成した mysql_init にSQLファイルを作成します。


1_create.sql

create database sample;

use sample;

CREATE TABLE users (
(ご自由に)
);




  • docker compose up -d で起動しましょう。接続できるようになっていますので、mysqlのcliなりworkbenchなりで確認してみてください。


解説

volumes の役割を理解することが今回の鍵とみています。

今回はdockerコンテナ内の二つのディレクトリを、ローカルのディレクトリにマウントさせることで初期化と永続化を実現しています。



  • /docker-entrypoint-initdb.d


    • dockerコンテナとして起動したときに、ここにあるSQL文を実行してくれるようです。

    • 今回はやりませんでしたが、shファイルの実行もしてくれます。




  • /var/lib/mysql


    • 名前がもうモロですが、コンテナのmysqlのシステムファイルがたくさん詰まっています。

    • これをvolumesでローカルのディレクトリからバインドすることで、同じ構成のファイルがローカルにも作成されます(今回の構成では、./db/mysql_dataが該当します)。




さいごに


  • 今回は業務システムのローカル環境を作る目的でやったのでMySQL5.7でやりましたがMySQL8.xにも近々向き合わねばなるまい・・・


おまけ


  • ・・・ということでMySQL8.0でも同じことをやってみました。

  • まずdocker-compose.ymlimageをMySQL8.0のものに直し、volumesに次の行を追加します。


docker-compose.yml

            - ./db/mysql_conf/:/etc/mysql/conf.d



  • 次に、追加したvolumesに対応するローカルディレクトリ(上記例では、./db/mysql_confが該当します)に次のファイル置きます。


default_authentication.cnf

[mysqld]

default_authentication_plugin=mysql_native_password


  • MySQL8.0以降では接続時の認証方式が変更になっているため、このファイルが必要になるようです。この事実や、対策方法はいろいろなところで紹介されていますが、一応ここでも載せておきます。