[Retry, k8s] 02. 워크로드 API - 파드(Pod)
카테고리: KUBERNETES
태그: kubernetes
[Retry, k8s] 02. 워크로드 API - 파드(Pod)
🔔 파드(Pod)
쿠버네티스에서 배포할 수 있는 가장 작은 단위로 파드는 한 개 이상의 컨테이너와 스토리지, 네트워크 속성으로 구성되며, 같은 파드에 포함된 컨테이너끼리는 네트워크적으로 격리되어 있지 않고 IP 주소를 공유한다. (즉, 컨테이너가 두 개 들어 있는 파드를 생성한 경우, 두 컨테이너는 같은 IP 주소를 가진다 따라서 파드 내부의 컨테이너는 서로 localhost로 통신할 수 있다.)
📜 파드 생성
cat <<EOF > sample-pod.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-pod
spec:
containers:
- name: nginx-container
image: nginx:1.16
EOF
# 파드 생성
$ kubectl apply -f sample-pod.yaml
pod/sample-pod created
# 파드 목록 표시
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
sample-pod 1/1 Running 0 14s
# 파드 상세 정보 표시
$ kubectl get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
sample-pod 1/1 Running 0 30s 10.44.0.1 k8s-node01 <none> <none>
📜 두 개의 컨테이너를 포함한 파드 생성
【두 개의 컨테이너를 가진 파드 예제】
cat <<EOF > sample-2pod.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-2pod
spec:
containers:
- name: nginx-container
image: nginx:1.16
- name: redis-container
image: redis:3.2
EOF
# 두 개의 컨테이너를 포함한 파드 생성
$ kubectl apply -f sample-2pod.yaml
pod/sample-2pod created
# 두 개의 컨테이너를 포함한 파드 확인
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
sample-2pod 2/2 Running 0 14s
【같은 포틀를 사용하는 두 개의 컨테이너를 가진 파드 예제】
cat<<EOF > sample-2pod-fail.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-2pod-fail
spec:
containers:
- name: nginx-container-112
image: nginx:1.16
- name: nginx-container-113
image: nginx:1.17
EOF
# 포트 충돌이 있는 파드 생성
$ kubectl apply -f sample-2pod-fail.yaml
pod/sample-2pod-fail created
# 파드 상태가 에러임을 확인
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
sample-2pod-fail 1/2 Error 0 14s
# 파드 로그 확인
$ kubectl logs sample-2pod-fail -c nginx-container-113
2023/03/14 10:01:49 [emerg] 1#1: bind() to 0.0.0.0:80 failed (98: Address already in use)
nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use)
📜 컨테이너에 접근 & 명령어 실행
【컨테이너 접근】
# 컨테이너에서 /bin/bash 실행
$ kubectl exec -it sample-pod -- /bin/bash
root@sample-pod:/#
# 확인 작업에 필요한 패키지 설치
root@sample-pod:/# apt update && apt -y install iproute2 procps
# 컨테이너 내부에서 IP 주소 확인
root@sample-pod:/# ip addr
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
21: eth0@if22: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1376 qdisc noqueue state UP group default
link/ether ee:8b:41:e9:e3:f2 brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 10.44.0.1/12 brd 10.47.255.255 scope global eth0
valid_lft forever preferred_lft forever
# 컨테이너 내부에서 바인드(listen)하는 포트 확인
root@sample-pod:/# root@sample-pod:/# ss -napt
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 511 0.0.0.0:80 0.0.0.0:* users:(("nginx",pid=1,fd=6))
TIME-WAIT 0 0 10.44.0.1:45618 151.101.110.132:80
TIME-WAIT 0 0 10.44.0.1:35726 151.101.66.132:80
# 컨테이너 내부에서 프로세스 확인
root@sample-pod:/# ps aux
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
root 1 0.0 0.1 10628 5492 ? Ss 09:52 0:00 nginx: master process nginx -g daemon off;
nginx 6 0.0 0.0 11132 2676 ? S 09:52 0:00 nginx: worker process
root 7 0.0 0.1 3872 3276 pts/0 Ss 10:07 0:00 /bin/bash
root 462 0.0 0.0 7644 2756 pts/0 R+ 10:11 0:00 ps aux
【컨테이너에서 명령 실행】
# 컨테이너에서 ls 명령 실행
$ kubectl exec -it sample-pod -- /bin/ls
bin dev home lib64 mnt proc run srv tmp var
boot etc lib media opt root sbin sys usr
# 다수의 컨테이너를 포함한 파드의 경우, 특정 컨테이너 지정
$ kubectl exec -it sample-2pod -c nginx-container -- /bin/ls
bin dev home lib64 mnt proc run srv tmp var
boot etc lib media opt root sbin sys usr
# 옵션을 포함한 명령어 실행
$ kubectl exec -it sample-pod -- /bin/ls --all --classify
./ .dockerenv* boot/ etc/ lib/ media/ opt/ root/ sbin/ sys/ usr/
../ bin/ dev/ home/ lib64/ mnt/ proc/ run/ srv/ tmp/ var/
# 파이프 등 특정 문자열을 포함한 경우
$ kubectl exec -it sample-pod -- /bin/bash -c "ls -a --classify | grep lib"
lib/
lib64/
📜 호스트의 네트워크 구성을 사용한 파드 기동
hostNetwork를 사용한 파드는 쿠버네티스 노드의 IP 주소를 사용하는 관계로 포트번호 충돌을 방지하기 위해 기본적으로 사용되지는 않는다.
cat << EOF > sample-hostnetwork.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-hostnetwork
spec:
hostNetwork: true
containers:
- name: nginx-container
image: nginx:1.16
EOF
# 파드의 IP 주소 확인
$ kubectl get pod sample-hostnetwork -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
sample-hostnetwork 1/1 Running 0 9s 192.168.219.101 k8s-node01 <none> <none>
# 파드가 기동 중인 노드의 IP 주소 확인
$ kubectl get node -o wide
NAME STATUS ROLES AGE VERSION INTERNAL-IP EXTERNAL-IP OS-IMAGE KERNEL-VERSION CONTAINER-RUNTIME
k8s-master01 Ready control-plane 25h v1.26.2 192.168.219.10 <none> Ubuntu 22.04.2 LTS 5.15.0-67-generic docker://23.0.1
k8s-node01 Ready <none> 25h v1.26.2 192.168.219.101 <none> Ubuntu 22.04.2 LTS 5.15.0-67-generic docker://23.0.1
k8s-node02 Ready <none> 25h v1.26.2 192.168.219.102 <none> Ubuntu 22.04.2 LTS 5.15.0-67-generic docker://23.0.1
# 파드의 호스트명 확인
$ kubectl exec -it sample-hostnetwork -- hostname
k8s-node01
# 파드의 DNS 설정 확인
$ kubectl exec -it sample-hostnetwork -- cat /etc/resolv.conf
nameserver 168.126.63.1
nameserver 8.8.8.8
📜 파드 DNS 설정
【ClusterFirst(기본값)】 : 클러스터 내부 DNS에 질의하여 해석되지 않으면 업스트림에 질의함
cat <<EOF > sample-dnspolicy-clusterfirst.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-dnspolicy-clusterfirst
spec:
dnsPolicy: ClusterFirst
containers:
- name: nginx-container
image: nginx:1.16
EOF
# 컨테이너 내부의 DNS 설정 파일 /etc/resolv.conf를 표시
$ kubectl exec -it sample-dnspolicy-clusterfirst -- cat /etc/resolv.conf
nameserver 10.96.0.10
search default.svc.cluster.local svc.cluster.local cluster.local
options ndots:5
# 클러스터 내부의 DNS Service에 할당된 IP 주소를 확인
root@k8s-master01:~/kube_test# kubectl get services -n kube-system
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kube-dns ClusterIP 10.96.0.10 <none> 53/UDP,53/TCP,9153/TCP 25h
【None】 : 파드 정의 내에서 정적으로 설정
cat <<EOF > sample-dnspolicy-none.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-dnspolicy-none
spec:
dnsPolicy: None
dnsConfig:
nameservers:
- 8.8.8.8
- 8.8.4.4
searches:
- example.com
options:
- name: ndots
value: "5"
containers:
- name: nginx-container
image: nginx:1.16
EOF
# 컨테이너 내부의 DNS 설정 파일 /etc/resolv.conf를 표시
$ kubectl exec -it sample-dnspolicy-none -- cat /etc/resolv.conf
nameserver 8.8.8.8
nameserver 8.8.4.4
search example.com
options ndots:5
【Default】 : 파드가 기동하는 쿠버네티스 노드의 /etc/resolv.conf를 상속받는다.
cat <<EOF > sample-dnspolicy-default.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-dnspolicy-default
spec:
dnsPolicy: Default
containers:
- name: nginx-container
image: nginx:1.16
EOF
# 컨테이너 내부의 DNS 설정 파일 /etc/resolv.conf를 표시
$ kubectl exec -it sample-dnspolicy-default -- cat /etc/resolv.conf
nameserver 168.126.63.1
nameserver 8.8.8.8
【ClusterFirstWithHostNet】 : ClusterFirst의 동작과 같다(hostNetwork 사용 시 설정)
cat <<EOF > sample-dnspolicy-clusterfirstwithhostnet.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-dnspolicy-clusterfirstwithhostnet
spec:
dnsPolicy: ClusterFirstWithHostNet
hostNetwork: true
containers:
- name: nginx-container
image: nginx:1.16
EOF
# 컨테이너 내부의 DNS 설정 파일 /etc/resolv.conf를 표시
$ kubectl exec -it sample-dnspolicy-clusterfirstwithhostnet -- cat /etc/resolv.conf
nameserver 10.96.0.10
search default.svc.cluster.local svc.cluster.local cluster.local
options ndots:5
📜 정적 호스트명 해석 설정(/etc/hosts)
cat <<EOF > sample-hostaliases.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-hostaliases
spec:
containers:
- name: nginx-container
image: nginx:1.16
hostAliases:
- ip: 8.8.8.8
hostnames:
- google-dns
- google-public-dns
EOF
$ kubectl exec -it sample-hostaliases -- cat /etc/hosts
# Kubernetes-managed hosts file.
127.0.0.1 localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
fe00::0 ip6-mcastprefix
fe00::1 ip6-allnodes
fe00::2 ip6-allrouters
10.36.0.1 sample-hostaliases
# Entries added by HostAliases.
8.8.8.8 google-dns google-public-dns
📜 작업 디렉터리 설정
cat <<EOF > sample-workingdir.yaml
apiVersion: v1
kind: Pod
metadata:
name: sample-workingdir
spec:
containers:
- name: nginx-container
image: nginx:1.16
workingDir: /tmp
EOF
$ kubectl exec -it sample-pod -- pwd
/
$ kubectl exec -it sample-workingdir -- pwd
/tmp
댓글 남기기