목차
시작하며
k8s환경을 구축한 이후 jupyter와 superset을 설치하였는데 이상하게 정상적으로 실행되지 않았다. 에러 로그를 추적하면서 pv, pvc, storageClass에 존재를 알게 되었고 이것을 사용해야지만 정상적으로 설치되어 사용할 수 있는 것이었다.
pv와 pvc를 활용하기 위해선 스토리지가 필요한데 온프레미스 환경에서는 네트워크 기반 스토리지를 사용한다. 대표적으로 3가지가 있다.
1. rook-ceph
2. NFS(Network File System)
3. GlusterFS
필자는 rook-ceph를 가장 많이 쓴다고 하여 이것에 대한 것만 알아보았고 나머지는 잘 모른다. k8s 환경에서 스토리지를 설치하는 것은 정말 신경쓸 것이 많았다. 필요조건은 다음과 같다.
a. node 3개 이상
b. node 당 파티션 설정이되어 있지 않은 빈 디스크 1개 이상
- lsblk -f 또는 df -h
c. 각 node server 8 core 이상
- lscpu | grep "^CPU(s):" | awk '{print $2}'
d. 각 node server memory 20GB 이상
- free -h
b. node 당 파티션 설정이되어 있지 않은 빈 디스크 1개 이상(참고자료)
이해를 돕기 위해 설치전과 후를 비교했다.


이 조건에 해당하지 않은 상태에서 설치하였고, 안 되는 이유를 찾는 데 많은 시간이 걸렸다.. 다른 분들은 이 글을 보고 시간을 낭비하지 않길 바란다.
설치 따라하기
git clone 전에 git을 설치하자
sudo dnf install -y git
[root@docker01 ceph]# kubectl create namespace rook-ceph
[root@docker04 ceph]# cd /var/lib
[root@docker04 ceph]# git clone --single-branch --branch release-1.16 https://github.com/rook/rook.git
[root@docker04 ceph]# cd rook/deploy/examples
// rook-ceph -> namespace 생성 및 여기에 pods 실행
[root@docker04 ceph]# export ROOK_OPERATOR_NAMESPACE="rook-ceph"
[root@docker04 ceph]# export ROOK_CLUSTER_NAMESPACE="rook-ceph"
[root@docker04 ceph]# sed -i.bak \
-e "s/\(.*\):.*# namespace:operator/\1: $ROOK_OPERATOR_NAMESPACE # namespace:operator/g" \
-e "s/\(.*\):.*# namespace:cluster/\1: $ROOK_CLUSTER_NAMESPACE # namespace:cluster/g" \
-e "s/\(.*serviceaccount\):.*:\(.*\) # serviceaccount:namespace:operator/\1:$ROOK_OPERATOR_NAMESPACE:\2 # serviceaccount:namespace:operator/g" \
-e "s/\(.*serviceaccount\):.*:\(.*\) # serviceaccount:namespace:cluster/\1:$ROOK_CLUSTER_NAMESPACE:\2 # serviceaccount:namespace:cluster/g" \
-e "s/\(.*\): [-_A-Za-z0-9]*\.\(.*\) # driver:namespace:operator/\1: $ROOK_OPERATOR_NAMESPACE.\2 # driver:namespace:operator/g" \
-e "s/\(.*\): [-_A-Za-z0-9]*\.\(.*\) # driver:namespace:cluster/\1: $ROOK_CLUSTER_NAMESPACE.\2 # driver:namespace:cluster/g" \
/var/lib/rook/deploy/examples/common.yaml \
/var/lib/rook/deploy/examples/operator.yaml \
/var/lib/rook/deploy/examples/cluster.yaml
[root@docker04 ceph]# kubectl create -f crds.yaml -f common.yaml -f operator.yaml
// 꼭 rook-ceph-operator 가 STATUS = Running 인지 확인한 후 다음을 진행하자
[root@docker04 ceph]# kubectl get pods -n rook-ceph
NAME READY STATUS RESTARTS AGE
rook-ceph-operator-68c44c7fc4-22cq4 1/1 Running 0 29m
[root@docker04 ceph]# kubectl create -f cluster.yaml
NAME READY STATUS RESTARTS AGE
csi-cephfsplugin-5dfv2 3/3 Running 0 28m
csi-cephfsplugin-5whdx 3/3 Running 0 28m
csi-cephfsplugin-provisioner-69fcc97965-p282p 6/6 Running 0 28m
csi-cephfsplugin-provisioner-69fcc97965-p47bf 6/6 Running 0 28m
csi-cephfsplugin-s2npg 3/3 Running 0 28m
csi-rbdplugin-79msq 3/3 Running 0 28m
csi-rbdplugin-mc8r6 3/3 Running 0 28m
csi-rbdplugin-provisioner-54fdf8db4c-kj8dk 6/6 Running 0 28m
csi-rbdplugin-provisioner-54fdf8db4c-wbhvw 6/6 Running 0 28m
csi-rbdplugin-wwp22 3/3 Running 0 28m
rook-ceph-crashcollector-docker03-5b5896dfcd-rmcl8 1/1 Running 0 25m
rook-ceph-crashcollector-docker05-549458499b-8q2bb 1/1 Running 0 25m
rook-ceph-crashcollector-docker06-59644d6f8f-q9wsc 1/1 Running 0 25m
rook-ceph-mgr-a-575d888889-rslgh 1/1 Running 0 25m
rook-ceph-mon-a-5bbfd67998-64lw6 1/1 Running 0 28m
rook-ceph-mon-b-546948d4c9-gbr64 1/1 Running 0 28m
rook-ceph-mon-d-758f494bd5-ppbtg 1/1 Running 0 24m
rook-ceph-operator-68c44c7fc4-22cq4 1/1 Running 0 29m
rook-ceph-osd-0-b4c745d6-crn2w 1/1 Running 0 23m
rook-ceph-osd-1-59879b6f95-sn2sr 1/1 Running 0 23m
rook-ceph-osd-2-7d667774f9-hklkn 1/1 Running 0 23m
rook-ceph-osd-prepare-docker03-xrwrw 0/1 Completed 0 23m
rook-ceph-osd-prepare-docker05-c6mfv 0/1 Completed 0 23m
rook-ceph-osd-prepare-docker06-fndfb 0/1 Completed 0 23m
osd까지 모두 생성된 이후 아래와 같이 cephcluster의 PHASE가 Ready이면 성공이다.
[root@docker04 ceph]# kubectl get cephcluster -n rook-ceph
NAME DATADIRHOSTPATH MONCOUNT AGE PHASE MESSAGE HEALTH EXTERNAL
rook-ceph /var/lib/rook 3 32m Ready Cluster created successfully HEALTH_WARN
HEALTH_WARN이 발생하였다. 이 경우엔 아래 toolbox 설치 후 접근하여 로그를 확인할 수 있다.
[root@docker04 ceph]# kubectl create -f toolbox.yaml
[root@docker04 ceph]# kubectl -n rook-ceph exec -it $(kubectl -n rook-ceph get pod -l "app=rook-ceph-tools" -o jsonpath='{.items[0].metadata.name}') bash
kubectl exec [POD] [COMMAND] is DEPRECATED and will be removed in a future version. Use kubectl exec [POD] -- [COMMAND] instead.
[root@rook-ceph-tools-867586b448-qp5mk /]# ceph -s
cluster:
id: 5792cb1b-922b-4574-ba02-25aa85651499
health: HEALTH_WARN
clock skew detected on mon.b, mon.d
mon d is low on available space
services:
mon: 3 daemons, quorum a,b,d (age 62m)
mgr: a(active, since 25m)
osd: 3 osds: 3 up (since 62m), 3 in (since 63m)
data:
pools: 1 pools, 128 pgs
objects: 0 objects, 0 B
usage: 19 MiB used, 220 GiB / 220 GiB avail
pgs: 128 active+clean
에러가 2가지가 발생했다.
1. clock skew detected on mon.b, mon.d
2. mon d is low on available space
오류를 조치한 방법은 아래 게시글을 참고하기 바란다.
[kubernetes] rook-ceph Error: clock skew detected on mon.b, mon.d
목차 결론 mon.b와 mon.d에 서버 시간이 맞지 않을 때 발생하는 에러이다. 필자는 ntp 서버를 구축하여 시간을 동기화 시켰는데 해당 서버들에 ntp 동기화 적용을 하지 않아 발생했다. 방법 1) 시간 확
jfbta.tistory.com
[kubernetes] rook-ceph Error: mon d is low on available space
목차 결론 직역하면 mon d에 사용 가능한 공간이 부족하다는 의미다. 디스크 확보 전 Avail은 16G였다. [root@docker05 apps]# df -h Filesystem Size Used Avail Use% Mounted on /dev/mapper/centos-root 50G 30G 16G 59% / 디스크
jfbta.tistory.com
rook-ceph 완전 삭제하기
[root@docker04 ceph]# cd /var/lib
[root@docker04 ceph]# cd rook/cluster/examples/kubernetes/ceph
[root@docker04 ceph]# kubectl delete -f crds.yaml -f common.yaml -f operator.yaml
[root@docker04 ceph]# kubectl delete -f toolbox.yaml
// cluster 제거를 시도하면 종속적으로 실행중인 프로세스 때문에 멈출 것이다.
[root@docker04 ceph]# kubectl delete -f cluster.yaml
----
제거 시 멈춘 경우 강제 삭제 명령어를 실행해보자.
----
// cephcluster 강제삭제
for CRD in $(kubectl get crd -n rook-ceph | awk '/ceph.rook.io/ {print $1}'); do
kubectl get -n rook-ceph "$CRD" -o name | \
xargs -I {} kubectl patch -n rook-ceph {} --type merge -p '{"metadata":{"finalizers": []}}'
done
// 파드 강제 삭제
kubectl delete pod --all -n rook-ceph --grace-period 0 --force
// 네임스페이스 강제 삭제
kubectl get namespace "rook-ceph" -o json \
| tr -d "\n" | sed "s/\"finalizers\": \[[^]]\+\]/\"finalizers\": []/" \
| kubectl replace --raw /api/v1/namespaces/"rook-ceph"/finalize -f -
----
// rook-ceph를 설치할 때 git으로 받아온 폴더이다. 이것을 꼭 제거해주어야 한다.
[root@docker04 ceph]# rm -rf /var/lib/rook
// 모든 node에 있는 빈디스크 xvdb를 초기화 시키는 명령어이다. node서버에 직접 접근한 후 실행한다.
// 둘 중 하나 실행
[root@docker04 ceph]# dd if=/dev/zero of=/dev/xvdb bs=120M status=progress
[root@docker04 ceph]# dd if=/dev/random of=/dev/xvdb bs=120M status=progress
bs=120M은 네트워크 속도이기 때문에 높을 수록 빠르다.
여기까지 삭제를 완료했다면 다시 되돌아가 설치해서 테스트한다.
설치 완료 확인
[root@docker04 ceph]# kubectl get cephcluster -n rook-ceph
NAME DATADIRHOSTPATH MONCOUNT AGE PHASE MESSAGE HEALTH EXTERNAL
rook-ceph /var/lib/rook 3 32m Ready Cluster created successfully HEALTH_OK
HEALTH_OK가 되어야 성공이다.
PV 자동 생성 테스트
[root@docker04 /]# cd var/lib/rook/cluster/examples/kubernetes/ceph/
[root@docker04 /]# kubectl create -f csi/rbd/storageclass.yaml
pvc에서 연결을 시도할 storageclass를 생성합니다.
[root@docker04 ceph]# cd ..
[root@docker04 kubernetes]# ll
total 16
drwxr-xr-x 7 root root 4096 Mar 5 10:18 ceph
-rw-r--r-- 1 root root 1205 Mar 4 19:33 mysql.yaml
-rw-r--r-- 1 root root 129 Mar 4 19:33 README.md
-rw-r--r-- 1 root root 1303 Mar 4 19:33 wordpress.yaml
[root@docker04 kubernetes]# kubectl create -f mysql.yaml
service/wordpress-mysql created
persistentvolumeclaim/mysql-pv-claim created
deployment.apps/wordpress-mysql created
[root@docker04 kubernetes]# kubectl create -f wordpress.yaml
service/wordpress created
persistentvolumeclaim/wp-pv-claim created
deployment.apps/wordpress created
kubectl get pv,pvc로 확인하면 아래와 같은 결과가 나타날 것이다.
Every 2.0s: kubectl get pv,pvc Tue Mar 5 11:44:34 2024
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
persistentvolume/pvc-00c3baf5-0c75-454b-a1ed-a9e58149dc47 20Gi RWO Delete Bound default/mysql-pv-claim rook-ceph-block 2m47s
persistentvolume/pvc-32878213-173a-4475-89b5-e48718ee1991 20Gi RWO Delete Bound default/wp-pv-claim rook-ceph-block 2m34s
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
persistentvolumeclaim/mysql-pv-claim Bound pvc-00c3baf5-0c75-454b-a1ed-a9e58149dc47 20Gi RWO rook-ceph-block 2m47s
persistentvolumeclaim/wp-pv-claim Bound pvc-32878213-173a-4475-89b5-e48718ee1991 20Gi RWO rook-ceph-block 2m34s
마지막으로 Dashboard 실행 후 모니터링
[root@docker04 ceph]# kubectl edit cephcluster -n rook-ceph
(수정 전)
dashboard:
enabled: true
ssl: true
(수정 후)
dashboard:
enabled: true
ssl: false
https가 아닌 http로 접근해야되기 때문에 ssl을 false로 바꿔준다.
[root@docker04 ceph]# vim dashboard-loadbalancer.yaml
(수정 전)
spec:
ports:
- name: dashboard
port: 8443
protocol: TCP
targetPort: 8443
(수정 후)
spec:
ports:
- name: dashboard
port: 7000
protocol: TCP
targetPort: 7000
[root@docker04 ceph]# kubectl apply -f dashboard-loadbalancer.yaml
ssl을 false로 바꾸면 port가 7000이 되기 때문에 실행할 dashboard도 같이 변경해야한다.
kubectl edit service/rook-ceph-mgr-dashboard-loadbalancer -n rook-ceph
```
spec:
clusterIP: 10.106.234.12
clusterIPs:
- 10.106.234.12
externalTrafficPolicy: Cluster
internalTrafficPolicy: Cluster
ipFamilies:
- IPv4
ipFamilyPolicy: SingleStack
ports:
- name: dashboard
nodePort: 30900
port: 7000
protocol: TCP
targetPort: 7000
selector:
app: rook-ceph-mgr
mgr_role: active
rook_cluster: rook-ceph
sessionAffinity: None
type: NodePort
status:
loadBalancer: {}
```
대시보드에 접근하기 위해 type을 nodePort로 변경한 후 원하는 포트번호를 지정하여 수정하여 접근한다.
kubectl -n rook-ceph get secret rook-ceph-dashboard-password -o yaml | grep "password:" | awk '{print $2}' | base64 --decode
Ceph ID : admin
Password는 위 명령어를 통해 얻는다. [rook-ceph가 1.16 버전에서는 디폴트에서 패스워드를 변경하면 나중에 변경된 패스워드로 로그인할 수 없는 버그가 발생하여 디폴트를 사용하는 것을 권장함.]
'Infrastructure > Docker & Kubernetes' 카테고리의 다른 글
[kubernetes] helm install로 superset 완벽하게 설치하기 (2) | 2024.03.16 |
---|---|
[kubernetes] on-premise 환경에서 LoadBalancer(metalLB) 설치 따라하기 (0) | 2024.03.16 |
[kubernetes] rook-ceph Error: clock skew detected on mon.b, mon.d (1) | 2024.03.09 |
[kubernetes] rook-ceph Error: mon d is low on available space (1) | 2024.03.09 |
[kubernetes] token, hash token 발급 후 join, node 추가 방법 (0) | 2024.03.03 |