개요
유데미의 Certified Kubernetes Administrator (CKA) with Practice Tests 강의 중, 'Demo - Deployment with Kubeadm' 강의를 보며 kubeadm을 활용해 가상머신에 K8s Cluster를 구축하였습니다.
그러나 쿠버네티스 버전이 업데이트 되면서, 강의 내용과 공식문서에 차이가 있거나 강의를 따라했을 때 제대로 동작하지 않는 부분이 있어 이를 해결하며 구축한 과정을 기록하기 위해 글을 작성하였습니다.
강의에서 제공되는 Vagrantfile을 이용해 VirtualBox에 3개의 노드를 생성한 후, vagrant ssh로 노드에 접속하여 클러스터 환경을 구축하였습니다.
K8s Cluster
- 1개의 control plane과 2개의 worker node로 구성
- OS: Ubuntu
- K8s version: 1.31
- cri, cni 구현체로 containerd, weave 사용
구축 과정
1~4번 과정은 모든 노드에서 동일하게 수행해야 합니다.
1. IPv4 패킷 전달 활성화
기본적으로 Linux 커널은 인터페이스 간에 IPv4 패킷을 라우팅하는 것을 허용하지 않기 때문에 IPv4 패킷 전달을 수동으로 활성화해야 합니다.
# sysctl params required by setup, params persist across reboots
cat <<EOF | sudo tee /etc/sysctl.d/k8s.conf
net.ipv4.ip_forward = 1
EOF
# Apply sysctl params without reboot
sudo sysctl --system
sysctl net.ipv4.ip_forward의 결과가 1이면 IPv4 패킷 전달이 활성화 된 것입니다.
2. container runtime 설치
containerd 설치
# Add Docker's official GPG key:
sudo apt-get update
sudo apt-get install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc
# Add the repository to Apt sources:
echo \
"deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu \
$(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
sudo apt-get update
# Install containerd
sudo apt-get install containerd.io
systemctl status containerd로 확인
3. cgroup driver 설정
kubelet의 기본 cgroup driver는 cgroupfs입니다. 따라서 systemd를 cgroup driver로 사용하는 경우 다음과 같은 설정이 필요합니다.
# init system으로 systemd를 사용한다면 cgroup driver로 systemd 사용해야 함
# init system을 확인하는 방법
ps -p 1
/etc/containerd/config.toml 파일을 다음과 같이 수정해야 합니다.
[plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runc]
[plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runc.options]
SystemdCgroup = true
저의 경우 위와 같이 수정했으나, 일정 시간이 지난 후 api server 종료되는 문제가 발생하였습니다.
다음과 같은 방법으로 수정한 후 정상적으로 동작했습니다.
sudo su -c "containerd config default > /etc/containerd/config.toml"
sudo vi /etc/containerd/config.toml
# vi editor에서 /SystemdCgroup 로 해당 내용 찾은 후 true로 수정
설정을 마친 뒤 containerd를 재시작합니다.
sudo systemctl restart containerd
4. kubeadm, kubelet 및 kubectl 설치
sudo apt-get update
# apt-transport-https may be a dummy package; if so, you can skip that package
sudo apt-get install -y apt-transport-https ca-certificates curl gpg
# If the directory `/etc/apt/keyrings` does not exist, it should be created before the curl command, read the note below.
# sudo mkdir -p -m 755 /etc/apt/keyrings
curl -fsSL https://pkgs.k8s.io/core:/stable:/v1.31/deb/Release.key | sudo gpg --dearmor -o /etc/apt/keyrings/kubernetes-apt-keyring.gpg
# This overwrites any existing configuration in /etc/apt/sources.list.d/kubernetes.list
echo 'deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://pkgs.k8s.io/core:/stable:/v1.31/deb/ /' | sudo tee /etc/apt/sources.list.d/kubernetes.list
sudo apt-get update
sudo apt-get install -y kubelet kubeadm kubectl
sudo apt-mark hold kubelet kubeadm kubectl
sudo systemctl enable --now kubelet
5. kubeadm init
pod-network-cidr은 꼭 10.244.0.0/16일 필요는 없으나, 이후 설정하게 될 weave의 ipalloc_range와 동일해야 합니다. 또한 /16을 서브넷 마스크로 사용하는 것이 좋습니다. (cidr 블록 크기가 너무 작으면 나중에 원인 찾기 어려운 에러 발생 가능)
kubeadm init --pod-network-cidr=10.244.0.0/16 --apiserver-advertise-address={control plane node의 ip address}
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
kubectl get po로 정상 동작을 확인합니다.
중요: kubeadm init이 완료된 뒤, 'kubeadm join sudo kubeadm join --token <token> <control-plane-host>:<control-plane-port> --discovery-token-ca-cert-hash sha256:<hash>'의 형식으로 출력된 내용은 나중에 워커 노드에서 실행하기 위해 저장해두어야 합니다.
6. Pod network add-on 설치
Weave 설치 및 설정
KUBEVER=$(kubectl version | base64 | tr -d '\n')
kubectl apply -f https://reweave.azurewebsites.net/k8s/net?k8s-version=$KUBEVER
kubectl edit -n kube-system ds weave-net
# 다음 내용을 weave container의 env에 추가
- name: IPALLOC_RANGE
value: 10.244.0.0/16
7. 워커 노드 추가
저장해둔 'kubeadm join --token <token> <control-plane-host>:<control-plane-port> --discovery-token-ca-cert-hash sha256:<hash>'의 형식으로 출력된 내용을 복사하여 워커 노드에서 실행합니다.
정상적으로 실행되었다면 control plane에서 kubectl get no로 확인이 가능하며, Not Ready 상태의 노드 있다면 해당 노드에서 sudo systemctl restart kubelet을 실행합니다.
kubectl run nginx --image=nginx로 정상적으로 pod가 생성되는지 확인하여 클러스터 구축을 마무리합니다.
트러블슈팅
k9s 설치
k9s를 설치하여 사용한다면 kubectl을 사용하는 것보다 훨씬 빠르고 편하게 Cluster 리소스와 관련된 작업들을 처리할 수 있습니다.
curl -sS https://webinstall.dev/k9s | bash
source ~/.config/envman/PATH.env
token과 hash 값 저장하지 못한 경우
# token 확인
sudo kubeadm token list
# 9on8ak.tfzsb97r3hoh3xki
# Hash 값 확인
openssl x509 -pubkey -in /etc/kubernetes/pki/ca.crt | openssl rsa -pubin -outform der 2>/dev/null | openssl dgst -sha256 -hex | sed 's/^.* //'
# 85a9d1bb9787409727d6078f09c07d9430729a1a525d2d1ddd5827c29d8a939d
# 확인한 token과 Hash 값 이용해 kubeadm join
sudo kubeadm join 192.168.10.112:6443 --token 9on8ak.tfzsb97r3hoh3xki --discovery-token-ca-cert-hash sha256:85a9d1bb9787409727d6078f09c07d9430729a1a525d2d1ddd5827c29d8a939d
weave와 kube-proxy가 제대로 동작하지 않는 경우
저의 경우 모든 노드의 ip 주소가 각각 두 개였고, 그 중 더 작은 ip 주소가 모두 같았습니다. (kubeadm을 사용할 경우) 노드의 더 작은 ip 주소가 기본 ip 주소로 cluster에서 사용되기 때문에 노드간 ip 주소가 충돌하여 이러한 문제가 발생했습니다.
다음과 같은 방법으로 해결할 수 있었습니다.
먼저 노드의 ip 주소를 다른 노드와 충돌하지 않는 ip 주소로 명시하고,
sudo vi /var/lib/kubelet/kubeadm-flags.env
# 마지막에 —node-ip={사용할 노드 ip 주소} 추가
기존에 저장된 데이터와 Weave pod를 삭제한 후, Weave pod가 다시 생성되도록 하여 문제를 해결하였습니다.
sudo rm -rf /var/lib/weave/weave-netdata.db
for i in $(kubectl get pods -n kube-system | awk '{print $1}' | grep weave); do kubectl delete pod -n kube-system $i; done
kubeadm이나 kubectl 동작하지 않는 경우
먼저 다음 명령어를 실행하여 재시작한 후,
sudo systemctl daemon-reload
sudo systemctl restart kubelet
sudo systemctl restart containerd
그럼에도 kubectl 동작하지 않는 경우, 다음 명령어를 통해 kube-apiserver의 로그를 확인하여 해결 방법을 찾았습니다.
sudo crictl ps -a
sudo crictl logs {container-id}
모든 방법을 시도했음에도 해결되지 않으면, kubeadm을 reset 후 다시 init 하였습니다.
sudo kubeadm reset
'Cloud engineering' 카테고리의 다른 글
kubeadm으로 구축한 쿠버네티스 클러스터에 모니터링 시스템 구축하기 (0) | 2024.10.15 |
---|---|
kubeadm으로 구축한 쿠버네티스 환경에서 GitOps 구축하기 (2) | 2024.10.08 |
AWS Innovate Migrate, Modernize, Build 특집 온라인 컨퍼런스 후기 (6) | 2024.09.28 |
CKA 후기 (0) | 2024.09.24 |
kind 이용해 로컬 환경에 K8s Cluster 구축하기 (1) | 2024.09.16 |