포스트

Rocky linux에 k8s(v1.34.2) 손설치 1 가상머신 준비



최종 구성도

Prerequisites

  • 리눅스에 가상머신 프로비저닝을 위한 VirtualBox 설치
1
2
3
4
5
6
7
8
9
10
11
12
13
# 저장소 추가
sudo mkdir -p /etc/apt/keyrings
wget -O- https://www.virtualbox.org/download/oracle_vbox_2016.asc | sudo gpg --dearmor --yes --output /etc/apt/keyrings/oracle-virtualbox2016.gpg

echo "deb [arch=amd64 signed-by=/etc/apt/keyrings/oracle-virtualbox2016.gpg] https://download.virtualbox.org/virtualbox/debian $(lsb_release -cs) contrib" | sudo tee /etc/apt/sources.list.d/virtualbox.list

# 업데이트 및 설치
sudo apt-get update
sudo apt-get install -y virtualbox-7.0
sudo apt-get install -y virtualbox-ext-pack

# 사용자 추가
sudo usermod -aG vboxusers $USER
  • 가상머신 프로비저닝을 위한 Vagrant 설치
1
2
3
4
5
wget -O - https://apt.releases.hashicorp.com/gpg | sudo gpg --dearmor -o /usr/share/keyrings/hashicorp-archive-keyring.gpg

echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/hashicorp-archive-keyring.gpg] https://apt.releases.hashicorp.com $(grep -oP '(?<=UBUNTU_CODENAME=).*' /etc/os-release || lsb_release -cs) main" | sudo tee /etc/apt/sources.list.d/hashicorp.list

sudo apt update && sudo apt install vagrant

설치시 트러블 슈팅

1
2
# IP추가
sudo bash -c 'echo "* 192.168.10.0/24" >> /etc/vbox/networks.conf'
  • VirtualBox와 KVM 충돌시
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
# KVM 모듈 언로드 
sudo modprobe -r kvm_intel 
# 또는 AMD CPU인 경우 
sudo modprobe -r kvm_amd 

# 확인 
lsmod | grep kvm 

# 부팅 후에도 자동 언로드 설정 
sudo bash -c 'echo "blacklist kvm_intel" >> /etc/modprobe.d/blacklist.conf'

# 또는 AMD 
sudo bash -c 'echo "blacklist kvm_amd" >> /etc/modprobe.d/blacklist.conf' 

# 재부팅
sudo reboot

Vagrant로 가상 머신 프로비저닝 하기

Rocky Linux용 자동화 스크립트 다운로드(init_cfg.sh)

  • TASK 1 : vagrant 사용자가 로그인할 때 자동으로 root 권한으로 전환되게 설정하고, vi 명령어를 vim으로 자동 변환하며, 서버의 시간대를 서울(Asia/Seoul)로 설정
  • TASK 2: Rocky Linux는 보안 강화 모듈인 SELinux를 사용
  • TASK 3: 메모리 가상 확장 기능인 SWAP을 끈다.
  • TASK 4: 필요한 유틸리티들을 설치
  • TASK 5: 관리자 계정의 비밀번호를 ‘qwe123’으로 설정
  • TASK 6: 원격 접속을 위해 암호 인증과 root 로그인을 허용하도록 설정한 후 SSH 서비스를 재시작한다.
  • TASK 7: hosts 파일에 IP와 호스트명을 매핑하여, DNS 서버 없이도 각 서버에 접근할 수 있게 설정

init_cfg.sh 다운로드 Link

1
wget https://raw.githubusercontent.com/hyeonjae1122/Vagrant-for-Rocky-Linux/refs/heads/main/init_cfg.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
# Rocky Linux용 init_cfg.sh 수정

#!/usr/bin/env bash
echo ">>>> Initial Config Start <<<<"

echo "[TASK 1] Setting Profile & Bashrc"
echo "sudo su -" >> /home/vagrant/.bashrc
echo 'alias vi=vim' >> /etc/profile
ln -sf /usr/share/zoneinfo/Asia/Seoul /etc/localtime # Change Timezone


#########################################
########### SELinux 사용 #################
#########################################
echo "[TASK 2] Disable SELinux (Rocky Linux uses SELinux, not AppArmor)"
setenforce 0 >/dev/null 2>&1
sed -i 's/^SELINUX=enforcing/SELINUX=disabled/' /etc/selinux/config

echo "[TASK 3] Disable and turn off SWAP"
swapoff -a && sed -i '/swap/s/^/#/' /etc/fstab

echo "[TASK 4] Install Packages"
yum update -y -q >/dev/null 2>&1
yum install -y tree git jq yq unzip vim sshpass >/dev/null 2>&1

echo "[TASK 5] Setting Root Password"
echo "root:qwe123" | chpasswd

echo "[TASK 6] Setting Sshd Config"
cat << EOF >> /etc/ssh/sshd_config
PasswordAuthentication yes
PermitRootLogin yes
EOF
systemctl restart sshd >/dev/null 2>&1

echo "[TASK 7] Setting Local DNS Using Hosts file"
sed -i '/^127\.0\.\(1\|2\)\.1/d' /etc/hosts
cat << EOF >> /etc/hosts
192.168.10.10  jumpbox
192.168.10.100 server.kubernetes.local server
192.168.10.101 node-0.kubernetes.local node-0
192.168.10.102 node-1.kubernetes.local node-1
EOF

echo ">>>> Initial Config End <<<<"

Rockylinux 이미지와 버전정보

Vagrantfile 다운로드 Link

1
wget https://raw.githubusercontent.com/hyeonjae1122/Vagrant-for-Rocky-Linux/refs/heads/main/vagrantfile

Box Link bento/rockylinux-9 이미지 경로

1
2
BOX_IMAGE = "bento/rockylinux-9"
BOX_VERSION = "202510.26.0"

Vagrant 를 이용한 가상 머신 배포

총 4대의 가상머신을 배포한다.

NAMEDescriptionCPURAMNIC1NIC2HOSTNAME
jumpboxAdministration host21536 MB10.0.2.15192.168.10.10jumpbox
serverKubernetes server22GB10.0.2.15192.168.10.100server.kubernetes.local server
node-0Kubernetes worker22GB10.0.2.15192.168.10.101node-0.kubernetes.local node-0
node-1Kubernetes worker22GB10.0.2.15192.168.10.102node-1.kubernetes.local node-1

배포 명령어 실행

1
2
3
4
ls -al
-rw-rw-r-- 1 hyeonjae hyeonjae 3073 Jan 10 18:01 vagrantfile

vagrant up
1
2
# 실습용 OS 이미지 자동 다운로드 확인
vagrant box list

1
2
# 배포된 가상머신 확인
vagrant status

아래와 같이 예상대로 4대의 가상머신이 배포된 것을 확인할 수 있다.

![600x150](https://raw.githubusercontent.com/hyeonjae1122/hyeonjae1122.github.io/main/assets/20260110T043413999Z.png)

jumpbox 가상머신접속

jumpbox에 ssh접속을 위한 명령어이다. 아주 많이 쓰이는 명렁어이므로 익숙해지자.

1
vagrant ssh jumpbox

머신 상태확인 명렁어 모음

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
# 사용자 확인
whoami
pwd

# OS version 확인
cat /etc/os-release

# SELinux 상태 확인
getenforce
sestatus
cat /etc/selinux/config

# /etc/hosts 파일 내용 확인
cat /etc/hosts

cat /etc/os-release 를 통하여 Rock Linux 임을 확인

필요한 각종 Tool을 설치한다. 기본 저장소에 없는 패키지들도 있으니 epel-release를 추가하자.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
# Tool Install
## EPEL = Extra Packages for Enterprise Linux**
### Rocky Linux(RHEL 기반)의 **기본 저장소에 없는 추가 패키지들을 제공하는 저장소

dnf -y install epel-release 
dnf install tree git jq yq unzip vim sshpass -y

# Installed:
#  git-2.47.3-1.el9_6.x86_64                     git-core-2.47.3-1.el9_6.x86_64
#  git-core-doc-2.47.3-1.el9_6.noarch            perl-DynaLoader-1.47-481.1.el9_6.x86_64
#  perl-Error-1:0.17029-7.el9.0.1.noarch         perl-File-Find-1.37-481.1.el9_6.noarch
#  perl-Git-2.47.3-1.el9_6.noarch                perl-TermReadKey-2.38-11.el9.x86_64
#  perl-lib-0.65-481.1.el9_6.x86_64              sshpass-1.09-4.el9.x86_64
#  yq-4.47.1-2.el9.x86_64
# Complete!

k8s hardway에 필요한 리소스를 다운 받기 위해 아래 레포지토리를 클론하자.

1
2
3
4
# Sync GitHub Repository ## --depth 1 : 최신 커밋만 가져오는 shallow clone을 의미
git clone --depth 1 https://github.com/kelseyhightower/kubernetes-the-hard-way.git

cd kubernetes-the-hard-way

아키텍처 확인

1
2
3
# CPU 아키텍처 확인 
uname -m # x86_64
uname -a # Linux jumpbox 5.14.0-570.52.1.el9_6.x86_64 #1 SMP PREEMPT_DYNAMIC Wed Oct 15 13:59:22 UTC 2025 x86_64 x86_64 x86_64 GNU/Linux

레포지토리 파일 내용 확인

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
cd kubernetes-the-hard-way

ls -al
total 60
drwxr-xr-x. 6 root root  4096 Jan 10 20:52 .
dr-xr-x---. 4 root root   150 Jan 10 20:52 ..
-rw-r--r--. 1 root root  5863 Jan 10 20:40 ca.conf
drwxr-xr-x. 2 root root  4096 Jan 10 20:40 configs
-rw-r--r--. 1 root root  1059 Jan 10 20:40 CONTRIBUTING.md
-rw-r--r--. 1 root root   407 Jan 10 20:40 COPYRIGHT.md
drwxr-xr-x. 2 root root  4096 Jan 10 20:40 docs
-rw-r--r--. 1 root root   839 Jan 10 20:40 downloads-amd64.txt
-rw-r--r--. 1 root root   839 Jan 10 20:40 downloads-arm64.txt
drwxr-xr-x. 8 root root   178 Jan 10 20:40 .git
-rw-r--r--. 1 root root  1167 Jan 10 20:40 .gitignore
-rw-r--r--. 1 root root 11358 Jan 10 20:40 LICENSE
-rw-r--r--. 1 root root  2624 Jan 10 20:40 README.md
drwxr-xr-x. 2 root root  4096 Jan 10 20:40 units

k8s 구성을 위한 컴포넌트 다운로드한다. 위에서 다운로드한 레포지토리에 있는 바이너리 파일들의 링크는 버전이 낮으므로 아래와 같이 1.34버전에 맞춰준다.

[쿠버네티스 다운로드 공식 링크] (https://www.downloadkubernetes.com/)

1
2
3
4
5
6
7
8
9
10
11
12
13
cat > downloads-amd64.txt << 'EOF'
https://dl.k8s.io/v1.34.2/bin/linux/amd64/kube-scheduler
https://dl.k8s.io/v1.34.2/bin/linux/amd64/kubectl
https://dl.k8s.io/v1.34.2/bin/linux/amd64/kubelet
https://dl.k8s.io/v1.34.2/bin/linux/amd64/kube-apiserver
https://dl.k8s.io/v1.34.2/bin/linux/amd64/kube-controller-manager
https://dl.k8s.io/v1.34.2/bin/linux/amd64/kube-proxy
https://github.com/kubernetes-sigs/cri-tools/releases/download/v1.34.0/crictl-v1.34.0-linux-amd64.tar.gz
https://github.com/opencontainers/runc/releases/download/v1.4.0/runc.amd64
https://github.com/containernetworking/plugins/releases/download/v1.8.0/cni-plugins-linux-amd64-v1.8.0.tgz
https://github.com/containerd/containerd/releases/download/v2.1.5/containerd-2.1.5-linux-amd64.tar.gz
https://github.com/etcd-io/etcd/releases/download/v3.6.7/etcd-v3.6.7-linux-amd64.tar.gz
EOF

최신버전으로 변경하였다면 wget으로 다운로드한다.

1
2
3
4
5
wget -q --show-progress \
  --https-only \
  --timestamping \
  -P downloads \
  -i downloads-amd64.txt

각종 컴포넌트 분류를 위한 폴더를 만들고 압축을 풀어준다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
mkdir -p downloads/{client,cni-plugins,controller,worker}
tree -d downloads

# 압축풀기
tar -xvf downloads/crictl-v1.34.0-linux-amd64.tar.gz \
-C downloads/worker/ && tree -ug downloads

tar -xvf downloads/containerd-2.1.5-linux-amd64.tar.gz --strip-components 1 -C downloads/worker/ && tree -ug downloads

tar -xvf downloads/cni-plugins-linux-amd64-v1.8.0.tgz -C downloads/cni-plugins/ && tree -ug downloads

tar -xvf downloads/etcd-v3.6.7-linux-amd64.tar.gz \
-C downloads/ \
--strip-components 1 \
etcd-v3.6.7-linux-amd64/etcdctl \
etcd-v3.6.7-linux-amd64/etcd && tree -ug downloads

# 확인
tree downloads/worker/ 
tree downloads/cni-plugins
ls -l downloads/{etcd,etcdctl}

# 파일 이동 
mv downloads/{etcdctl,kubectl} downloads/client/ 
mv downloads/{etcd,kube-apiserver,kube-controller-manager,kube-scheduler} downloads/controller/ 
mv downloads/{kubelet,kube-proxy} downloads/worker/ 
mv downloads/runc.amd64 downloads/worker/runc

# 확인 
tree downloads/client/ 
tree downloads/controller/ 
tree downloads/worker/

# 불필요한 압축 파일 제거 
ls -l downloads/*gz 
rm -rf downloads/*gz

# Make the binaries executable. 
ls -l downloads/{client,cni-plugins,controller,worker}/* 
chmod +x downloads/{client,cni-plugins,controller,worker}/* 
ls -l downloads/{client,cni-plugins,controller,worker}/*

# 일부 파일 소유자 변경 
tree -ug downloads # cat /etc/passwd | grep vagrant && cat /etc/group | grep vagrant 
chown root:root downloads/client/etcdctl 
chown root:root downloads/controller/etcd 
chown root:root downloads/worker/crictl 
tree -ug downloads

# kubernetes client 도구인 kubectl를 설치 
ls -l downloads/client/kubectl 
cp downloads/client/kubectl /usr/local/bin/

kubectl 버전 확인

1
kubectl version --client

![[2026-01-04-Bootstrap k8s the hard way-18.png]]

SSH 접속 환경 설정

vagrant ssh jumpbox

  • SSH 접속환경을 설정해준다.
    • IP , FQDN, HOST, SUBNET을 설정
    • 새로운 SSH key를 생성하고 각각 노드에 전달
    • Hostname 설정 및 ssh 접속 확인
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
# Machine Database (서버 속성 저장 파일) : IPV4_ADDRESS FQDN HOSTNAME POD_SUBNET
## 참고) server(controlplane)는 kubelet 동작하지 않아서, 파드 네트워크 대역 설정 필요 없음
cat <<EOF > machines.txt
192.168.10.100 server.kubernetes.local server
192.168.10.101 node-0.kubernetes.local node-0 10.200.0.0/24
192.168.10.102 node-1.kubernetes.local node-1 10.200.1.0/24
EOF
cat machines.txt

while read IP FQDN HOST SUBNET; do
  echo "${IP} ${FQDN} ${HOST} ${SUBNET}"
done < machines.txt


# Configuring SSH Access 설정
 
# sshd config 설정 파일 확인 : 이미 암호 기반 인증 접속 설정 되어 있음
grep "^[^#]" /etc/ssh/sshd_config
...
PasswordAuthentication yes
PermitRootLogin yes

# Generate a new SSH key
ssh-keygen -t rsa -N "" -f /root/.ssh/id_rsa
ls -l /root/.ssh
-rw------- 1 root root 2602 Jan  2 21:07 id_rsa
-rw-r--r-- 1 root root  566 Jan  2 21:07 id_rsa.pub

# Copy the SSH public key to each machine
while read IP FQDN HOST SUBNET; do
  sshpass -p 'qwe123' ssh-copy-id -o StrictHostKeyChecking=no root@${IP}
done < machines.txt

while read IP FQDN HOST SUBNET; do
  ssh -n root@${IP} cat /root/.ssh/authorized_keys
done < machines.txt

# Once each key is added, verify SSH public key access is working
# 아래는 IP 기반으로 접속 확인
while read IP FQDN HOST SUBNET; do
  ssh -n root@${IP} hostname
done < machines.txt


# Hostnames 설정

# 확인 : init_cfg.sh 로 이미 설정되어 있음
while read IP FQDN HOST SUBNET; do
  ssh -n root@${IP} cat /etc/hosts
done < machines.txt

while read IP FQDN HOST SUBNET; do
  ssh -n root@${IP} hostname --fqdn
done < machines.txt

# 아래는 hostname 으로 ssh 접속 확인
cat /etc/hosts
while read IP FQDN HOST SUBNET; do
  sshpass -p 'qwe123' ssh -n -o StrictHostKeyChecking=no root@${HOST} hostname
done < machines.txt

while read IP FQDN HOST SUBNET; do
  sshpass -p 'qwe123' ssh -n root@${HOST} uname -o -m -n
done < machines.txt
이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.