๐ก ๋ณธ ๋ฌธ์๋ '์ฟ ๋ฒ๋คํฐ์ค ์ ๋ฌธ: Part I. ์ฟ ๋ฒ๋คํฐ์ค ์์ํ๊ธฐ'์ ๋ํด ์ ๋ฆฌํด๋์ ๊ธ์ ๋๋ค.
'์ฟ ๋ฒ๋คํฐ์ค ์ ๋ฌธ'์ด๋ผ๋ Kubernetest์ ๊ฐ๋ ๋ฐ ์ค์ต์ ๋ค๋ฃฌ ์ฑ ์ ์ฝ์ผ๋ฉฐ ๊ด๋ จ ํต์ฌ ๋ด์ฉ์ ์ ๋ฆฌํ์์ต๋๋ค. ๋ณธ ๋ฌธ์์ ๊ฒฝ์ฐ 'Part I. ์ฟ ๋ฒ๋คํฐ์ค ์์ํ๊ธฐ'์ ๋ด์ฉ์ธ ์ฟ ๋ฒ๋คํฐ์ค๋ฅผ ์ฒ์ ์ ํ๋ ์ฌ๋์ด ๊ผญ ์์์ผ ํ ๋ด์ฉ์ ๋ํด ๋ค๋ฃจ์์ผ๋ ์ฐธ๊ณ ํ์๊ธฐ ๋ฐ๋๋๋ค. ์ถ๊ฐ๋ก, ํด๋น ์ฑ ์ ์ํ ์์ ๋ [github] kubernetes-book-sample์์ ๋ค์ด ๋ฐ์ kubectl apply -f <filename>.yaml ๋ช ๋ น์ ํตํด ์ค์ตํ ์ ์์ผ๋ ์ฐธ๊ณ ํ์๊ธฐ ๋ฐ๋๋๋ค.
1. ์ฟ ๋ฒ๋คํฐ์ค ์๊ฐ
์ฟ ๋ฒ๋คํฐ์ค์ ์ปจํ ์ด๋๊ฐ ๋ฌด์์ธ์ง ์๊ฐํ๊ณ ์ฟ ๋ฒ๋คํฐ์ค์ ์ฃผ์ ํน์ง์ ์๊ฐํฉ๋๋ค.
์ปจํ ์ด๋
๋ฆฌ๋ ์ค๋ ์๋ ํ๋ก์ธ์ค ๋ณ๋ก ์์์ ๊ฒฉ๋ฆฌํด์ ์ฌ์ฉํ๋ cgroup๊ณผ ํน์ ๋๋ ํ ๋ฆฌ๋ก ๊ถํ์ ์ ํํ๋ chroot ๋ฑ์ผ๋ก ๊ฒฉ๋ฆฌ ํ๊ฒฝ์ ๊ตฌ์ฑํ ์ ์์์ต๋๋ค. ์ฌ๊ธฐ์ ๋์คํฌ์ ํ์ผ ๋ณ๊ฒฝ ์ฌํญ์ ๋ ์ด์ด ํํ๋ก ์ ์ฅํ๋ ํ์ผ ์์คํ ์ ํฉํด '์ปจํ ์ด๋'๋ผ๋ ๊ฐ๋ ์ด ํ์ํ์ต๋๋ค.
๊ธฐ์กด์ ๊ฐ์ํ๋ ํด๋ผ์ฐ๋ ์ปดํจํ ์ ์ค๋ช ํ ๋์ ๊ฐ์ ๋จธ์ (Virtual Machine, VM)์ ๋ง์ด ์ธ๊ธํฉ๋๋ค. ํ์ง๋ง ์ปจํ ์ด๋๊ฐ ์๋ ค์ง๋ฉฐ ๊ตฌ์กฐ์ ๋ ์ด์ด๊ฐ ๋ ๊ฐ๋จํ ์ปจํ ์ด๋ ๊ธฐ์ ์ ๊ด์ฌ์ด ์ ๋ฆฌ๊ธฐ ์์ํ์ต๋๋ค.
- ์ปจํ ์ด๋์ ๊ฒฝ์ฐ, Host OS ์์ ๋์ปค๊ฐ ์์ผ๋
- ๊ฐ์๋จธ์ ์ ๊ฒฝ์ฐ, ํ์ดํผ๋ฐ์ด์ ์์ ๊ฐ์๋จธ์ ๋ง๋ค Guest OS๊ฐ ์๊ณ ๊ทธ ์์ ์ฑ์ด ์์น
๋ฐ๋ผ์ ์ปจํ ์ด๋ ๊ตฌ์กฐ๊ฐ ํจ์ฌ ๊ฐ๋จํฉ๋๋ค. ๋ํ ๋์ปค๋ฅผ ์ด์ฉํ๋ฉด ๊ฐ๋จํ ๋ช ๋ น์ผ๋ก ์ปจํ ์ด๋ ์ด๋ฏธ์ง๋ฅผ ๋ง๋ค๊ณ ์ ์ฅ/์คํ์ด ํธ๋ฆฌํฉ๋๋ค.
์ปจํ ์ด๋ ์ค์ผ์คํธ๋ ์ด์ ์์คํ
์ด๋ ๊ฒ ์ปจํ ์ด๋๋ฅผ ์คํํ๊ธฐ์๋ ๋์ปค๊ฐ ๋งค์ฐ ํธ๋ฆฌํ์ง๋ง, ์ค์ ์์ฉ ์๋น์ค๋ฅผ ์ด์ํ ๋์ฒ๋ผ ์ฌ๋ฌ ๋์ ์๋ฒ๋ฅผ ๊ด๋ฆฌํ๊ธฐ์๋ ๋ถํธํ ์ ์ด ๋ง์ต๋๋ค. ์ด๋ฅผ ๋์์ฃผ๋ ์์คํ ์ '์ปจํ ์ด๋ ์ค์ผ์คํธ๋ ์ด์ '์ด๋ผ ํ๋ฉฐ, ์ด๋ฌํ ์์คํ ์ ๋ค์๊ณผ ๊ฐ์ ์ฃผ์ ํน์ง์ด ์์ต๋๋ค.
- ์๋ฒ ํ๋์ ์ฅ์ ๋ฐ์์ ์์ฉ ์๋น์ค์ ์ํฅ์ ๋ฐ์ง ์๋๋ก ๊ด๋ฆฌ
- ์ฌ๋ฌ ๋์ ์๋ฒ๋ฅผ ํ๋ฒ์ ๋ช ๋ น์ผ๋ก ์๋ ๋ฐฐํฌ
์ด๋ ๊ฒ ์ปจํ ์ด๋ ์ค์ผ์คํธ๋ ์ด์ ์์คํ ์๋ ์ฌ๋ฌ ์์ฉ ์๋น์ค๊ฐ ์์๋๋ฐ, ํ์ฌ๋ ์ฟ ๋ฒ๋คํฐ์ค(Kubernetes, k8s)๊ฐ ์ฌ์ค์ ํ์ค์ผ๋ก ์ฌ์ฉ๋๊ณ ์์ผ๋ฉฐ, ๋ค์๊ณผ ๊ฐ์ ํน์ง์ ๊ฐ์ง๊ณ ์์ต๋๋ค.
์ฟ ๋ฒ๋คํฐ์ค์ ํน์ง
- ์ ์ธ์ API
- ์ปจํ ์ด๋๊ฐ ์ค์ ํ ์ํ๊ฐ ์๋๋ผ๋ฉด ๊ทธ๊ฒ์ ๋ง๊ฒ ์๋์ผ๋ก ๋ง์ถค(ํญ์ ์ํ๋ ์ํ๋ก ์๋ ๋ณต๊ตฌ)
- ํ์ง๋ง ์ด๋ก ์ธํด ๋ถํธํ ์ ๋ ์์(์ฑ์ด ์์ด์ผ ํ ๋๋ ์ค์ ํ๊ธฐ ์ฝ์ง๋ง, ์ฑ ์ฌ์์ ๊ฐ์ ๋จ์ํ ์์ ์ ํ ์ ์์ → ์ฟ ๋ฒ๋คํฐ์ค ์์คํ ๋ด๋ถ ๋์์ผ๋ก ์ฌ์ฉ์๊ฐ ์ ์ดํ ์ ์๊ธฐ ๋๋ฌธ)
- ์ํฌ๋ก๋ ๋ถ๋ฆฌ
- ๋ถ์ฐ๋ ํ๋ก์ธ์ค์ ๊ด๋ฆฌ๋ฅผ ์ถ์ํํ๋ ๋ ์ด์ด๊ฐ ๋๋ฏ๋ก ์์คํ ์ด์์ ๋ํด ๊ณ ๋ฏผ์ ๋์ด์ค๋๋ค.
- ์ด๋์๋ ์คํ ๊ฐ๋ฅ
- ๊ฐ์ธ ์ปดํจํฐ, ์ฌ๋ฌ ๋ ์๋ฒ, ํผ๋ธ๋ฆญ ํด๋ผ์ฐ๋, ๋จ์ํ ์น์์ ๊ตฌ๋ ๊ฐ๋ฅ.
- ์ปค๋ฎค๋ํฐ
- 2019๋ 12์ ๊ธฐ์ค ์ฝ 2,300๋ช ์ ๊ธฐ์ฌ์์ 86,000๊ฐ์ ์ปค๋ฐ์ด ์์
- ์ฟ ๋ฒ๋คํฐ์ค ๊ณต์ ๊นํ๋ธ์ Issue
- slack ์ฑ๋(kubernetes-users)
- ํ์ด์ค๋ถ ๊ทธ๋ฃน(Kubernetes Korea Group)
- ํด๋ผ์ฐ๋ ํ๋ ํผ: ๋ฎ์ ์ง์
์ฅ๋ฒฝ
- Google Cloud Platform
- Microsoft Azure
- Amazon EKS: AWS์์๋ ์ฟ ๋ฒ๋คํฐ์ค ๊ด๋ฆฌํ ์๋น์ค
2. ์ฟ ๋ฒ๋คํฐ์ค ์ค์นํ๊ธฐ
์ฟ ๋ฒ๋คํฐ์ค๋ฅผ ์ด์ฉํ๋ ๋ฐฉ๋ฒ
์ด์ ๋ถํฐ ์ค์ ์ฌ๋ฌ๋ถ์ ์ปดํจํฐ์ ๋์ปค์ ์ฟ ๋ฒ๋คํฐ์ค๋ฅผ ์ด์ฉํ๋ ๋ฐฉ๋ฒ์๋ ๋ค์๊ณผ ๊ฐ์ด 4๊ฐ์ง๊ฐ ์์ต๋๋ค.
- ์น ์์์ ์ด์ฉ: ์นดํ์ฝ๋ค ์ฟ ๋ฒ๋คํฐ์ค ํ๋ ์ด๊ทธ๋ผ์ด๋ (kubectl ๊ด๋ จ ๋ช
๋ น ์คํ ๊ฐ๋ฅ)
- O'reilly์ ์ธ์๋์ด ํ์ฌ ์ง์ํ์ง ์์ (22.06.15. ์ดํ)
- ๋์ปค ๋ฐ์คํฌํฑ: ๋ก์ปฌ์ ์ฟ ๋ฒ๋คํฐ์ค ์ง์ ์ค์น
- ๋์ปค ๋ฐ์คํฌํฝ ์คํ ํ ‘Enable Kubernetes’, ‘Deploy Docker Stacks to Kubernetes by default’ ์ต์ ์ ์ฉ
- ํด๋ผ์ฐ๋ ์๋น์ค: ์ค์ ์์ฉ ์๋น์ค์ ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ๊ตฌ์ฑํ๊ณ ๊ด๋ฆฌ ๊ฐ์ฅ ๊ฐ๋จํ ๋ฐฉ๋ฒ
- ๊ตฌ๊ธ ์ฟ ๋ฒ๋คํฐ์ค ์์ง(GKE)
- ์๋ง์กด ์ฟ ๋ฒ๋คํฐ์ค ์ผ๋์คํฑ ์ปจํ ์ด๋ ์๋น์ค(Amazon EKS)
- ์ ์ ์ฟ ๋ฒ๋คํฐ์ค ์๋น์ค(AKS)
- ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ์ง์ ๊ตฌ์ฑํ๋ ๋๊ตฌ: ๊ท์น์ค์ ์ด์๋ฅผ ํด๊ฒฐํ ๋ ํ์ฉ
- Kubeadm
- Kubespray
์ด๋ ๊ฒ 4๊ฐ์ง ๋ฐฉ๋ฒ ๋ชจ๋ kubernetes๋ฅผ ์ฌ์ฉํ๊ธฐ ์ํ kubectl ๋ช ๋ น์ ์ง์ํฉ๋๋ค. ์ฌ๊ธฐ์ '์น ์์์ ์ด์ฉ', '๋์ปค ๋ฐ์คํฌํฑ', 'ํด๋ผ์ฐ๋ ์๋น์ค'์ ๊ฒฝ์ฐ ์ฑ ์์์ ์์ธํ ๋ค๋ฃจ๊ณ ์์ง ์๊ธฐ์ ๋ฐ๋ก ์์ธํ ์๊ฐํ์ง ์๊ณ , '์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ์ง์ ๊ตฌ์ฑํ๋ ๋๊ตฌ'์ ๋ํด ์์ธํ ์ค๋ช ํ๋๋ก ํ๊ฒ ์ต๋๋ค.
์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ์ง์ ๊ตฌ์ฑํ๋ ๋๊ตฌ
ํด๋ผ์ฐ๋ ์๋น์ค์์ ์ ๊ณตํ๋ ์ฟ ๋ฒ๋คํฐ์ค ๋๊ตฌ๋ฅผ ์ด์ฉํ๋๋ผ๋ ์ฌ๋ฌ๊ฐ์ง ์ฌ์ ๋๋ฌธ์ ์ง์ ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ๊ตฌ์ฑํด์ผ ํ ๋๋ ์์ต๋๋ค. ์ฌ๊ธฐ์์๋ ์ฌ๋ด ์๋ฒ ์์์ ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ์ง์ ๊ตฌ์ฑํ๊ฑฐ๋, ๊ท์น ์ค์(compliance) ์ด์๋ฅผ ํด๊ฒฐํ ๋ ํ์ฉํ๋ ๋ํ์ ์ธ ๋๊ตฌ์ธ Kubeadm, Kubespray๋ฅผ ์ดํด๋ณด๊ฒ ์ต๋๋ค.
1) Kubeadm
Kubeadm์ ์ฟ ๋ฒ๋คํฐ์ค์์ ๊ณต์ ์ ๊ณตํ๋ ํด๋ฌ์คํฐ ์์ฑ/๊ด๋ฆฌ ๋๊ตฌ์ ๋๋ค. ์ฌ๋ฌ ๋ ์๋ฒ๋ฅผ ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ก ์์ฝ๊ฒ ๊ตฌ์ฑ ๊ฐ๋ฅํ๋ฉฐ, ์๋์ ๊ฐ์ ๊ตฌ์กฐ๋ก ๋ก๋๋ฒจ๋ฐ์๋ฅผ ๋์ด ๊ณ ๊ฐ์ฉ์ฑ์ ์ ๊ณตํ๋ ํด๋ฌ์คํฐ๊น์ง ๊ตฌ์ฑ ๊ฐ๋ฅํฉ๋๋ค.
- ์ฌ๋ฌ ๋์ ๋ง์คํฐ ๋ ธ๋๋ฅผ ๊ตฌ์ฑํ๊ณ ๊ทธ ์์ ๋ก๋๋ฐธ๋ฐ์๋ฅผ ๋์ด ์์ปค ๋ ธ๋๋ค์ด ๋ง์คํฐ ๋ ธ๋์ ์ ๊ทผํ ๋ ๋ก๋๋ฒจ๋ฐ์๋ฅผ ๊ฑฐ์ณ ์ ๊ทผ
- ๋ฐ๋ผ์ ๋ง์คํฐ ๋ ธ๋ 1๋์ ์ฅ์ ๊ฐ ๋ฐ์ํ๋๋ผ๋ ๋ก๋๋ฐธ๋ฐ์์์ ๋ค๋ฅธ ๋ง์คํฐ ๋ ธ๋๋ก ์ ๊ทผํ๊ฒ ํ์ฌ ์ ๋ขฐ์ฑ ์ ์ง ๊ฐ๋ฅ
- ์ฐธ๊ณ ๋ก, ์ ๊ทธ๋ฆผ์ ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ์ ๋ฐ์ดํฐ ์ ์ฅ์ ์ญํ ์ ํ๋ etcd ํด๋ฌ์คํฐ๋ฅผ ๋ง์คํฐ ๋ ธ๋์ ํจ๊ป ์ค์นํ์ฌ ์ด์ํ๋ 'stacked etcd' ๋ฐฉ๋ฒ์ด๋ผ ํฉ๋๋ค.
์ฌ๊ธฐ์, ๋ง์คํฐ ๋ ธ๋์ ์์ปค๋ ธ๋๋?
- ๋ง์คํฐ ๋ ธ๋: ๋ ธ๋๋ค์ ์ํ๋ฅผ ๊ด๋ฆฌํ๊ณ ์ ์ดํฉ๋๋ค. ์ฟ ๋ฒ๋คํฐ์ค์ ๋ฐ์ดํฐ ์ ์ฅ์๋ก ์ฌ์ฉํ๋ etcd๋ฅผ ํจ๊ป ์ค์นํ๊ฑฐ๋ผ ๋ณ๋ ๋ ธ๋์ ๋ถ๋ฆฌํด์ ์ค์นํ๊ธฐ๋ ํฉ๋๋ค.
- ์์ปค ๋ ธ๋: Kubelet์ด๋ผ๋ ํ๋ก์ธ์ค๊ฐ ๋์ํ๋ฉฐ, ๋ง์คํฐ ๋ ธ๋์ ๋ช ๋ น์ ๋ฐ์ ์ฌ์ฉ์๊ฐ ์ ์ธํ pod(ํ๋)๋ Job(์ก)์ ์คํํฉ๋๋ค.
2) Kubespray
Kubespray๋ ์์ฉ ์๋น์ค์ ์ ํฉํ ๋ณด์์ฑ๊ณผ ๊ณ ๊ฐ์ฉ์ฑ์ด ์๋ ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ๋ฐฐํฌํ๋ ์คํ์์ค ํ๋ก์ ํธ์ ๋๋ค. ์ค์ ์ ๋ฐ๋ผ ์ฌ์ฉ์์๊ฒ ๋ง๋ ํด๋ฌ์คํฐ๋ฅผ ๊ตฌ์ฑํ ์ ์์ผ๋ฏ๋ก ์จํ๋ ๋ฏธ์ค ํ๊ฒฝ์์ ์์ฉ์๋น์ค์ ์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ๊ตฌ์ฑํ ๋ ์ ์ฉํฉ๋๋ค. ๋ํ ์ค์น ์ดํ์ ingress-nginx ์ปจํธ๋กค๋ฌ, Helm, ๋ณผ๋ฅจ ํ๋ฌ๊ทธ์ธ, cephfs๋ฅผ ํ๋ก๋น์ ๋ํ๋ cephfs-provisioner, SSL ์ธ์ฆ์๋ฅผ ๊ด๋ฆฌํ๋ cert-manager ๋ฑ์ ์ถ๊ฐ ๊ตฌ์ฑ ์์๋ฅผ ํด๋ฌ์คํฐ์ ์คํํ๋ ์ญํ ๋ ํฉ๋๋ค. ์ด๋ ๊ณต์๋ฌธ์์์ ๋ ์์ธํ ๋ด์ฉ์ ์ฐธ๊ณ ํ ์ ์์ต๋๋ค.
Kubespray์์ ์ ๊ณตํ๋ ํด๋ฌ์คํฐ ๊ณ ๊ฐ์ฉ์ฑ ๊ตฌ์กฐ๋ Kubeadm๊ณผ ์ฝ๊ฐ ๋ค๋ฆ ๋๋ค.
Kubeadm์ฒ๋ผ ๋ณ๋์ ๋ก๋๋ฒจ๋ฐ์๋ฅผ ์ฌ์ฉํ์ง ์๊ณ ๋ ธ๋ ๊ฐ๊ฐ์ nginx๊ฐ ๋ฆฌ๋ฒ์ค ํ๋ก์๋ก ์คํ๋๋ฉฐ, ์ด nginx-proxy๊ฐ ์ ์ฒด ๋ง์คํฐ ๋ ธ๋๋ฅผ ๋ฐ๋ผ๋ณด๋ ๊ตฌ์กฐ์ ๋๋ค. ๊ทธ๋์ ์ฟ ๋ฒ๋คํฐ์ค์ ์ปดํฌ๋ํธ๋ค์ ์ง์ ๋ง์คํฐ ๋ ธ๋์ ํต์ ํ์ง ์๊ณ ์์ ์ ์๋ฒ ์์ nginx์ ํต์ ํฉ๋๋ค. ๋ง์คํฐ ๋ ธ๋์ ์ฅ์ ๊ฐ์ง๋ health check๋ฅผ ์ด์ฉํด nginx๊ฐ ์์์ ์ฒ๋ฆฌํฉ๋๋ค.
์ฟ ๋ฒ๋คํฐ์ค๋ Container Network Interface(CNI)๋ฅผ ๋ง์กฑํ๋ ๋ค์ํ ๋คํธ์ํฌ ํ๋ฌ๊ทธ์ธ์ ์ง์ํ์ฌ, ๊ฐ๋จํ ์ค์ ์ผ๋ก ํด๋ฌ์คํฐ ๋คํธ์ํฌ๋ฅผ ์๋ ๊ตฌ์ฑํ ์ ์์ต๋๋ค. ๋ค์์ ๋งํฌ๋ฅผ ์ฐธ๊ณ ํ์๊ธฐ ๋ฐ๋๋๋ค.
- Kubespray๊ฐ ์ง์ํ๋ ๋คํธ์ํฌ ํ๋ฌ๊ทธ์ธ: https://kubernetes.io/ko/docs/concepts/cluster-administration/addons/#%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%82%B9%EA%B3%BC-%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-%ED%8F%B4%EB%A6%AC%EC%8B%9C
3. ์ฟ ๋ฒ๋คํฐ์ค๋ก ์ปจํ ์ด๋ ์คํํ๊ธฐ
์ด ์ฑ ์ ์ค์ต ๊ธฐ๋ฐ์ธ ์ฟ ๋ฒ๋คํฐ์ค ์ปค๋งจ๋๋ผ์ธ ์ธํฐํ์ด์ค kubectl ๊ธฐ๋ณธ ์ฌ์ฉ๋ฒ๊ณผ ์ด๋ฅผ ์ด์ฉํ ์ปจํ ์ด๋ ์คํ ๋ฐฉ๋ฒ์ ์ดํด๋ด ๋๋ค.
3.1 kubectl
์ฟ ๋ฒ๋คํฐ์ค ํด๋ฌ์คํฐ๋ฅผ ๊ณ ๋๋ฆฌํ๋ ๋์์ ๋๋ถ๋ถ kubectl์ด๋ผ๋ CLI๋ก ์คํํ ์ ์์ผ๋ฉฐ, ์ง์ํ๋ ๋ช ๋ น์ ๋ค์๊ณผ ๊ฐ์ด ๊ตฌ๋ถ๋ฉ๋๋ค.
- ์ฟ ๋ฒ๋คํฐ์ค ์์๋ค์ ์์ฑ, ์ ๋ฐ์ดํธ, ์ญ์ (create, update, delete)
- ๋๋ฒ๊ทธ, ๋ชจ๋ํฐ๋ง, ํธ๋ฌ๋ธ ์ํ (log, exec, cp, top, attach, ...)
- ํด๋ฌ์คํฐ ๊ด๋ฆฌ(cordon, top, drain, taint, ...)
๋์ฑ ๋ ์์ธํ kubectl ์ฌ์ฉ๋ฒ์ ์ฟ ๋ฒ๋คํฐ์ค ๊ณต์๋ฌธ์๋ฅผ ์ฐธ๊ณ ํ์ธ์~
3.1.1 ์ค์น
Kubespray Kubeadm ๋ฑ ๋ง์คํฐ ๋ ธ๋์ kubectl์ด ์ค์น๋์ด ์์ผ๋ฉฐ, ๋ง์คํฐ ๋ ธ๋์ ์ง์ ์ ๊ทผํด ํด๋ฌ์คํฐ ๊ด๋ฆฌ์ ๊ถํ์ผ๋ก kubectl ๊ด๋ จ ๋ช ๋ น๋ค์ ์ฌ์ฉํ ์ ์์ต๋๋ค. ๊ทธ๋ฐ๋ฐ ์ด ๋ฐฉ์์ผ๋ก๋ ์ฌ๋ฌ ์ฌ์ฉ์์ ๊ถํ์ ์ ์ดํ ์ ์๋ค๋ ๋ฌธ์ ๊ฐ ์์ผ๋ฉฐ, ํด๋ฌ์คํฐ ์ฌ์ฉ์ ๊ฐ๊ฐ์ ํด๋ฌ์คํฐ ์ธ๋ถ์ kubectl์ ์ค์นํ๊ณ ์ธ์ฆ ์ ๋ณด๋ฅผ ์ค์ ํด์ผ ํฉ๋๋ค.
์ค์น๋ ์ด์์ฒด์ ๋ณ ํจํค์ง ๋งค๋์ (ubuntu: apt, mac: brew, window: chocholatey,...)์ผ๋ก ํด๋ฌ์คํฐ ์ธ๋ถ์ ์ฌ์ฉ์ ์ปดํจํฐ์ kubectl์ ์ค์นํ ์ ์์ต๋๋ค. Apple sillicon MacOS์์๋ ๋ค์๊ณผ ๊ฐ์ด ์ค์นํ ์ ์์ต๋๋ค.
$ curl -LO "https://dl.k8s.io/release/$(curl -L -s https://dl.k8s.io/release/stable.txt)/bin/darwin/arm64/kubectl"
$ chmod +x ./kubectl
$ sudo mv ./kubectl /usr/local/bin/kubectl
์ฃผ์ ํด๋ผ์ฐ๋ ์๋น์ค์ ์ฟ ๋ฒ๋คํฐ์ค ๋๊ตฌ์๋ ํด๋ฌ์คํฐ ์ธ๋ถ์ kubectl์ ์ค์นํด์ ์ฌ์ฉํ๋ ๋ฐฉ๋ฒ์ ์ ๊ณตํฉ๋๋ค.
- Amazon EKS: https://docs.aws.amazon.com/ko_kr/eks/latest/userguide/install-kubectl.html
- GKE: https://cloud.google.com/kubernetes-engine/docs/quickstarts/deploy-app-container-image?hl=ko
- AKS: https://learn.microsoft.com/en-us/azure/aks/learn/quick-kubernetes-deploy-cli
3.1.2 ๊ธฐ๋ณธ ์ฌ์ฉ๋ฒ
kubectl์ ๋ค์ ํ์์ผ๋ก ๋ช ๋ น์ ์์ฑํฉ๋๋ค
kubectl [command] [Type] [NAME] [FLAG]
- command: ์์์ ์คํํ๋ ค๋ ๋์์ด๋ฉฐ, create, get, delete ๋ฑ์ ์ฌ์ฉํ ์ ์์ต๋๋ค.
- TYPE: ์์ ํ์ ์ด๋ฉฐ, pod, service, ingress ๋ฑ์ ์ฌ์ฉํ ์ ์์ต๋๋ค.
- NAME: ์์ ์ด๋ฆ์ ๋๋ค.
- FLAG: ๋ถ๊ฐ์ ์ผ๋ก ์ค์ ํ ์ต์ ์ ์ ๋ ฅํฉ๋๋ค.
๊ฐ๋จํ minikube tutorial์์ ์ ๊ณตํ๋ ์๊ฐ๊ฐ์ ๋ฆฌํดํด์ฃผ๋ ์๋ฒ๊ฐ ๋์ํ๋ ์ด๋ฏธ์ง๋ฅผ ๋์ฐ๋ kubectl ๋ช ๋ น ์์์ ๋๋ค.
% kubectl run hello --image=registry.k8s.io/e2e-test-images/agnhost:2.39 --port=8081
pod/echoserver created
์ดํ ํ๋๊ฐ ์ ์์ ์ผ๋ก ์์ฑ๋์๋์ง ํ์ธํด๋ณด๊ฒ ์ต๋๋ค.
% kubectl get pods
NAME READY STATUS RESTARTS AGE
hello 1/1 Running 0 96s
- NAME: ํ๋์ ์ด๋ฆ์ ํ์
- READY: ํ๋์ ์ค๋น ์ํ๋ฅผ ํ์
- 0/1: ํ์ฌ ํ๋๊ฐ ์์ฑ๋์์ผ๋ ์ฌ์ฉํ ์ค๋น๊ฐ ๋์ง ์์์
- 1/1: ํ๋๊ฐ ์์ฑ๋์์ผ๋ฉฐ ์ฌ์ฉํ ์ค๋น๊ฐ ๋๋ฌ์
- STATUS: ํ๋์ ํ์ฌ ์ํ๋ฅผ ํ์
- RESTARTS: ํด๋น ํ๋๊ฐ ๋ช๋ฒ ์ฌ์์ํ๋์ง ํ์
- AGE: ํ๋๋ฅผ ์์ฑํ ํ ์๊ฐ์ด ์ผ๋ง๋ ์ง๋ฌ๋์ง
K8s์ Pod์ ์ ๊ทผํ ๋ ํ์ํ ์๋น์ค๋ฅผ ์์ฑํด์ผ ํฉ๋๋ค.
์์ ๋จ์ํ ์ด๋ฏธ์ง๋ฅผ ๋์ ๋ 'hello' ํ๋์ ๊ฒฝ์ฐ ๋ค์์ ๋ช ๋ น์ด๋ก ์๋น์ค๋ฅผ ์์ฑํ ์ ์์ต๋๋ค.
% kubectl expose po hello --type=LoadBalancer --port=8081
service/hello exposed
๋ค์์ผ๋ก ์๋น์ค๊ฐ ์ ์์ ์ผ๋ก ์์ฑ๋์๋์ง ํ์ธํด๋ณด๊ฒ ์ต๋๋ค.
% kubectl get service
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
hello LoadBalancer 10.106.2.186 localhost 8081:30129/TCP 5s
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 28d
- NAME: ์๋น์ค์ ์ด๋ฆ์ ํ์
- TYPE: ์๋น์ค์ ํ์ ์ ์๋ฏธ
- CLUSTER-IP: ํ์ฌ ํด๋ฌ์คํฐ ์์์ ์ฌ์ฉ๋๋ IP
- EXTERNAL-IP: ํด๋ฌ์คํฐ ์ธ๋ถ์์ ์ ์ํ ๋ ์ฌ์ฉํ๋ IP
- <none>: ๋ณ๋๋ก ์ค์ ํ์ง ์์
- PORT(S): ํด๋น ์๋น์ค์ ์ ์ํ๋ ํฌํธ๋ฅผ ํ์
- AGE: ์์์ ์์ฑํ๊ณ ์ผ๋ง๋ ์๊ฐ์ด ์ง๋ฌ๋์ง ๋ํ๋
์ฐธ๊ณ ๋ก, ์ฌ๊ธฐ์ kubernetes๋ผ๋ ์ด๋ฆ์ ์๋น์ค๋ kube-apiserver ๊ด๋ จ ํ๋๋ค์ ๊ฐ๋ฆฌํต๋๋ค.
์ด์ ์น ๋ธ๋ฌ์ฐ์ ์์ http://localhost:8080/ ๋ก ์ ์ํ๊ฑฐ๋ curl์ ์ด์ฉํ๋ฉด ๋ค์ ๋ฉ์์ง๋ฅผ ํ์ธํ ์ ์์ต๋๋ค.
% curl http://localhost:8080
NOW: 2023-03-02 03:19:03.265168927 +0000 UTC m=+1601.533555441
์ดํ pod์ด๋ service๋ฅผ ์ค์งํ๊ณ ์ถ์ผ๋ฉด ๋ค์๊ณผ ๊ฐ์ด ์ ๋ ฅํ๋ฉด ๋ฉ๋๋ค.
% kubectl delete pod hello
pod "hello" deleted
% kubectl delete service hello
service "hello" deleted
3.1.3 POSIX/GNU ์คํ์ผ์ ๋ช ๋ น ์์ฑ ๊ท์น
kubectl์ ๊ธฐ๋ณธ์ ์ผ๋ก POSIX/GNU์คํ์ผ ๋ช ๋ น ๊ท์น์ ๋ฐ๋ฆ ๋๋ค.
- - ๊ณผ ํจ๊ปํ๋ ์ต์ : ์งง์ ์ต์ ์ผ๋ก ๋จ์ผ ์ํ๋ฒณ/์ซ์ ์ธ์๋ฅผ ์ฌ์ฉํจ
- - ๊ณผ ํจ๊ปํ๋ ์ต์ : ๊ธด ์ต์ ์ผ๋ก ๋ ๊ธ์ ์ด์์ ์ํ๋ฒณ/์ซ์ ์ธ์๋ฅผ ์ฌ์ฉํจ
- Ref. program Argument Syntax Conventions: https://www.gnu.org/software/libc/manual/html_node/Argument-Syntax.html
3.1.4 ํ๋๊ทธ
๋ชจ๋ ๋ช ๋ น์์ ์ฌ์ฉํ ์ ์๋ ์ ์ญ ํ๋๊ทธ์ ๊ฐ๋ณ ๋ช ๋ น์์๋ง ์ฌ์ฉํ ์ ์๋ ๊ฐ๋ณ ํ๋๊ทธ๋ก ๊ตฌ๋ถํฉ๋๋ค.
์ ์ญํ๋๊ทธ์ ๊ฒฝ์ฐ kubectl options ์์ ํ์ธํ ์ ์์ผ๋ฉฐ, ๋ํ์ ์ผ๋ก -h, -v๊ฐ ์์ต๋๋ค.
- -h(help): kubectl [command] --help ํํ๋ก ์ฌ์ฉํ๋ฉฐ, ๊ฐ๋ณ ๋ช ๋ น์ ๋์๋ง์ ์ถ๋ ฅํฉ๋๋ค.
- -v [log level]: ๋ช ๋ น์ ์คํํ๋ ๊ณผ์ ์ ๋ก๊ทธ๋ฅผ ์ถ๋ ฅํ๊ฑฐ๋ ๋ก๊ทธ ๋ ๋ฒจ์ ์ค์ ํ๋ฉฐ, ๋๋ฒ๊น ํ ๋ ์ ์ฉํฉ๋๋ค.
3.1.5 kubeconfig ํ๊ฒฝ ๋ณ์
kubectl์ ๊ธฐ๋ณธ์ ์ผ๋ก $HOME/.kube/config ํ์ผ์์ ํด๋ฌ์คํฐ, ์ธ์ฆ, ์ปจํ ์คํธ ์ ๋ณด๋ฅผ ์ฝ์ด ๋ค์ ๋๋ค. ์ด๋ฌํ ํด๋ฌ์คํฐ ๊ตฌ์ฑ ์ ๋ณด๋ฅผ kubeconfig๋ผ ์นญํฉ๋๋ค.
ํด๋ฌ์คํฐ์์ ์ฌ์ฉํ ์ ์๋ ์์๋ค์ kubectl api-resources ๋ช ๋ น์ผ๋ก ํ์ธํ ์ ์์ต๋๋ค.
% kubectl api-resources
NAME SHORTNAMES APIVERSION NAMESPACED KIND
bindings v1 true Binding
componentstatuses cs v1 false ComponentStatus
configmaps cm v1 true ConfigMap
endpoints ep v1 true Endpoints
...
- SHORTNAMES: : ์์์ ๋จ์ถ ์ด๋ฆ
- APIGROUP: ํจ๊ป ๋ ธ์ถ๋๋ ์์ ์งํฉ
- NAMESPACED: ํน์ ๋ค์์คํ์ด์ค์ ์ํ๋ ์์
- KIND: ๊ฐ์ฒด ์คํค๋ง
๋์ปค ๋ฐ์คํฌํฑ์ผ๋ก ์ฟ ๋ฒ๋คํฐ์ค๋ฅผ ์ฌ์ฉํ๋ค๋ฉด ์๋์ผ๋ก kubeconfig๊ฐ ์ค์ ๋ฉ๋๋ค. ๋ค์ ๋ช ๋ น์ ์คํํด ์ฌ์ฉํ ์ ์์ต๋๋ค
% kubectl config use-context docker-desktop
๋ฌผ๋ก , --kubeconfig ์ต์ ์ผ๋ก ๋ค๋ฅธ ์ค์ ํ์ผ์ ์ง์ ํ ์๋ ์์ต๋๋ค.
kubectl -kubeconfig=AWSconfig get pods
์ด๋ ๋ค์ค ํฌ๋ฌ์คํฐ์ ๋ค๋ฅธ ์ธ์ฆ/ํด๋ฌ์คํฐ ์ ๋ณด๋ก ์ ๊ทผํ ๋ ์ฌ์ฉํฉ๋๋ค.
Kubespray๋ก ํด๋ฌ์คํฐ๋ฅผ ๊ตฌ์ฑํ๋ค๋ฉด ๋จผ์ ๋ง์คํฐ ๋ ธ๋์ ์ง์ ์ ๊ทผํด ~/.kube/config ๋ด์ฉ์ ํด๋ฌ์คํฐ ์ธ๋ถ์ ์ฌ์ฉ์ ์ปดํจํฐ ~/.kube/config์ ๊ทธ๋๋ก ๋ณต์ฌํด ๊ด๋ฆฌ์ ๊ถํ์ผ๋ก kubespray ํด๋ฌ์คํฐ ๊ตฌ์ฑ์ ์ฌ์ฉํ ์ ์์ต๋๋ค.
3.1.6 ์๋ ์์ฑ
kubectl์ bash zsh์์์ ์๋์์ฑ์ ๊ณต์์ ์ผ๋ก ์ง์ํฉ๋๋ค.
% echo 'source <(kubectl completion bash)' >>~/.bashrc
% echo 'source <(kubectl completion zsh)' >>~/.zshrc
3.2 ๋ํ๋ก์ด๋จผํธ๋ฅผ ์ด์ฉํด ์ปจํ ์ด๋ ์คํํ๊ธฐ
์ฟ ๋ฒ๋คํฐ์ค๋ฅผ ์ด์ฉํด์ ์ปจํ ์ด๋๋ฅผ ์คํํ๋ ๋ฐฉ๋ฒ์๋ ๋๊ฐ์ง๊ฐ ์์ต๋๋ค.
- kubectl run ๋ช ๋ น์ผ๋ก ์ง์ ์ปจํ ์ด๋๋ฅผ ์คํํ๋ ๊ฒ
- ์ปจํ ์ด๋ ์ค์ ์ฌํญ์ ๋ด์ yaml ํ์์ ํ ํ๋ฆฟ์ผ๋ก ์ปจํ ์ด๋๋ฅผ ์คํํ๋ ๊ฒ
ํนํ ํ ํ๋ฆฟ์ผ๋ก ์ปจํ ์ด๋๋ฅผ ๊ด๋ฆฌํ๋ฉด ๋ฒ์ ๊ด๋ฆฌ ์์คํ ๊ณผ ์ฐ๋ํด์ ์์ ์ ์ ๋ณ๋ ์ฌํญ์ ์ถ์ ํ๊ธฐ ์ฝ๋ค๋ ์ฅ์ ์ด ์์ต๋๋ค.
3.2.1 kubectl run์ผ๋ก ์ปจํ ์ด๋ ์คํํ๊ธฐ
deployment๋ฅผ ์ด์ฉํด ์ปจํ ์ด๋๋ฅผ ์คํํฉ๋๋ค.
% kubectl create deployment hello-node --image=registry.k8s.io/e2e-test-images/agnhost:2.39 -- /agnhost netexec --http-port=8080
deployment.apps/hello-node created
๋ค์์ ๋ช ๋ น์ผ๋ก deployment์ ์ํ๋ฅผ ํ์ธํฉ๋๋ค.
% kubectl get deployments
NAME READY UP-TO-DATE AVAILABLE AGE
hello-node 1/1 1 1 11s
๋ค์์ ๋ช ๋ น์ผ๋ก ์ปจํ ์ด๋๊ฐ ์ ๋๋ก ์คํ๋๋์ง ํ์ธํฉ๋๋ค.
% kubectl get pods
NAME READY STATUS RESTARTS AGE
hello-node-67949d9db-2h4br 1/1 Running 0 96s
๋ค์์ ๋ช ๋ น์ ์ฌ์ฉํ์ฌ ์คํ์ค์ธ ํ๋ ๊ฐ์๋ฅผ ๋๋ฆด ์ ์์ต๋๋ค. ์ดํ get deployments ๋ช ๋ น์ผ๋ก ํ์ธํ๋ฉด ํ๋๊ฐ 2๊ฐ๋ก ์ฆ๊ฐ๋ ๊ฒ์ ํ์ธํ ์ ์์ต๋๋ค.
% kubectl scale deploy hello-node --replicas=2
deployment.apps/hello-node scaled
3.2.2 ํ ํ๋ฆฟ์ผ๋ก ์ปจํ ์ด๋ ์คํํ๊ธฐ
์ปจํ ์ด๋ ์ค์ ์ฌํญ์ ๋ด์ .yaml ํ์ผ์ ๋ง๋ ํ ๋ค์์ ๋ช ๋ น์ ํตํด ํ๋๋ฅผ ์คํํ ์ ์์ต๋๋ค.
% kubectl apply -f <ํ์ผ์ด๋ฆ>.yaml
3.3 ํด๋ฌ์คํฐ ์ธ๋ถ์์ ํด๋ฌ์คํฐ ์ ์ฑ์ ์ ๊ทผํ๊ธฐ
์คํ๋ ์ปจํ ์ด๋๋ฅผ ์๋น์ค๋ก ์คํ์์ผ๋ณด๋๋ก ํ๊ฒ ์ต๋๋ค.
% kubectl expose deployment hello-node --type=LoadBalancer --port=8080
service/hello-node exposed
% kubectl get service
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
hello-node LoadBalancer 10.110.186.126 localhost 8080:32568/TCP 20m
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 28d
๋ค์์ ๋ช ๋ น์ ํตํด ์ข ๋ ์์ธํ ๋ด์ฉ์ ํ์ธํ ์ ์์ต๋๋ค.
% kubectl describe service hello-node
Name: hello-node
Namespace: default
Labels: app=hello-node
Annotations: <none>
Selector: app=hello-node
Type: LoadBalancer
IP Family Policy: SingleStack
IP Families: IPv4
IP: 10.110.186.126
IPs: 10.110.186.126
LoadBalancer Ingress: localhost
Port: <unset> 8080/TCP
TargetPort: 8080/TCP
NodePort: <unset> 32568/TCP
Endpoints: 10.1.0.16:8080,10.1.0.22:8080
Session Affinity: None
External Traffic Policy: Cluster
Events: <none>
์ดํ TargetPort์ ํด๋นํ๋ ํฌํธ๋ก ์ ์ํ๋ฉด ์ปจํ ์ด๋์ ์ ๊ทผํ ์ ์์ต๋๋ค.
์ฐธ๊ณ
- ์ ์์ฒ, ํ์์ฉ, ์ ๊ฒฝ๋ก, ๊ณต์ฉ์ค. ใ์ฟ ๋ฒ๋คํฐ์ค ์ ๋ฌธ: 90๊ฐ์ง ์์ ๋ก ๋ฐฐ์ฐ๋ ์ปจํ ์ด๋ ๊ด๋ฆฌ ์๋ํ ํ์คใ. ์ฎ๊ธด์ด(์ญ). ๋์๋ถ์ค(๋์books), 2020.01.
- [Github] kubernetes-book-sample: https://github.com/arisu1000/kubernetes-book-sample
- [Dockerhub] simple-container-app: https://hub.docker.com/r/arisu1000/simple-container-app
- [Official Docs] Kubespray: https://kubespray.io/#/
- [Official Docs] Hello Minikube: https://kubernetes.io/docs/tutorials/hello-minikube/
- [POSIX/GNU] Program Argument Syntax Conventions: https://www.gnu.org/software/libc/manual/html_node/Argument-Syntax.html