1. 系統(tǒng)架構(gòu)
本文檔參照Harbor官方高可用方案說明,并且在Kubernetes
集群通過helm
來部署Harbor
刻坊。
Harbor
的大部分組件都是無狀態(tài)的應用谭胚,針對該種應用比如portal灾而、core旁趟、nginx
等只需要增加其相應的副本數(shù)量即可锡搜;在存儲數(shù)據(jù)層面耕餐,需要提供高可用的Postgresql肠缔、redis
集群桩砰,另外針對鏡像和chart
服務也需要提供可持久的存儲(PVCs
)亚隅。鑒于以上理論,也就有了下面的Harbor
高可用方案設計架構(gòu)圖(摘自Harbor官網(wǎng)
):
既然有了上圖的系統(tǒng)架構(gòu)設計行疏,下面開始著手具體部署實現(xiàn)。
另外本文只針對Harbor
高可用的設置贞让,其它部署可參照Harbor NFS部署和Harbor CEPH部署喳张。
2. 部署準備
2.1 Chart下載
首先下載Harbor Chart
销部,參照如下操作即可:
# 添加helm harbor repo
helm repo add harbor https://helm.goharbor.io
# 下載chart
helm fetch harbor/harbor
# 解壓縮
tar xvf harbor-xxx.tgz
cd harbor-xxx/
2.2 Harbor參數(shù)配置
跟常規(guī)部署一樣,需要修改values.yaml
文件:
- 修改
Harbor
對外暴露方式:上面提到的兩篇博文都是采用NodePort
的暴露方式擂涛,此處建議采用Ingress
,于是需要修改expose.ingress.hosts.core
和expose.ingress.hosts.notary
這兩個字段踩身; - 修改
externalURL
:修改成expose.ingress.hosts.core
字段的值挟阻,但是前面加上協(xié)議名稱附鸽; - 修改
PostgreSQL
配置:首先修改database.type
-->external
熄浓,然后填入database.external
區(qū)域的信息比如訪問數(shù)據(jù)庫的host赌蔑、端口竟秫、用戶名肥败、密碼等信息
皿哨,另外注意:這一塊需要提前手動創(chuàng)建四個空數(shù)據(jù)庫:harbor Core往史、Clair佛舱、Notary Server椎例、Notary Signer
,然后把數(shù)據(jù)庫的名稱填入database.external
區(qū)域请祖,至于PostgreSQL
高可用部署下文會進一步說明订歪; - 修改
Redis
配置:首先修改redis.type
-->external
,然后填入redis.external
區(qū)域信息肆捕,高可用方案下如果采用Redis Sentinal
方案刷晋,因為Harbor
上游項目代碼的Redis
客戶端不支持Sentinal
,所以可以考慮使用HAProxy
慎陵; - 持久化存儲配置:這一塊配置跟上面所提兩篇博文一致,預先安裝對應存儲的驅(qū)動插件,然后依據(jù)
StorageClass
創(chuàng)建PVC
進而提供PV
方式甥厦; - 修改其他組件的副本數(shù)量:修改
portal.replicas
,core.replicas
,jobservice.replicas
,registry.replicas
,chartmuseum.replicas
,clair.replicas
,notary.server.replicas
andnotary.signer.replicas
ton(n>=2谦秧,這里是3)
;
配置完之后亏娜,我們需要在環(huán)境中搭建高可用的數(shù)據(jù)庫:PostgreSQL和Redis
溯泣。
3. PostgreSQL高可用部署
這里采用stolon來部署PostgreSQL
的高可用,具體部署步驟可參考Stolon Inside Kubernetes。
一點說明:盡管helm hub
上已經(jīng)有stolon
的chart咱圆,但是不建議使用忱详,本人曾經(jīng)嘗試安裝過幾次航唆,不過最后都沒安裝成功,原因未知。
3.1 下載源碼和鏡像
按如下操作即可:
# 源碼下載
git clone https://github.com/sorintlab/stolon.git
# stolon鏡像下載
docker pull sorintlab/stolon:v0.13.0-pg10 # 網(wǎng)上隨便找的一個鏡像虐译,實際使用時可根據(jù)需求修改stolon/examples/kubernetes/image/docker/Dockerfile實現(xiàn)訂制
# 進入kubernetes部署目錄
cd stolon/examples/kubernetes/
3.2 初始化Stolon集群
# stolon集群初始化
kubectl run -i -t stolonctl --image=sorintlab/stolon:v0.13.0-pg10 --restart=Never --rm -- /usr/local/bin/stolonctl --cluster-name=kube-stolon --store-backend=kubernetes --kube-resource-kind=configmap init
3.3 參數(shù)配置
進入stolon kubernetes
安裝目錄后供鸠,可以看到:
需要修改出不多:
鏡像信息:此處均修改成
sorintlab/stolon:v0.13.0-pg10
postgres
數(shù)據(jù)庫用戶名稱:默認stolon
繁堡,可通過修改stolon-keeper.yaml
文件配置項完成設置绳矩;postgres
數(shù)據(jù)庫訪問密碼:默認password1
审姓,在secret.yaml
中存儲,如需更改先base64轉(zhuǎn)碼后存入魔吐;-
后端存儲配置:HA方案采用共享存儲酬姆,這里提前預先安裝ceph驅(qū)動插件只需在
stolon-keeper.yaml
文件做如下圖示修改即可立美,至于容量大小按需填入蔫巩;
副本數(shù)量:按需填入嫌松,這里默認都是
2
沪曙;
3.4 組件安裝
下面開始stolon
各個組件的部署,依次執(zhí)行如下命令即可:
kubectl create -f stolon-sentinel.yaml
kubectl create -f secret.yaml
kubectl create -f stolon-keeper.yaml
kubectl create -f stolon-proxy.yaml
kubectl create -f stolon-proxy-service.yaml
# RBAC相關
kubectl create -f role.yaml
kubectl create -f role-binding.yaml
如果出現(xiàn)如下結(jié)果說明安裝基本上是ok
了:
并且我們還可以通過kubectl logs
命令發(fā)現(xiàn)兩個keeper
一個是master
萎羔,而另一個則是standby
液走。
3.5 Harbor高可用準備及相關參數(shù)調(diào)整
3.5.1 Harbor參數(shù)調(diào)整
更新values.yaml
文件:
- database.external.host -->
stolon-proxy-service
即stolon-proxy的service名稱; - database.external.username -->
stolon
贾陷; - database.external.password -->
password1
缘眶;
3.5.2 Postgres初始化
如上面所說,需要預先在Postgres
集群中創(chuàng)建幾個空數(shù)據(jù)庫髓废,可借助kubernetes Job
來完成巷懈。因為Postgres
客戶端命令行工具支持以文件傳入SQL
命令的方式,所以只需把創(chuàng)建數(shù)據(jù)庫的命令放入幾個文件里慌洪,然后通過一個腳本調(diào)用它們即可:
-
幾個sql命令文件:
初始化腳本程序
#!/bin/bash
# postgresql.sh
host="stolon-proxy-service"
user="stolon"
db="postgres"
export PGPASSWORD="password1"
args=(
# force postgres to not use the local unix socket (test "external" connectibility)
--host "$host"
--username "$user"
--dbname "$db"
--quiet --no-align --tuples-only
)
if select="$(echo 'SELECT 1' | psql "${args[@]}")" && [ "$select" = '1' ]; then
psql -h stolon-proxy-service -p 5432 postgres -U stolon -f "/docker-entrypoint-initdb.d/notary_server.sql"
psql -h stolon-proxy-service -p 5432 postgres -U stolon -f "/docker-entrypoint-initdb.d/notary_signer.sql"
psql -h stolon-proxy-service -p 5432 postgres -U stolon -f "/docker-entrypoint-initdb.d/registry.sql"
psql -h stolon-proxy-service -p 5432 postgres -U stolon -f "/docker-entrypoint-initdb.d/clair.sql"
exit 0
fi
exit 1
- Job yaml文件
apiVersion: batch/v1
kind: Job
metadata:
name: stolon-init-database-job
spec:
template:
spec:
containers:
- name: stolon-proxy
image: sorintlab/stolon:master-pg10
command:
- "/bin/bash"
- "/docker-entrypoint-initdb.d/postgresql.sh"
volumeMounts:
- mountPath: /docker-entrypoint-initdb.d
name: database
restartPolicy: OnFailure #失敗重啟
volumes:
- name: database
hostPath:
path: /postgres_init # 把之前準備的sql和腳本文件放置這個目錄下顶燕,總共5個文件
activeDeadlineSeconds: 600 #10分鐘沒有complete,不再重啟并移除Pod
把之前準備好的sql和腳本文件拷貝到各個worker
節(jié)點/postgres_init
目錄蒋譬,然后再master
執(zhí)行批處理任務即可完成數(shù)據(jù)庫的初始化工作割岛,另外如果新建的數(shù)據(jù)庫名稱跟Harbor
配置不一致注意更新,自此Postgresql
高可用部署完成犯助。
4. Redis高可用部署
4.1 Redis哨兵集群部署
直接采用helm
部署即可癣漆,操作步驟可參考如下:
helm repo add stable `https://kubernetes-charts.storage.googleapis.com`
helm fetch stable/redis-ha
tar xvf redis-ha-xxx.tgz
cd redis-ha
修改values.yaml
配置,修改的地方不多絕大部分默認配置即可剂买,其中有兩處額外注意一下:
-
redis
訪問密碼設置:需提前創(chuàng)建一個包含redis
密碼信息的secret
對象惠爽,比如下面這樣:
然后通過kubectl create -f redis-secret.yaml
創(chuàng)建癌蓖,之后根據(jù)secret
修改values.yaml
對應認證信息即可:
(secret
中密碼都是base64
轉(zhuǎn)碼之后的結(jié)果,此處redis
密碼: password1 )
注意:如果如本文redis
集群最終要對接Harbor
且采用haproxy tcp-check
來偵測redis master
婚肆,此處auth
--> false
租副。
- 持久化存儲設置:因為數(shù)據(jù)庫后端采用共享存儲,設置好
PVC
對應的storageclass
和容量即可:
然后開始部署:
# 可以先檢查下配置
helm install --name vienfu-redis-cluster . --debug --dry-run
# 正式安裝
helm install --name vienfu-redis-cluster .
等待一會而便會發(fā)現(xiàn)部署完成了:
下面做個簡單測試:
4.2 Harbor高可用準備及參數(shù)調(diào)整
一般情況下只需訪問redis-sentinal
集群服務便可對redis master
進行讀寫较性,但是由于Harbor
內(nèi)置的redis
客戶端不支持sentinal
用僧,所以直接訪問redis sentinal
服務是不行的。那么直接訪問redis-server
的服務可以嗎赞咙?答案也是不可以的责循,因為這有可能后端最終訪問到redis slave
節(jié)點,而slave
節(jié)點卻是只讀的攀操,所以需要其他一種方式能夠從redis server
節(jié)點中找出redis master
院仿,根據(jù)官方文檔提示采用HAProxy
,仔細查閱下HAProxy
配置官方文檔速和,可以通過haproxy tcp-check
功能來鎖定redis master
歹垫,如下是可參照的haproxy
配置:
# cat /etc/haproxy/conf.d/redis-ha.conf
frontend ft_redis
bind 10.0.2.15:6379 name redis
default_backend bk_redis
backend bk_redis
option tcp-check
tcp-check connect
tcp-check send PING\r\n
tcp-check expect string +PONG
tcp-check send info\ replication\r\n
tcp-check expect string role:master
tcp-check send QUIT\r\n
tcp-check expect string +OK
server R1 vienfu-redis-cluster-redis-ha-server-0.vienfu-redis-cluster-redis-ha.default.svc.cluster.local:6379 check inter 1s
server R2 vienfu-redis-cluster-redis-ha-server-1.vienfu-redis-cluster-redis-ha.default.svc.cluster.local:6379 check inter 1s
server R3 vienfu-redis-cluster-redis-ha-server-2.vienfu-redis-cluster-redis-ha.default.svc.cluster.local:6379 check inter 1s
然后設置開機啟動及重啟haproxy
服務即可。
注意此處也要對應調(diào)整Harbor參數(shù)配置:redis.external.host
--> 上面haproxy配置的VIP:10.0.2.15
颠放。
4.2.1 其它說明
此外如你所見排惨,此處haproxy
后端server
的配置采用的是對應server
的域名,直接使用POD IP
也可以慈迈,不過考慮到該IP
可能會變若贮,所以建議使用域名來配置haproxy
后端server
,那么節(jié)點如何解析kubernetes
的service
域名呢痒留?對,通過CoreDNS
蠢沿。
首先伸头,需要獲取CoreDNS
對應的nameserver
,很簡單執(zhí)行如下命令即可:
kubectl get svc -n kube-system
把結(jié)果dns服務對應的CLUSTER-IP
作為新增的nameserver
配置到節(jié)點的域名配置文件中(一般默認/etc/resolve.conf
)舷蟀,不過高版本的linux一般都是通過systemd
來控制域名解析服務恤磷,如果直接修改該文件重啟域名服務是不生效的,在此提供一個簡單方法直接關掉systemd-resolved
并且禁用開機啟動野宜,這樣直接修改/etc/resolve.conf
就立刻生效了扫步,其他方法可參照Ubuntu 18.04修改DNS。
之后匈子,重啟haproxy
服務的過程中可能會碰到如下問題:提示后端server的域名無法解析河胎,但是執(zhí)行nslookup
命令卻能解析域名,發(fā)現(xiàn)也ping
不通虎敦,最終參照網(wǎng)上nslookup works but can not ping問題最終得以解決游岳。
5. Harbor HA安裝
按照如下命令執(zhí)行完成最終部署:
# 可先檢查下Harbor配置
helm install --name harbor-ha . --debug --dry-run
# 正式部署
helm install --name harbor-ha .