LoginSignup
2
0

More than 3 years have passed since last update.

docker-composeでmysqlコンテナーを立てて、replicationをかける(mac)

Last updated at Posted at 2021-02-02

DBレプリケーションとは

image.png
Master DBのデータがSlave DBに同期化されて、同じデータをSlave DBから確認できます。
データの安定性を確保するかつ、書き込みはMaster DB, 読み込みはSlave DBを利用してDBの負荷を下げるために使います。
(最近はMasterやSlaveなどの言葉は使わない方向に進んでいますが)

ディレクトリ構造

image.png

docker-compose.yml

docker-compose.yml
version: '3.3'

services:
  db-master:
    image: mymaster
    volumes:
      - ./mymaster/mysql-init-files/:/docker-entrypoint-initdb.d/
      - ./mymaster/mysql-config-files/:/etc/mysql/conf.d
    restart: always
    container_name: mymaster
    environment:
      - MYSQL_ALLOW_EMPTY_PASSWORD="true"
    ports:
      - '3333:3306'
    expose:
      - '3333'

  db-slave:
    image: myslave
    volumes:
      - ./myslave/mysql-init-files/:/docker-entrypoint-initdb.d/
      - ./myslave/mysql-config-files/:/etc/mysql/conf.d
    restart: always
    container_name: myslave
    environment:
      - MYSQL_ALLOW_EMPTY_PASSWORD="true"
    ports:
      - '2222:3306'
    expose:
      - '2222'

imageとしてmymasterを利用していますが、dockerfileでビルドしたものです。大した内容はありませんのでmysqlのimageを使用しても構いません。

Masterの設定

dockerfile

dockerfile
FROM mysql:5.7

EXPOSE 3306

CMD ["mysqld"]

my.cnf

[mysqld]
log-bin=mysql-bin
server-id=1

log-binはクエリを実行するとき残すログです。
server-idを1として指定します。

create.sql

create.sql
CREATE DATABASE repl;

CREATE TABLE repl.user(
  id VARCHAR(100) PRIMARY KEY,
  name VARCHAR (100)
);

create user master@'%' identified by 'master';
grant all privileges on *.* to master@'%' identified by 'master';

grant replication slave on *.* to 'slave'@'%' identified by 'slave';

重要なのは
grant replication slave on *.* to 'slave'@'%' identified by 'slave';
でSlaveからレプリケーションをかけるユーザーを作成することです。

Slave設定

dockerfile

dockerfile
FROM mysql:5.7

EXPOSE 3306

CMD ["mysqld"]

Masterと同じです。

my.cnf

[mysqld]
server-id=2
replicate-do-db='repl'

server-idを2に指定します。
レプリケーションするDBを指定します。

create.sql

create.sql
CREATE DATABASE repl;

CREATE TABLE repl.user(
  id VARCHAR(100) PRIMARY KEY,
  name VARCHAR (100)
);

create user slave@'%' identified by 'slave';
grant all privileges on repl.* to slave@'%' identified by 'slave';

レプリケーションのため、Masterと同じテーブルを作成することが必要です。

最後に、シェルスクリプトでレプリケーションを実行します。

レプリケーションの実行

init.sh

init.sh
#!/bin/sh

#make mymaster image
docker build --no-cache -t mymaster ./mymaster/

#make myslave image
docker build --no-cache -t myslave ./myslave/
docker-compose -f ./docker-compose.yml up -d --remove-orphans

sleep 15s

# macのコマンドですので、Windowsなら他のIPアドレス取得方法が必要です。
myaddress=`ipconfig getifaddr en0`
myaddress=${myaddress}

# Masterのログファイルの場所を取得します。
master_log_file=`mysql -h127.0.0.1 --port 3333 -uroot -e "show master status\G" | grep mysql-bin`
master_log_file="${master_log_file}"

re="[a-z]*-bin.[0-9]*"

if [[ ${master_log_file} =~ $re ]];then
    master_log_file=${BASH_REMATCH[0]}
fi

# Masterのポジションも取得します。
master_log_pos=`mysql -h127.0.0.1 --port 3333 -uroot -e "show master status\G" | grep Position`
master_log_pos="${master_log_pos}"

re="[0-9]+"

if [[ ${master_log_pos} =~ $re ]];then
    master_log_pos=${BASH_REMATCH[0]}
fi

query="change master to master_host='${myaddress}', master_user='slave', master_password='slave', master_log_file='${master_log_file}', master_log_pos=${master_log_pos}, master_port=3333"

mysql -h127.0.0.1 --port 2222 -uroot -e "${query}"
mysql -h127.0.0.1 --port 2222 -uroot -e "start slave"

init.shを実行するとdockerのimageをビルドして、コンテナー間のレプリケーションをかけます。
これでレプリケーションをかけたmysqlコンテナーができました。

2
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
0