Ossian Story
article thumbnail
Published 2017. 11. 8. 17:47
[DB] Redis Sentinel 구성 [DB]/Redis

[DB] Redis Sentinel 구성


Redis Sentinel


Redis Sentinel은 Redis 서버에 대한 상태를 감시합니다.

Redis Master에 장애가 발생할 경우 Redis Slave를 Redis Master로 자동으로 변경하여 FailOver에 대처합니다.


Redis Sentinel의 작동방식은 Redis 상태체크 시 다수결에 의해 결정됩니다. 따라서 Redis Sentinel은 홀수로 구성해야 합니다.


예를 들어 "Redis Sentinel-1"이 Redis-Master가 응답이 없다고 "Sentinel-2"와 "Redis Sentinel-3"에게 알립니다.

만약 "Redis Sentinel-2"와 "Redis Sentinel-3"이 Redis-Master와 응답에 성공했다면, Redis-Master의 상태를 정상으로 판단합니다.

반면 "Redis Sentinel-2"와 "Redis Sentinel-3"이 Redis-Master와 응답에 실패했다면, Redis-Master의 상태를 장애로 판단하고

Redis-Slave를 Redis-Master로 변경합니다.


위 처럼 "Redis Sentinel-1"이 Redis-Master가 응답이 없다고 알린 상태를 SDown(Subjective Down)이라 하고

"Redis Sentinel-2"와 "Redis Sentinel-3"이 Redis-Master와 응답에 실패하여 Redis-Master를 장애로 판단한 상태를 ODown(Objective Down)라고 합니다.


Redis Sentinel 구성


Redis Sentinel은 Redis가 실행중인 서버에서 구성해도 되고, 독립적으로 구성해도 됩니다.

Redis가 실행중인 동일한 서버에서 Redis Sentinel을 구성 시 Redis Port와 다른 Port만 사용하면 됩니다.

다만 위에서 언급된 내용처럼 Sentinel을 홀수로 구성해야 원활한 FailOver 처리가 가능합니다.



Redis Sentinel Configuration


Redis Sentinel Configuration 파일은 Redis를 설치했던 디렉토리에 있습니다.

아래의 설정 및 실행은 3대의 Redis Sentinel에서 모두 설정 및 실행해 주어야 합니다.

Redis Sentinel은 Redis-Slave 3대에 구성하였습니다.

$> cd redis-4.0.2
$> pwd
/home/ossian/redis-4.0.2
 
$> ls -l
total 280
-rw-rw-r--.  1 root root 131381 Sep 21 14:12 00-RELEASENOTES
-rw-rw-r--.  1 root root     53 Sep 21 14:12 BUGS
-rw-rw-r--.  1 root root   1815 Sep 21 14:12 CONTRIBUTING
-rw-rw-r--.  1 root root   1487 Sep 21 14:12 COPYING
drwxrwxr-x.  6 root root    192 Nov  7 15:19 deps
-rw-rw-r--.  1 root root     11 Sep 21 14:12 INSTALL
-rw-rw-r--.  1 root root    151 Sep 21 14:12 Makefile
-rw-rw-r--.  1 root root   4223 Sep 21 14:12 MANIFESTO
-rw-rw-r--.  1 root root  20530 Sep 21 14:12 README.md
-rw-rw-r--.  1 root root  57764 Sep 21 14:12 redis.conf
-rwxrwxr-x.  1 root root    271 Sep 21 14:12 runtest
-rwxrwxr-x.  1 root root    280 Sep 21 14:12 runtest-cluster
-rwxrwxr-x.  1 root root    281 Sep 21 14:12 runtest-sentinel
-rw-rw-r--.  1 root root   7606 Sep 21 14:12 sentinel.conf
drwxrwxr-x.  3 root root   8192 Nov  7 15:20 src
drwxrwxr-x. 10 root root    167 Sep 21 14:12 tests
drwxrwxr-x.  8 root root   4096 Sep 21 14:12 utils



원본 파일은 유지하고 "sentinel.conf" 파일을 Redis의 Config가 위치한 디렉토리로 복사합니다.

$> sudo cp sentinel.conf /etc/redis/stn26379.conf



sentinel.conf 파일이 복사된 디렉토리로 이동합니다.

$> cd /etc/redis/



stn26379.conf 파일을 열어 수정합니다.

$> sudo vi stn26379.conf



bind의 주석을 삭제 후 Sentinel Server들의 IP 또는  0.0.0.0으로 변경합니다.

보안을 위해서는 0.0.0.0 보다 Sentinel Server들의 IP를 입력하는 것이 좋습니다. 

# Before doing that MAKE SURE the instance is protected from the outside
# world via firewalling or other means.
#
# For example you may use one of the following:
#
 bind 0.0.0.0   # 주석을 삭제 후 Sentinel server들의 IP 또는 0.0.0.0으로 변경합니다.
#
# protected-mode no



Sentinel의 실행 Port를 확인합니다. 기본 Port를 사용할 예정임에 따라 따로 변경하지 않습니다.

만약 실행 Port를 변경하고자 할 경우 해당 Port값을 변경하면 됩니다. 

# port <sentinel-port>
# The port that this sentinel instance will run on
port 26379
 
# sentinel announce-ip <ip>



Redis Master에 대한 정보를 입력합니다.

맨 마지막에 있는 숫자 "2"는 위에서 말씀드린 Sentinel Server 몇 대가 SDown 상태로 판단할 때 Redis-Master를 ODown으로 판단할 것인가?

에 대한 숫자 값입니다. 이 숫자 값을 "quorum"이라고 합니다.


현재 Redis Sentinel Server가 3대가 구성되어 있고 이중 2대의 Sentinel Server가 Redis-Master를 SDown상태로 판단하면 ODown 상태로 판단하여

Redis-Slave를 Redis-Master로 변경합니다.


만약 Redis Sentinel Server가 3대인데 "quorum" 값을 4로 설정하였을 경우 FailOver가 되지 않습니다.

# Also note that the configuration file is rewritten when a
# slave is promoted to master.
#
# Note: master name should not include special characters or spaces.
# The valid charset is A-z 0-9 and the three characters ".-_".
sentinel monitor mymaster 10.146.0.8 6379 2
 
# sentinel auth-pass <master-name> <password>
#
# Set the password to use to authenticate with the master and slaves.
# Useful if there is a password set in the Redis instances to monitor.



Redis Sentinel이 Redis-Master와 몇초동안 응답에 실패했을 때 SDown 상태로 판단할 것인가?에 대한 시간 설정입니다.

아래의 값은 5초로 설정된 값입니다.

# Number of milliseconds the master (or any attached slave or sentinel) should
# be unreachable (as in, not acceptable reply to PING, continuously, for the
# specified period) in order to consider it in S_DOWN state (Subjectively
# Down).
#
# Default is 30 seconds.
sentinel down-after-milliseconds mymaster 5000
 
# sentinel parallel-syncs <master-name> <numslaves>



Redis-Master에 장애가 발생했을 시 Redis Slave는 새로운 Redis-Master의 데이터를 Sync 해야합니다.

이 때 새로운 Redis-Master에 Redis-Slave가 동시에 몇대를 접속할 수 있게 할 것인가?에 대한 설정입니다.

여러 대의 Redis-Slave가 동시의 Redis-Master로 접속 시 과부하가 발생될 수 있으므로 1대씩 순차적으로 Redis-Slave가 접속할 수 있도록

설정된 값입니다.

# How many slaves we can reconfigure to point to the new slave simultaneously
# during the failover. Use a low number if you use the slaves to serve query
# to avoid that all the slaves will be unreachable at about the same
# time while performing the synchronization with the master.
sentinel parallel-syncs mymaster 1
 
# sentinel failover-timeout <master-name> <milliseconds>



Failover 시 3분이내에 Failover가 처리가 완료되면 Redis-Slave를 Redis-Master로 변환처리 합니다.

# - The maximum time a failover in progress waits for all the slaves to be
#   reconfigured as slaves of the new master. However even after this time
#   the slaves will be reconfigured by the Sentinels anyway, but not with
#   the exact parallel-syncs progression as specified.
#
# Default is 3 minutes.
sentinel failover-timeout mymaster 180000
 
# SCRIPTS EXECUTION




Redis Sentinel이 FailOver 시 사용될 Redis-Master / Redis-Slave의 암호를 입력합니다.

# Note that the master password is also used for slaves, so it is not
# possible to set a different password in masters and slaves instances
# if you want to be able to monitor these instances with Sentinel.
#
# However you can have Redis instances without the authentication enabled
# mixed with Redis instances requiring the authentication (as long as the
# password set is the same for all the instances requiring the password) as
# the AUTH command will have no effect in Redis instances with authentication
# switched off.
#
# Example:
#
 sentinel auth-pass mymaster mypassword #주석제거 후 Redis-Master / Redis-Slave의 암호를 입력합니다.
 
# sentinel down-after-milliseconds <master-name> <milliseconds>



맨 마지막 줄에 아래와 같이 추가하여 데몬으로 실행 할 때 참조할 수 있게 합니다.

daemonize yes
pidfile /var/run/sentinel_26379.pid
logfile /var/log/sentinel_26379.log



Redis-Master와 Redis-Slave의 암호를 Sentinel.conf에서 입력한 암호로 동일하게 변경합니다.
"[DB] Redis Replication 구성" 포스팅을 보고 설정하셨다면 이미 입력되어있을 것 입니다.
 - "masterauth" 와 "requirepass"에 Redis-Master의 암호를 입력합니다.


$> sudo vi /etc/redis/6379.conf



# If the master is password protected (using the "requirepass" configuration
# directive below) it is possible to tell the slave to authenticate before
# starting the replication synchronization process, otherwise the master will
# refuse the slave request.
#
 masterauth mypassword  # 주석 제거 후 Redis-Master의 암호를 입력합니다.
 
# When a slave loses its connection with the master, or when the replication
# is still in progress, the slave can act in two different ways:



# Warning: since Redis is pretty fast an outside user can try up to
# 150k passwords per second against a good box. This means that you should
# use a very strong password otherwise it will be very easy to break.
#
 requirepass mypassword # 주석 제거 후 Redis-Master의 암호를 입력합니다.
 
# Command renaming.





Redis Sentinel 실행 준비


Sentinel을 실행하기 위해서 Daemon 스크립트를 작성이 필요합니다.


아래의 경로에 stn_26379스크립트 파일을 생성합니다.

$> pwd
/etc/init.d
 
$> sudo vi stn_26379



아래의 내용에서 Port 번호만 변경하여 stn_26379 스크립트 파일을 작성합니다.

- 아래의 스크립트는 "http://crystalcube.co.kr/177"에서 발췌하였습니다.

#!/bin/sh
#Configurations injected by install_sentinel below.... 
 
EXEC=/usr/local/bin/redis-sentinel
CLIEXEC=/usr/local/bin/redis-cli 
PIDFILE=/var/run/sentinel_26379.pid 
CONF="/etc/redis/stn26379.conf" 
REDISPORT="26379"
 
 
case "$1" in
    start)
        if [ -f $PIDFILE ]
        then
            echo "$PIDFILE exists, process is already running or crashed" 
        else
            echo "Starting Redis Sentinel server..."
            $EXEC $CONF
        fi
        ;;
    stop)
        if [ ! -f $PIDFILE ]
        then
            echo "$PIDFILE does not exist, process is not running"
        else
            PID=$(cat $PIDFILE)
            echo "Stopping ..."
            $CLIEXEC -p $REDISPORT shutdown
            while [ -/proc/${PID} ]
            do
                echo "Waiting for Redis Sentinel to shutdown ..."
                sleep 1
            done
                echo "Redis Sentinel stopped"
        fi
        ;;
    status)
        PID=$(cat $PIDFILE)
        if [ ! -/proc/${PID} ]
        then
            echo 'Redis Sentinel is not running'
        else
            echo "Redis Sentinel is running ($PID)"
        fi
        ;;
    restart)
        $0 stop
        $0 start
        ;;
    *)
        echo "Please use start, stop, restart or status as first argument"
        ;;
esac



chmod로 "stn_26379"를 실행할 수 있도록 권한을 변경합니다.

$> sudo chmod 755 stn_26379




Redis Sentinel 실행


작성 및 권한 변경이 완료되었다면 3대의 Redis Sentinel에서 "stn_26379"를 실행합니다.

$> sudo /etc/init.d/stn_26379 start
Starting Redis Sentinel server...



아래의 명령어로 Sentinel이 정상적으로 실행되었는지 확인합니다.

$> ps -ef | grep sentinel
root      5139     1  0 02:46 ?        00:00:00 /usr/local/bin/redis-sentinel 0.0.0.0:26379 [sentinel]



"tail -n 16 /var/log/sentinel_26379.log" 명령어로 로그 확인 시 아래와 같이 정상적인 로그를 확인합니다.

$> tail -16 /var/log/sentinel_26379.log 
5304:X 09 Nov 02:59:18.412 # +sdown master mymaster 10.146.0.8 6379
5304:X 09 Nov 04:59:21.405 # User requested shutdown...
5304:X 09 Nov 04:59:21.405 * Removing the pid file.
5304:X 09 Nov 04:59:21.405 # Sentinel is now ready to exit, bye bye...
4757:X 09 Nov 04:59:31.161 # oO0OoO0OoO0Oo Redis is starting oO0OoO0OoO0Oo
4757:X 09 Nov 04:59:31.161 # Redis version=4.0.2, bits=64, commit=00000000, modified=0, pid=4757, just started
4757:X 09 Nov 04:59:31.161 # Configuration loaded
4758:X 09 Nov 04:59:31.163 * Increased maximum number of open files to 10032 (it was originally set to 1024).
4758:X 09 Nov 04:59:31.163 * Running mode=sentinel, port=26379.
4758:X 09 Nov 04:59:31.166 # Sentinel ID is 523a3124f8caba52304fc6c98113ca0e73b63967
4758:X 09 Nov 04:59:31.166 # +monitor master mymaster 10.146.0.8 6379 quorum 2
4758:X 09 Nov 04:59:31.167 * +slave slave 10.146.0.11:6379 10.146.0.11 6379 @ mymaster 10.146.0.8 6379
4758:X 09 Nov 04:59:31.169 * +slave slave 10.146.0.9:6379 10.146.0.9 6379 @ mymaster 10.146.0.8 6379
4758:X 09 Nov 04:59:31.170 * +slave slave 10.146.0.10:6379 10.146.0.10 6379 @ mymaster 10.146.0.8 6379
4758:X 09 Nov 04:59:31.814 * +sentinel sentinel 655e4ac96c52bd18528a154a6f484581a0e8e05a 10.146.0.9 26379 @ mymaster 10.146.0.8 6379
4758:X 09 Nov 04:59:34.607 * +sentinel sentinel 6f42ad5bf41de6878880870487a4690c062bd940 10.146.0.11 26379 @ mymaster 10.146.0.8 6379




Redis Sentinel 동작 확인


Sentinel 실행이 완료되었으면 Redis Master를 종료합니다.

$> sudo /etc/init.d/redis_6379 stop
Stopping ...
Redis stopped



Redis Master의 종료가 완료되었다면 Sentinel에서 Log를 확인해봅니다.

Redis Master(10.146.0.8)가 Down된 걸 Sentinel이 감지하고, 다수결의 원칙에 의하여 Redis Slave(10.146.0.9)를 새로운 마스터로 선출하여 변경처리하였습니다.

6186:X 09 Nov 05:03:39.532 # +sdown master mymaster 10.146.0.8 6379
6186:X 09 Nov 05:03:39.612 # +new-epoch 1
6186:X 09 Nov 05:03:39.613 # +vote-for-leader 6f42ad5bf41de6878880870487a4690c062bd940 1
6186:X 09 Nov 05:03:40.634 # +odown master mymaster 10.146.0.8 6379 #quorum 3/2
6186:X 09 Nov 05:03:40.634 # Next failover delay: I will not start a failover before Thu Nov  9 05:09:39 2017
6186:X 09 Nov 05:03:40.829 # +config-update-from sentinel 6f42ad5bf41de6878880870487a4690c062bd940 10.146.0.11 26379 @ mymaster 10.146.0.8 6379
6186:X 09 Nov 05:03:40.829 # +switch-master mymaster 10.146.0.8 6379 10.146.0.9 6379
6186:X 09 Nov 05:03:40.829 * +slave slave 10.146.0.10:6379 10.146.0.10 6379 @ mymaster 10.146.0.9 6379
6186:X 09 Nov 05:03:40.829 * +slave slave 10.146.0.11:6379 10.146.0.11 6379 @ mymaster 10.146.0.9 6379
6186:X 09 Nov 05:03:40.829 * +slave slave 10.146.0.8:6379 10.146.0.8 6379 @ mymaster 10.146.0.9 6379
6186:X 09 Nov 05:03:45.850 # +sdown slave 10.146.0.8:6379 10.146.0.8 6379 @ mymaster 10.146.0.9 6379



Redis-Slave-1(10.146.0.9)에서 Redis 정보를 확인하면 아래와 같이 정상적으로 Master로 작동하는 것을 확인 할 수 있습니다.

$> redis-cli -a mypassword
127.0.0.1:6379> info replication
# Replication
role:master
connected_slaves:2
slave0:ip=10.146.0.10,port=6379,state=online,offset=110258,lag=0
slave1:ip=10.146.0.11,port=6379,state=online,offset=110258,lag=1
master_replid:2e437a9af070352aede942f9a3712cfe71688a8a
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:110258
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:58717
repl_backlog_histlen:51542



기존의 Redis Master를 다시 가동하면 Sentinel에서 기존의 Redis-Master를 Redis-Slave로 변경한 로그를 확인할 수 있습니다.

4718:X 09 Nov 05:09:45.892 * +convert-to-slave slave 10.146.0.8:6379 10.146.0.8 6379 @ mymaster 10.146.0.9 6379



기존의 Redis Master에서 Redis 정보 확인 시 Slave로 작동하는 것을 확인 할 수 있습니다.

$> redis-cli -a mypassword
127.0.0.1:6379> info replication
# Replication
role:slave
master_host:10.146.0.9
master_port:6379
master_link_status:up
master_last_io_seconds_ago:0
master_sync_in_progress:0
slave_repl_offset:153595
slave_priority:100
slave_read_only:1
connected_slaves:0
master_replid:2e437a9af070352aede942f9a3712cfe71688a8a
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:153595
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:131170
repl_backlog_histlen:22426






참고 사이트


http://crystalcube.co.kr/177

  + Redis에 대해 자세히 알게 해주셔서 너무나 감사합니다.




'[DB] > Redis' 카테고리의 다른 글

[DB] Redis Persistance - 데이터 저장  (0) 2017.11.13
[DB] Redis + HAProxy를 활용한 FailOver 구성  (0) 2017.11.09
[DB] Redis Replication 구성  (0) 2017.11.07
[DB] Redis 설치  (0) 2017.11.06
profile

Ossian Story

@ossians