DB/MariaDB

MariaDB Master-Slave 구성

Dev.Congsik 2025. 5. 29. 16:26
728x90

* 구축 환경
마스터 : 192.168.0.19:33306 (linux, docker, mariadb:10.6.21-focal)
슬레이브 : 192.168.0.19:33307 (linux, docker, mariadb:10.6.21-focal)

 


1. master 설정 후 재기동
** 도커로 mariadb 기동 시 'docker exec -it [마스터 mariadb 컨테이너명] bash'로 접속 필요

vi my.cnf (master)

[client]
default-character-set = utf8mb4

[mysql]
default-character-set = utf8mb4

[mysqldump]
default-character-set = utf8mb4

[mysqld]
character-set-server=utf8mb4
collation-server=utf8mb4_unicode_ci
skip-character-set-client-handshake
max_connections=2000
server-id = 1
log_bin = mysql-bin
log_slave_updates=1
binlog_format=ROW

#gtid_strict_mode=1
#maxscale 사용 또는 auto_failover, rejoin시 설정

 

 

1-1. mariadb 재기동

docker restart [마스터 컨테이너명]

 


2. 복제 사용자 생성
2-1. master mysql 접속

docker exec -it [마스터 컨테이너명] mysql -uroot -p[mariadb root 패스워드]

 


2-2. repl 복제 사용자 패스워드 지정

CREATE USER '[복제사용자명]'@'%' IDENTIFIED BY '[복제사용자 패스워드]';

 


2-3. 복제권한 부여

GRANT REPLICATION SLAVE ON *.* TO '[복제사용자명]'@'%';


2-4. 권한 새로고침

FLUSH PRIVILEGES;



3. nginx 중지

//nginx stop을 통해 사용자 접속 제한(매우 중요!!, 테이블 write 방지)
systemctl stop nginx;



4. 복제 시점 확인

//마스터 status 확인
show master status;
+------------------+----------+--------------+------------------+
| File             | Position | Binlog_Do_DB | Binlog_Ignore_DB |
+------------------+----------+--------------+------------------+
| mysql-bin.000001 |      328 |              |                  |
+------------------+----------+--------------+------------------+
-> File명, Position값 (반드시 기록해둘 것, 이후 5번 순서에서 사용)
-> 이 시점 이후로 테이블 write 발생 시, 마스터 백업 작업 필요함



5. slave 컨테이너 생성 후 접속

5-1. 중복 생성 방지

docker rm teamup-mariadb-slave

 


5-2. docker slave 컨테이너 생성

docker run --name teamup-mariadb-slave \
-p 33307:3306 \
-v /home/bibly/teamup/mariadb-slave/volume:/var/lib/mysql \
-v /home/bibly/teamup/mariadb-slave/conf:/etc/mysql/conf.d \
-e MARIADB_ROOT_PASSWORD=xladjqdprtm \
-d mariadb:10.6.21-focal

-> my.cnf와 같은 conf 파일은 도커 외부에서 마운트할 것!



5-3. 컨테이너 접속

docker exec -it teamup-mariadb-slave bash

 


5-4. slave my.cnf 수정

//my.cnf(slave)
[client]
default-character-set = utf8mb4

[mysql]
default-character-set = utf8mb4

[mysqldump]
default-character-set = utf8mb4

[mysqld]
character-set-server=utf8mb4
collation-server=utf8mb4_unicode_ci
skip-character-set-client-handshake
max_connections=2000
//slave만 추가
server-id=2
relay-log = relay-log
read_only = 1
log-bin=mysql-bin
binlog_format=ROW
log_slave_updates=1

#gtid_strict_mode=1
#maxscale 사용 또는 auto_failover, rejoin시 설정

 

 

4-2. slave mariadb 재기동

docker restart [slave 컨테이너명]

 

#master mariadb 로그
docker logs [master 컨테이너]
2025-06-12  5:04:03 81 [Note] Start binlog_dump to slave_server(2), pos(, 4), using_gtid(1), gtid('0-1-2850')

#slave mariadb 로그
docker logs [slave 컨테이너]
2025-06-12  5:04:03 13528 [Note] Slave I/O thread: connected to master 'repl@192.168.0.19:33306',replication starts at GTID position '0-1-2850'

-> gtid 복제설정 적용

 


5. slave mysql 접속 후 설정

//slave mysql 접속
mysql -uroot -p[패스워드]

//slave 중지(확인)
STOP SLAVE;

//복제 설정1 - (Master -> slave로 복제)
CHANGE MASTER TO
  MASTER_HOST='[마스터 ip]',
  MASTER_PORT=[마스터 port],
  MASTER_USER='[복제 사용자명]',
  MASTER_PASSWORD='[복제 사용자 패스워드]',
  MASTER_LOG_FILE='mysql-bin.000002', //3번 순서에서 기록한 File명
  MASTER_LOG_POS=6896; //3번 순서에서 기록한 Position값


//복제 설정2 - gtid 설정 시
CHANGE MASTER TO
  MASTER_HOST='[마스터 ip]',
  MASTER_PORT=[마스터 port],
  MASTER_USER='[복제 사용자명]',
  MASTER_PASSWORD='[복제 사용자 패스워드]',
  MASTER_USE_GTID=slave_pos;



5-1. slave 기동

start slave;



5-2. slave 상태 확인

show slave status\g
-> Slave_IO_Running: Yes / Slave_SQL_Running: Yes 확인



6. 데이터 삽입,조회 테스트 (가능할 경우)
//마스터 - 쓰기,수정,삭제 / 슬레이브 - 읽기전용 (일반사용자 대상, root는 모든 작업 가능)

//마스터 DB에서 테스트 데이터 삽입
MariaDB [(none)]> CREATE DATABASE test;
Query OK, 1 row affected (0.000 sec)

MariaDB [(none)]> USE test;
Database changed

MariaDB [test]> CREATE TABLE IF NOT EXISTS repl_test (id INT AUTO_INCREMENT PRIMARY KEY, created_at DATETIME);
Query OK, 0 rows affected (0.026 sec)

MariaDB [test]> INSERT INTO repl_test (created_at) VALUES (NOW());
Query OK, 1 row affected (0.010 sec)

 

//슬레이브 DB 접속 후 데이터 복제 확인
MariaDB [(none)]> SELECT * FROM test.repl_test;
+----+---------------------+
| id | created_at          |
+----+---------------------+
|  1 | 2025-05-29 02:05:50 |
+----+---------------------+
1 row in set (0.000 sec)




데이터 동기화 실패 -> 복제 재설정 시 가이드

-> 반드시 테이블 write 차단, nginx 중지 상태에서 진행할 것

1. master mysqldump 진행

docker exec [마스터 컨테이너명] \
  sh -c 'mysqldump -uroot -p[패스워드] --all-databases --single-transaction --master-data=2' \
  > [덤프파일 경로]



2. slave mariadb 데이터 초기화

docker exec -it [슬레이브 컨테이너명] bash
rm -rf /var/lib/mysql/*
exit



3. dump 파일 slave에 복사

docker cp [덤프파일 경로] [슬레이브 컨테이너명]:/master_dump.sql

 


4. slave에서 dump 적용

docker exec -it [슬레이브 컨테이너명] bash
mysql -uroot -p[패스워드] < /master_dump.sql



5. 복제지점 확인

//show master status; (마스터서버에서)
//MASTER_LOG_FILE(File), MASTER_LOG_POS(Position) 확인



6. slave에 복제 설정

//slave mysql 접속
docker exec -it [slave 컨테이너명] mysql -uroot -p[패스워드]

//복제 중지(확인)
stop slave;

//복제 설정1
CHANGE MASTER TO
  MASTER_HOST='[마스터 ip]',
  MASTER_PORT=[마스터 port],
  MASTER_USER='[복제 사용자명]',
  MASTER_PASSWORD='[복제 사용자 패스워드]',
  MASTER_LOG_FILE='mysql-bin.000002', //3번 순서에서 기록한 File명
  MASTER_LOG_POS=6896; //3번 순서에서 기록한 Position값


//복제 설정2 - gtid 설정 시
CHANGE MASTER TO
  MASTER_HOST='[마스터 ip]',
  MASTER_PORT=[마스터 port],
  MASTER_USER='[복제 사용자명]',
  MASTER_PASSWORD='[복제 사용자 패스워드]',
  MASTER_USE_GTID=slave_pos;


//복제 시작
start slave;

//복제 상태 확인
SHOW SLAVE STATUS\G
-> Slave_IO_Running: Yes / Slave_SQL_Running: Yes / Seconds_Behind_Master: 0 또는 실시간 변화
728x90