Docker上安裝Redis
阿新 • • 發佈:2021-03-18
Docker可以很方便的進行服務部署和管理,下面我們通過docker來搭建Redis的單機模式、Redis主從複製、Redis哨兵模式、Redis-Cluster模式
## 一、在Docker上安裝單機版Redis
首先需要先在伺服器上安裝docker [Docker安裝教程](https://blog.vchar.top/soft/1610330176.html) 、[Docker命令快速入門](https://blog.vchar.top/soft/1610452576.html);
### 拉取映象
```shell
docker pull redis
```
### 啟動Redis
```shell
docker run -d -v $PWD/data:/data --name redis -p 6379:6379 redis redis-server --requirepass "123456" --appendonly yes
```
啟動命令說明:
* `$PWD/data:/data` : 對映redis的data目錄到當前目錄下的data目錄
* `--requirepass` : 是設定redis的密碼
* `--appendonly yes` : 啟用持久化儲存
例如:
```shell
docker run -d -v /home/app/redis/data:/data --name redis -p 6379:6379 redis redis-server --requirepass "123456" --appendonly yes
```
如果需要使用配置檔案,則需要做個檔案對映;注意所在目錄下必須要有redis.conf這個檔案,否則將啟動失敗。
```shell
docker run -d -v /home/app/redis/data:/data -v /home/app/redis/conf:/usr/local/etc/redis --name redis -p 6379:6379 redis redis-server /usr/local/etc/redis/redis.conf
```
> redis的這個配置檔案可以到官方的這個地址上去獲取 [http://download.redis.io/redis-stable](http://download.redis.io/redis-stable)
### 啟動成功連線失敗的問題
* 如果是[阿里雲](https://www.aliyun.com/activity/daily/bestoffer?userCode=yk3sqxxe) 或者是[騰訊雲](https://cloud.tencent.com/act/cps/redirect?redirect=1062&cps_key=4fda4618fb133125079769157174b8b6&from=console) 這些雲伺服器;那麼還需要配置安全組,將redis的連線埠6379開放,否則將無法連線。
* 伺服器開啟了防火牆;這種情況需要使用命令讓防火牆開啟埠;注意啟動或關閉防火牆後docker也需要重啟才能生效;下面是常用命令:
```shell
# 檢視防火牆狀態
systemctl status firewalld
# 禁用防火牆
systemctl disable firewalld
# 開啟防火牆
systemctl start firewalld
# 關閉防火牆
systemctl stop firewalld
# 檢視已開啟的埠
firewall-cmd --zone=public --list-ports
# 新增埠
firewall-cmd --zone=public --add-port=9876/tcp --permanent
firewall-cmd --reload
```
* 其他情況:啟動有錯誤,檢視啟動日誌;redis綁定了埠,導致只有本地可以訪問;
## 二、在Docker上搭建Redis主從複製
Redis主從複製模式就是採用讀寫分離的模式,因為通常讀取資料的時候比較多,寫入資料的時候少以此來提高效能;但是一旦主節點掛了,整個叢集就只能提供讀取的服務了,因此缺乏高可用性。
搭建步驟和上面單機版的一樣,只是後面需要做相關的叢集配置
### 啟動容器
分別在3臺伺服器上啟動redis容器,埠號為6379
```shell
mkdir -p /home/app/redis-rw/data
docker run -d -v /home/app/redis-rw/data:/data --name redis-rw -p 6379:6379 redis redis-server --requirepass "123456" --appendonly yes --masterauth "123456"
```
### 在一臺伺服器上做實驗的注意點
需要讓容器間可以相互訪問,好像需要在防火牆上開啟對應的埠號;但是不建議這樣搞,只是實驗可以試哈,實際使用不要這樣弄(因為這樣的叢集沒有意義)。
在一臺機器上做的話,就像需要使用docker給容器分配的IP;通過如下命令檢視容器的IP:
```shell
docker inspect 容器ID
```
裡面的IPAddress就是容器的IP;我這裡的是如下所示的
```shell
redis-c1 172.17.0.2
redis-c1 172.17.0.3
redis-c1 172.17.0.4
```
### 配置redis叢集
通過docker互動命令登陸redis;為了方便這裡直接用容器名稱(可以使用容器ID)
```shell
docker exec -it redis-rw redis-cli
```
![](https://img2020.cnblogs.com/blog/1929453/202101/1929453-20210129214256758-1281828491.png)
> 如果redis設定了認證密碼,則登陸進去了使用`auth 密碼`進行認證;然後使用`info replication`命令檢視redis的資訊,可以看到都是master節點
現在我們將其中一臺伺服器作為master節點;因此我們分別登陸到其它的redis容器中執行如下命令(下面的命令就相當於在配置檔案中新增相關配置):
```shell
# 這裡是設定跟隨哪臺機器
SLAVEOF 192.168.56.102 6379
```
設定主節點訪問密碼;由於我們在啟動引數上已經設定了`--masterauth`引數,因此這裡就不用再設定
```shell
# 由於我們設定了訪問密碼,因此需要設定主節點的訪問密碼;否則從節點將無法訪問主節點資訊
config set masterauth 123456
# 如果是使用配置檔案來啟動,再加上下面的這條命令將其重新寫入配置檔案中
config rewrite
# 如果修改或設定密碼可以使用這個命令
config set requirepass 密碼
```
> 如果設定redis密碼,就是必須設定masterauth的值;否則將出現這個錯誤:`Master does not understand REPLCONF listening-port: -NOAUTH Authentication required.`
## 三、在Docker上搭建Sentinel模式
> 文章參考:https://blog.csdn.net/miss1181248983/article/details/90056960
主從模式的弊端就是不具備高可用性,當master掛掉以後,Redis將不能再對外提供寫入操作,因此sentinel應運而生。
Sentinel即哨兵,它主要是用來監控redis主從節點的執行狀態,用於解決在master節點掛了後選舉出新的主節點,保證整個叢集可以繼續提供寫資料的能力。
Sentinel模式具有以下特點:
* sentinel模式是建立在主從模式的基礎上,如果只有一個Redis節點,sentinel就沒有任何意義;
* 當master掛了以後,sentinel會在slave中選擇一個做為master,其他slave的會指向新的master;
* 當master重新啟動後,它將不再是master而是做為slave接收新的master的同步資料;
* sentinel因為也是一個程序有掛掉的可能,所以sentinel也會啟動多個形成一個sentinel叢集;
* 多sentinel配置的時候,sentinel之間也會自動監控;
* 當主從模式配置密碼時,sentinel也會同步將配置資訊修改到配置檔案中,不需要擔心;
* 一個sentinel或sentinel叢集可以管理多個主從Redis,多個sentinel也可以監控同一個redis;
* sentinel最好不要和Redis部署在同一臺機器,不然Redis的伺服器掛了以後,sentinel也掛了;
Sentinel模式的工作機制:
* 每個sentinel以每秒鐘一次的頻率向它所知的master,slave以及其他sentinel例項傳送一個 PING 命令;
* 如果一個例項距離最後一次有效回覆 PING 命令的時間超過 `down-after-milliseconds` 選項所指定的值, 則這個例項會被sentinel標記為主觀下線;
* 如果一個master被標記為主觀下線,則正在監視這個master的所有sentinel要以每秒一次的頻率確認master的確進入了主觀下線狀態;
* 當有足夠數量的sentinel(大於等於配置指定的值)在指定的時間範圍內確認master的確進入了主觀下線狀態, 則master會被標記為客觀下線;
* 在一般情況下, 每個sentinel會以每 10 秒一次的頻率向它已知的所有master,slave傳送 INFO 命令;
* 當master被sentinel標記為客觀下線時,sentinel向下線的master的所有slave傳送 INFO 命令的頻率會從 10 秒一次改為 1 秒一次;
* 若沒有足夠數量的sentinel同意master已經下線,master的客觀下線狀態就會被移除;若master重新向sentinel的 PING 命令返回有效回覆,master的主觀下線狀態就會被移除;
> 當使用sentinel模式的時候,客戶端就不要直接連線Redis,而是連線sentinel的ip和port,由sentinel來提供具體的可提供服務的Redis實現,這樣當master節點掛掉以後,sentinel就會感知並將新的master節點提供給使用者。
### 開始部署Sentinel模式的Redis叢集
現在準備一個主從模式的叢集,然後開始搭建Sentinel服務;為了保證高可用我們將Sentinel也是使用叢集模式搭建,使用3臺伺服器來搭建叢集,在每臺機器上都部署一臺。
#### 下載和修改sentinel配置檔案
```shell
mkdir -p /home/app/redis/conf
cd /home/app/redis/conf
wget http://download.redis.io/redis-stable/sentinel.conf
```
修改`sentinel.conf`配置檔案
```shell
# 配置主節點的資訊
sentinel monitor mymaster 192.168.56.105 6379 2
# sentinel的訪問地址
requirepass 123456
# 配置主節點的訪問密碼
sentinel auth-pass mymaster 123456
```
#### 啟動Sentinel
```shell
docker run -d -v /home/app/redis-sentinel/data:/data -v /home/app/redis/conf:/usr/local/etc/redis --name redis-sentinel -p 26379:26379 redis redis-sentinel /usr/local/etc/redis/sentinel.conf --appendonly yes
```
啟動成功後就可以直接通過Sentinel的埠進行連結了,Sentinel會返回當前主節點資訊
## 四、在Docker上搭建Redis Cluster模式
我們使用Sentinel模式搭建的redis叢集雖然解決了高可用的問題,但是最終也只有一個主節點;
當業務量大的時候會產生如下問題:
* 併發寫的請求增高;
* 資料量增大;此時需要考慮資料分片儲存了;
* 單個伺服器的網絡卡上限達到瓶頸;
由此單個主從複製就無法滿足需求了,因此Redis Cluster模式登場了;
Redis Cluster是分散式架構:即Redis Cluster中有多個節點(主從複製節點),每個節點都負責進行資料讀寫操作;每個節點之間會進行通訊。簡單來說就是多個主從複製節點叢集提供服務。
### 叢集要求
* Redis叢集至少需要3個節點,因為投票容錯機制要求超過半數節點認為某個節點掛了該節點才是掛了,所以2個節點無法構成叢集。
* 要保證叢集的高可用,需要每個節點都有從節點,也就是備份節點,所以Redis叢集至少需要6臺伺服器。
### 部署叢集
我們在每臺機器上執行如下命令來建立6個redis服務
```shell
docker run -d -v /home/app/redis-cluster/data:/data --name redis-cluster -p 6379:6379 -p 16379:16379 redis redis-server --requirepass "123456" --appendonly yes --masterauth "123456" --cluster-enabled yes
```
> 後面這個16379埠使用redis叢集間進行資料通訊的埠,它是在你設定的redis訪問埠上+10000;
如果向使用配置檔案實現可以修改redis.conf配置中叢集相關配置即可,獲取redis.conf配置:
```shell
wget http://download.redis.io/redis-stable/sentinel.conf
```
在上面的命令需要加上配置檔案路徑對映,下面是示例命令
```shell
docker run -d -v /home/app/redis-cluster/data:/data -v /home/app/redis/conf:/usr/local/etc/redis --name redis-c1 -p 6381:6379 -p 16379:16379 redis redis-server /usr/local/etc/redis/redis.conf
```
下面開始叢集的配置,直接使用redis-cli建立叢集即可;
```shell
docker exec -it redis-cluster /bin/bash
redis-cli --cluster create 192.168.56.101:6379 192.168.56.102:6379 192.168.56.103:6379 192.168.56.104:6379 192.168.56.105:6379 192.168.56.106:6379 --cluster-replicas 1 -a 123456
```
> 引數最後加`-a`是因為我們設定了密碼,因此需要加上訪問密碼;之後輸入yes即可。
注意如果在一臺機器上搞的docker需要使用host模式的網路連線型別才行,在建立的時候需要使用docker容器的IP;我們通過`docker inspect 容器ID`命令獲取容器的IP。
關注微信訂閱號‘起岸星辰’獲取最新資訊
![](https://img2020.cnblogs.com/blog/1929453/202101/1929453-20210129213155475-411555664.png)