버전 비교

  • 이 줄이 추가되었습니다.
  • 이 줄이 삭제되었습니다.
  • 서식이 변경되었습니다.
목차
minLevel1
maxLevel7

...

1. 서비스

1.1 클러스터 외부 트래픽 받는 방법

Nodeport

0fd0c795-7056-4d12-8c6d-4fdaa0b6c796.pngImage Removed0fd0c795-7056-4d12-8c6d-4fdaa0b6c796.pngImage Added

Load Balancer

f9ecd753-5b3e-45ae-8b79-006bba457411.pngImage Removedf9ecd753-5b3e-45ae-8b79-006bba457411.pngImage Added

Ingress

a14fa09f-03a3-49eb-8c7b-b324cdf5b78b.pngImage RemovedImage Added

1.2 서비스 개념

파드를 통해 사용자에게 서비스를 제공을 할 수 있으나, 파드에 장애가 발생했을 경우 서비스에 가용성을 보장할 수가 없기 때문에, Service를 통해 가용성을 보장합니다

...

  • 서비스를 클러스터 내부 IP에 노출합니다.

  • 클러스터 내에서만 서비스에 도달할 수 있으며, 서비스 타입의 기본값입니다.

6/00-svc-clusterip.yaml

코드 블럭
apiVersion: v1
kind: Pod
metadata:
  name: nginx
  labels:
    app.kubernetes.io/name: proxy
spec:
  containers:
  - name: nginx
    image: nginx:stable
    ports:
      - containerPort: 80
        name: http-web-svc

---
apiVersion: v1
kind: Service
metadata:
  name: nginx-service
spec:
  selector:
    app.kubernetes.io/name: proxy
  ports:
  - name: name-of-service-port
    protocol: TCP
    port: 80
    targetPort: http-web-svc

...

  • 고정포트로 각 노드의 IP에 서비스를 노출합니다.

  • NodePort 서비스가 라우팅되는 ClusterIP가 자동으로 생성되며 NodeIP:NodePort를 요청하며, 서비스 외수에서 NodePort 서비스에 접속할 수 있습니다.

코드 블럭
---    root@cp-k8s:~/2024_k8s/edu/6# k get svc
NAME            TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
kubernetes      ClusterIP   10.96.0.1       <none>        443/TCP   3h16m
nginx-service   ClusterIP   10.103.98.179   <none>        80/TCP    99s
root@cp-k8s:~/2024_k8s/edu/6# curl 10.103.98.179
<!DOCTYPE html>
apiVersion: apps/v1                                                                           
kind: Deployment<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>

(2) NodePort

  • 고정포트로 각 노드의 IP에 서비스를 노출합니다.

  • NodePort 서비스가 라우팅되는 ClusterIP가 자동으로 생성되며 NodeIP:NodePort를 요청하며, 서비스 외수에서 NodePort 서비스에 접속할 수 있습니다.

6/01-svc-nodeport.yaml

코드 블럭
apiVersion: apps/v1                                                                           
  
metadatakind: Deployment                                                                              
metadata:        name: nginx-deployment                                                                         labels:   
  name: nginx-deployment                                                                      
  labels:          app: nginx                                                                          
     
specapp: nginx                                                                                
spec:          replicas: 1                                                                              
  
  selectorreplicas: 1                                                                                 
  selector:   matchLabels:                                                                                
    appmatchLabels: nginx                                                                             
      app: nginx                                                                              
  template:                                                                                   
    metadata:                                                                                 
      labels:                                                                                 
        app: nginx                                                                            
    spec:                                                                                     
      containers:                                                                             
      - name: nginx                                                                           
        image: nginx                                                                          
        ports:                                                                                
        - containerPort: 80                                                                   
---                                                                                           
apiVersion: v1                                                                                
kind: Service                                                                                 
metadata:                                                                                     
  name: my-service-nodeport                                                                   
spec:                                                                                         
  type: NodePort                                                                              
  selector:                                                                                   
    app: nginx                                                                                
  ports:                                                                                      
      # 기본적으로 그리고 편의상 `targetPort` 는 `port` 필드와 동일한 값으로 설정된다.                           
    - port: 80                                                                                
      targetPort: 80                                                                          
      # 선택적 필드                                                                               
      # 기본적으로 그리고 편의상 쿠버네티스 컨트롤 플레인은 포트 범위에서 할당한다(기본값: 30000-32767)                   
      nodePort: 30007

(3) LoadBalancer

  • 클라우드 공급자의 로드 밸런서를 사용하여 서비스를 외부에 노출시킵니다.

  • 클러스터 외부 IP를 가지고 있기 때문에, 클러스터 외부에서 접근 가능합니다.

  • 외부 로드 밸런서가 라우팅되는 NodePort와 ClusterIP 서비스가 자동으로 생성됩니다.

  • 프라이빗 클라우드 환경에서는 MetalLB를 이용하여 LoadBalancer 타입의 서비스를 이용 할 수 있습니다.

--- apiVersion: apps/v1 kind: Deployment metadata: name: nginx2-deployment labels: app: nginx spec: replicas: 3 selector: matchLabels: app: nginx template: metadata: labels: app: nginx spec: containers: - name: nginx image: nginx ports: - containerPort: 80
코드 블럭
코드 블럭
root@cp-k8s:~/2024_k8s/edu# curl localhost:30007
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
코드 블럭
root@cp-k8s:~/2024_k8s/edu# cat /etc/hosts
127.0.0.1 localhost
192.168.1.10 cp-k8s
192.168.1.101 w1-k8s
192.168.1.102 w2-k8s
192.168.1.103 w3-k8s
root@cp-k8s:~/2024_k8s/edu# curl 192.168.1.102:30007
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

...

(3) LoadBalancer

  • 클라우드 공급자의 로드 밸런서를 사용하여 서비스를 외부에 노출시킵니다.

  • 클러스터 외부 IP를 가지고 있기 때문에, 클러스터 외부에서 접근 가능합니다.

  • 외부 로드 밸런서가 라우팅되는 NodePort와 ClusterIP 서비스가 자동으로 생성됩니다.

  • 프라이빗 클라우드 환경에서는 MetalLB를 이용하여 LoadBalancer 타입의 서비스를 이용 할 수 있습니다.

6/02-svc-loadbalancer.yaml

코드 블럭
---
apiVersion: apps/v1
kind: ServiceDeployment
metadata:
  name: nginx2-servicedeployment
spec:  labels:
type: LoadBalancer   selectorapp: nginx
spec:
  appreplicas: nginx3
  portsselector:
    - protocol: TCPmatchLabels:
      app: nginx
  template:
    metadata:
      portlabels:
 8088       targetPortapp: 80

(4) ExternalName

  • 값과 함께 CNAME 레코드를 리턴하여, 서비스를 externalName 필드의 콘텐츠에 매핑합니다.

  • 클러스터 내에서 외부 서비스를 이름으로 참조할 수 있게 해주는 서비스 타입입니다.

  • 내부 클러스터에서 외부 DNS 이름을 내부 서비스로 변환하여 접근 가능하게 됩니다.

코드 블럭
apiVersion: v1
kind: Service
metadata:
  name: my-database
spec:
  type: ExternalName
  externalName: db.example.com

  • 이 서비스는 my-database라는 이름으로 정의되며, 실제로는 db.example.com에 대한 DNS 쿼리로 변환됩니다.

  • 클러스터 내부의 애플리케이션에서 my-database라는 이름을 사용하여 외부의 db.example.com에 접근할 수 있습니다.

1.3 MetalLB 설치(Private 환경에서의 로드 밸런서)

(1) metallb 네임스페이스 생성

코드 블럭
[root@m-k8s vagrant]# kubectl create ns metallb-system

(2) metallb 설치

코드 블럭
[root@m-k8s vagrant]# kubectl apply -f https://raw.githubusercontent.com/metallb/metallb/v0.13.11/config/manifests/metallb-native.yaml
namespace/metallb-system configured
customresourcedefinition.apiextensions.k8s.io/addresspools.metallb.io created
customresourcedefinition.apiextensions.k8s.io/bfdprofiles.metallb.io created
customresourcedefinition.apiextensions.k8s.io/bgpadvertisements.metallb.io created
customresourcedefinition.apiextensions.k8s.io/bgppeers.metallb.io created
customresourcedefinition.apiextensions.k8s.io/communities.metallb.io created
customresourcedefinition.apiextensions.k8s.io/ipaddresspools.metallb.io created
customresourcedefinition.apiextensions.k8s.io/l2advertisements.metallb.io created
serviceaccount/controller created
serviceaccount/speaker created
role.rbac.authorization.k8s.io/controller created
role.rbac.authorization.k8s.io/pod-lister created
clusterrole.rbac.authorization.k8s.io/metallb-system:controller created
clusterrole.rbac.authorization.k8s.io/metallb-system:speaker created
rolebinding.rbac.authorization.k8s.io/controller created
rolebinding.rbac.authorization.k8s.io/pod-lister created
clusterrolebinding.rbac.authorization.k8s.io/metallb-system:controller created
clusterrolebinding.rbac.authorization.k8s.io/metallb-system:speaker created
configmap/metallb-excludel2 created

(3) 설치 확인

코드 블럭
[root@m-k8s vagrant]# kubectl get all -n metallb-system
NAME nginx
    spec:
      containers:
      - name: nginx
        image: nginx
        ports:
        - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: nginx2-service
spec:
  type: LoadBalancer
  selector:
    app: nginx
  ports:
    - protocol: TCP
      port: 8088
      targetPort: 80
코드 블럭
root@cp-k8s:~/2024_k8s/edu/6# k get svc
NAME                  TYPE           CLUSTER-IP       READYEXTERNAL-IP   STATUS PORT(S)   RESTARTS   AGE pod/controller-5567fb94fd-mn6jg   1/1AGE
kubernetes    Running   0     ClusterIP     2m4s
pod/speaker-2pxpd 10.96.0.1        <none>         1443/1TCP     Running   0  3h22m
my-service-nodeport   NodePort    2m3s pod/speaker-lpnmf  10.100.38.132    <none>           1/180:30007/TCP     Running5m1s
nginx-service  0       ClusterIP   2m3s pod/speaker-q8hvp  10.103.98.179    <none>           180/1TCP     Running   0   8m1s
nginx2-service      2m3s  NAMELoadBalancer   10.100.170.165   192.168.1.11   8088:30843/TCP   7s

image-20240523-131147.pngImage Addedimage-20240523-131207.pngImage Added

(4) ExternalName

  • 값과 함께 CNAME 레코드를 리턴하여, 서비스를 externalName 필드의 콘텐츠에 매핑합니다.

  • 클러스터 내에서 외부 서비스를 이름으로 참조할 수 있게 해주는 서비스 타입입니다.

  • 내부 클러스터에서 외부 DNS 이름을 내부 서비스로 변환하여 접근 가능하게 됩니다.

6/03-svc-externalname.yaml

코드 블럭
apiVersion: v1
kind: Service
metadata:
  name: my-database
spec:
TYPE  type: ExternalName
    CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
service/webhook-service   ClusterIP   10.108.47.177   <none>        443/TCP   2m4s

NAME                     DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTORexternalName: db.example.com
  • 이 서비스는 my-database라는 이름으로 정의되며, 실제로는 db.example.com에 대한 DNS 쿼리로 변환됩니다.

  • 클러스터 내부의 애플리케이션에서 my-database라는 이름을 사용하여 외부의 db.example.com에 접근할 수 있습니다.

1.3 MetalLB 설치(Private 환경에서의 로드 밸런서)

(1) metallb 네임스페이스 생성 (이미 생성해 두었음)

코드 블럭
[root@m-k8s vagrant]# kubectl create ns metallb-system

(2) metallb 설치 (이미 생성해 두었음)

6/04-metallb-install.txt

코드 블럭
[root@m-k8s vagrant]# kubectl apply -f https://raw.githubusercontent.com/metallb/metallb/v0.13.11/config/manifests/metallb-native.yaml
namespace/metallb-system configured
customresourcedefinition.apiextensions.k8s.io/addresspools.metallb.io created
customresourcedefinition.apiextensions.k8s.io/bfdprofiles.metallb.io created
customresourcedefinition.apiextensions.k8s.io/bgpadvertisements.metallb.io created
customresourcedefinition.apiextensions.k8s.io/bgppeers.metallb.io created
customresourcedefinition.apiextensions.k8s.io/communities.metallb.io created
customresourcedefinition.apiextensions.k8s.io/ipaddresspools.metallb.io created
customresourcedefinition.apiextensions.k8s.io/l2advertisements.metallb.io created
serviceaccount/controller created
serviceaccount/speaker created
role.rbac.authorization.k8s.io/controller created
role.rbac.authorization.k8s.io/pod-lister created
clusterrole.rbac.authorization.k8s.io/metallb-system:controller created
clusterrole.rbac.authorization.k8s.io/metallb-system:speaker created
rolebinding.rbac.authorization.k8s.io/controller created
rolebinding.rbac.authorization.k8s.io/pod-lister created
clusterrolebinding.rbac.authorization.k8s.io/metallb-system:controller created
clusterrolebinding.rbac.authorization.k8s.io/metallb-system:speaker created
configmap/metallb-excludel2 created

(3) 설치 확인

코드 블럭
[root@m-k8s vagrant]# kubectl get all -n metallb-system
NAME                     AGE daemonset.apps/speaker   3     READY   STATUS 3   RESTARTS   AGE
pod/controller-5567fb94fd-mn6jg  3 1/1     Running 3  0          32m4s
pod/speaker-2pxpd          kubernetes.io/os=linux   2m4s  NAME  1/1     Running   0          2m3s
pod/speaker-lpnmf    READY   UP-TO-DATE   AVAILABLE   AGE deployment.apps/controller   1/1     1Running   0         1 2m3s
pod/speaker-q8hvp         2m4s  NAME      1/1     Running   0          2m3s

NAME          DESIRED   CURRENT   READY   AGE replicaset.apps/controller-5567fb94fd  TYPE 1       CLUSTER-IP  1    EXTERNAL-IP   PORT(S)   1AGE
service/webhook-service   ClusterIP   2m4s
[root@m-k8s vagrant]# kubectl get pod -n metallb-system -o wide
NAME      10.108.47.177   <none>        443/TCP   2m4s

NAME                    READY DESIRED  STATUS CURRENT   RESTARTSREADY   AGEUP-TO-DATE   AVAILABLE  IP NODE SELECTOR            AGE
NODEdaemonset.apps/speaker   3  NOMINATED NODE   READINESS GATES controller-5567fb94fd-mn6jg 3  1/1     Running  3 0      3    2m13s   172.16.221.164   w1-k8s  3 <none>          kubernetes.io/os=linux <none> speaker-2pxpd 2m4s

NAME              1/1     Running   0   READY   UP-TO-DATE   AVAILABLE 2m12s  AGE
192.168.1.102deployment.apps/controller   1/1     1            1      w2-k8s   <none>  2m4s

NAME       <none> speaker-lpnmf                 1/1     Running   0   DESIRED   CURRENT   READY 2m12s  AGE
192.168.1.10replicaset.apps/controller-5567fb94fd   1         1        m-k8s 1   <none>    2m4s
[root@m-k8s vagrant]# kubectl get pod -n <none>metallb-system speaker-q8hvpo wide
NAME               1/1     Running   0   READY   STATUS    2m12sRESTARTS   192.168.1.101AGE    w1-k8s IP  <none>           <none>

(4) IPAddressPool 생성

  • 외부로 노출할 VIP에 대한 범위를 지정합니다.

  • 아이피 대역은 실제 External IP로 사용할 IP를 적어줍니다. (노드에서 할당이 가능하여야 함)

코드 블럭
apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: first-pool
  namespace: metallb-system
spec:
  addresses:
  - 192.168.1.150-192.168.1.200
---
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: first-pool-advertisement
  namespace: metallb-system
spec:
  ipAddressPools:
  - first-pool
  • 만든 configamap 생성

코드 블럭
kubectl apply -f 008.metalLB-addresspool.yaml
configmap/config created

정보

Loadbalancer 타입으로 서비스를 생성해보고, External IP가 할당되었는지 확인해봅니다.

2. Ingress

2.1 Ingress Controller

  • 인그레스 리소스를 해석하고, 이를 실제 네트워크 트래픽 관리로 변환하는 쿠버네티스 구성 요소입니다.

  • 다양한 종류의 인그레스 컨트롤러가 존재하며, 각 컨트롤러는 특정 구현 및 기능을 제공합니다.

2.2 Ingress

  • 클러스터 내의 서비스에 대한 외부 접근을 관리하는 API 오브젝트이며, 일반적으로 HTTP를 관리합니다.

  • 인그레스는 클러스터 외부에서 클러스터 내부 서비스로 HTTP와 HTTPS 경로를 노출시킵니다.

  • 인그레스 컨트롤러가 있어야 인그레스를 충족할 수 있으며, 인그레스 리소스만 생성한다면 효과가 없습니다.

    • 대표적인 인그레스 컨트롤러: ingress-nginx

...

(1) Ingress의 필요성

  • ingress를 이용하면 한 가지의 외부 Service로 도메인, 서브도메인 기반의 여러가지 백엔드 서비스에 연결 할 수 있는 장점이 있습니다.

  • ingress를 이용하면 ClusterIP 타입으로 외부에서 접근 할 수 있습니다.

  • ingress는 도메인기반, 서브도메인기반 등을 이용할 수 있으며 SSL을 지원합니다.

(2) Nginx Ingress Controller 설치

  • Private 환경에서 인그레스를 사용하기 위해 컨트롤러를 설치합니다.

코드 블럭
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.8.2/deploy/static/provider/cloud/deploy.yaml

namespace/ingress-nginx created
serviceaccount/ingress-nginx created
serviceaccount/ingress-nginx-admission created
role.rbac.authorization.k8s.io/ingress-nginx created
role.rbac.authorization.k8s.io/ingress-nginx-admission created
clusterrole.rbac.authorization.k8s.io/ingress-nginx created
clusterrole.rbac.authorization.k8s.io/ingress-nginx-admission created
rolebinding.rbac.authorization.k8s.io/ingress-nginx created
rolebinding.rbac.authorization.k8s.io/ingress-nginx-admission created
clusterrolebinding.rbac.authorization.k8s.io/ingress-nginx created
clusterrolebinding.rbac.authorization.k8s.io/ingress-nginx-admission created
configmap/ingress-nginx-controller created
service/ingress-nginx-controller created
service/ingress-nginx-controller-admission created
deployment.apps/ingress-nginx-controller created
job.batch/ingress-nginx-admission-create created
job.batch/ingress-nginx-admission-patch created
ingressclass.networking.k8s.io/nginx created
validatingwebhookconfiguration.admissionregistration.k8s.io/ingress-nginx-admission created

 

(3) 서비스 LoadBalancer 타입 설정

  • nginx의 svc는 편의상 이전단계에서 생성한 LoadBalancer 타입으로 지정해주도록 합니다

코드 블럭
kubectl edit svc/ingress-nginx-controller -n ingress-nginx (version이 올라오면서 LoadBalncer가 바로 잡힘)
spec:
  type: LoadBalancer // ClusterIP -> LoadBalancer  확인

kubectl get svc -A
ingress-nginx    ingress-nginx-controller             LoadBalancer   10.109.69.139    192.168.1.151   80:31100/TCP,443:31761/TCP   83s

(4) 생성된 lb의 Externel IP를 이용하여 통신을 시도 합니다.

  • 현재 연결된 백엔드 svc가 없으므로 404 Not Found를 확인 할 수 있습니다.

코드 블럭
C:\Users\khoj>curl 192.168.1.151
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx</center>
</body>
</html>

(5) Ingress 백엔드로 사용 할 서비스 생성

  • 테스트를 위하여 총 2가지의 pod와 ClusterIP 타입의 Service를 생성합니다.

  • 아래 deployment는 podname을 확인하도록 nginx 가 아닌 echoserver 이미지를 사용 합니다.

009.nginx.yml

코드 블럭
languageyaml
--- 
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx1-deployment
spec:
  selector:
    matchLabels:
      app: nginx1
  replicas: 1
  template:
    metadata:
      labels:
        app: nginx1
    spec:
      containers:
        - name: my-echo
          image: jmalloc/echo-server

---
 
apiVersion: v1
kind: Service
metadata:
  name: nginx-service-clusterip
  labels:
    name: nginx-service-clusterip
spec:
  type: ClusterIP
  ports:
    - port: 80       # Cluster IP
      targetPort: 8080  # Application port
      protocol: TCP
      name: http
  selector:
    app: nginx1
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx2-deployment
spec:
  selector:
    matchLabels:
      app: nginx2
  replicas: 1
  template:
    metadata:
      labels:
        app: nginx2
    spec:
      containers:
        - name: my-echo
          image: jmalloc/echo-server

---
 
apiVersion: v1
kind: Service
metadata:
  name: nginx2-service-clusterip
  labels:
    name: nginx2-service-clusterip
spec:
  type: ClusterIP
  ports:
    - port: 80       # Cluster IP
      targetPort: 8080  # Application port
      protocol: TCP
      name: http
  selector:
    app: nginx2

(6) 위에서 만든 yaml을 이용하여 pod 및 svc를 생성 합니다

코드 블럭
[root@m-k8s vagrant]# k apply -f 009.nginx.yml 
deployment.apps/nginx1-deployment created
service/nginx-service-clusterip created
deployment.apps/nginx2-deployment created
service/nginx2-service-clusterip created
  • pod와 Service가 잘 생성되었으며, 생성된 Service로 통신시도 시 연결된 Pod 이름을 확인합니다.

코드 블럭


kubectl get svc
NAME                           TYPE           CLUSTER-IP       EXTERNAL-IP     PORT(S)        AGE
nginx-service-clusterip    ClusterIP      10.105.151.217   <none>          80/TCP         20s
nginx2-service-clusterip   ClusterIP      10.106.195.22    <none>          80/TCP         20s

kubectl get pod
NAME          NODE     NOMINATED NODE   READINESS GATES
controller-5567fb94fd-mn6jg   1/1     Running   0          2m13s   172.16.221.164   w1-k8s   <none>           <none>
speaker-2pxpd                 1/1     Running   0          2m12s   192.168.1.102    w2-k8s   <none>           <none>
speaker-lpnmf                 1/1     Running   0          2m12s   192.168.1.10     m-k8s    <none>           <none>
speaker-q8hvp                 1/1     Running   0          2m12s   192.168.1.101    w1-k8s   <none>           <none>

(4) IPAddressPool 생성

  • 외부로 노출할 VIP에 대한 범위를 지정합니다.

  • 아이피 대역은 실제 External IP로 사용할 IP를 적어줍니다. (노드에서 할당이 가능하여야 함)

6/05-metallb-ipaddresspool.yaml

코드 블럭
apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: first-pool
  namespace: metallb-system
spec:
  addresses:
  - 192.168.1.150-192.168.1.200
---
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: first-pool-advertisement
  namespace: metallb-system
spec:
  ipAddressPools:
  - first-pool
코드 블럭
root@cp-k8s:~/2024_k8s/edu/6# k get IPAddressPool -n metallb-system
NAME           AUTO ASSIGN   AVOID BUGGY IPS   ADDRESSES
first-pool     true          false             ["192.168.1.150-192.168.1.200"]
  • 생성

코드 블럭
kubectl apply -f 05-metallb-ipaddresspool.yaml
ipaddresspool.metallb.io/first-pool created
l2advertisement.metallb.io/first-pool-advertisement created

정보

Loadbalancer 타입으로 서비스를 생성해보고, External IP가 할당되었는지 확인해봅니다.

...

2. Ingress

2.1 Ingress Controller

  • 인그레스 리소스를 해석하고, 이를 실제 네트워크 트래픽 관리로 변환하는 쿠버네티스 구성 요소입니다.

  • 다양한 종류의 인그레스 컨트롤러가 존재하며, 각 컨트롤러는 특정 구현 및 기능을 제공합니다.

2.2 Ingress

  • 클러스터 내의 서비스에 대한 외부 접근을 관리하는 API 오브젝트이며, 일반적으로 HTTP를 관리합니다.

  • 인그레스는 클러스터 외부에서 클러스터 내부 서비스로 HTTP와 HTTPS 경로를 노출시킵니다.

  • 인그레스 컨트롤러가 있어야 인그레스를 충족할 수 있으며, 인그레스 리소스만 생성한다면 효과가 없습니다.

    • 대표적인 인그레스 컨트롤러: ingress-nginx

...

(1) Ingress의 필요성

  • ingress를 이용하면 한 가지의 외부 Service로 도메인, 서브도메인 기반의 여러가지 백엔드 서비스에 연결 할 수 있는 장점이 있습니다.

  • ingress를 이용하면 ClusterIP 타입으로 외부에서 접근 할 수 있습니다.

  • ingress는 도메인기반, 서브도메인기반 등을 이용할 수 있으며 SSL을 지원합니다.

(2) Nginx Ingress Controller 설치

  • Private 환경에서 인그레스를 사용하기 위해 컨트롤러를 설치합니다.

6/06-ingress-nginx-install.txt

코드 블럭
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.8.2/deploy/static/provider/cloud/deploy.yaml

namespace/ingress-nginx created
serviceaccount/ingress-nginx created
serviceaccount/ingress-nginx-admission created
role.rbac.authorization.k8s.io/ingress-nginx created
role.rbac.authorization.k8s.io/ingress-nginx-admission created
clusterrole.rbac.authorization.k8s.io/ingress-nginx created
clusterrole.rbac.authorization.k8s.io/ingress-nginx-admission created
rolebinding.rbac.authorization.k8s.io/ingress-nginx created
rolebinding.rbac.authorization.k8s.io/ingress-nginx-admission created
clusterrolebinding.rbac.authorization.k8s.io/ingress-nginx created
clusterrolebinding.rbac.authorization.k8s.io/ingress-nginx-admission created
configmap/ingress-nginx-controller created
service/ingress-nginx-controller created
service/ingress-nginx-controller-admission created
deployment.apps/ingress-nginx-controller created
job.batch/ingress-nginx-admission-create created
job.batch/ingress-nginx-admission-patch created
ingressclass.networking.k8s.io/nginx created
validatingwebhookconfiguration.admissionregistration.k8s.io/ingress-nginx-admission created

 

(3) 서비스 LoadBalancer 타입 설정

  • nginx의 svc는 편의상 이전단계에서 생성한 LoadBalancer 타입으로 지정해주도록 합니다

코드 블럭
kubectl edit svc/ingress-nginx-controller -n ingress-nginx (version이 올라오면서 LoadBalncer가 바로 잡힘)
spec:
  type: LoadBalancer // ClusterIP -> LoadBalancer  확인

kubectl get svc -A
ingress-nginx    ingress-nginx-controller             LoadBalancer   10.109.69.139    192.168.1.151   80:31100/TCP,443:31761/TCP   83s

(4) 생성된 lb의 Externel IP를 이용하여 통신을 시도 합니다.

  • 현재 연결된 백엔드 svc가 없으므로 404 Not Found를 확인 할 수 있습니다.

코드 블럭
C:\Users\khoj>curl 192.168.1.151
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx</center>
</body>
</html>

(5) Ingress 백엔드로 사용 할 서비스 생성

  • 테스트를 위하여 총 2가지의 pod와 ClusterIP 타입의 Service를 생성합니다.

  • 아래 deployment는 podname을 확인하도록 nginx 가 아닌 echoserver 이미지를 사용 합니다.

6/07-ingress-backend.yml

코드 블럭
languageyaml
--- 
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx1-deployment
spec:
  selector:
    matchLabels:
      app: nginx1
  replicas: 1
  template:
    metadata:
      labels:
        app: nginx1
    spec:
      containers:
        - name: my-echo
          image: jmalloc/echo-server
---
apiVersion: v1
kind: Service
metadata:
  name: nginx1-service-clusterip
  labels:
    name: nginx1-service-clusterip
spec:
  type: ClusterIP
  ports:
    - port: 80       # Cluster IP
      targetPort: 8080  # Application port
      protocol: TCP
      name: http
  selector:
    app: nginx1
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx2-deployment
spec:
  selector:
    matchLabels:
      app: nginx2
  replicas: 1
  template:
    metadata:
      labels:
        app: nginx2
    spec:
      containers:
        - name: my-echo
          image: jmalloc/echo-server
---
apiVersion: v1
kind: Service
metadata:
  name: nginx2-service-clusterip
  labels:
    name: nginx2-service-clusterip
spec:
  type: READYClusterIP
  STATUS  ports:
   RESTARTS   AGE
nginx1-deployment-545749bf4d-h7qfx port: 80       # Cluster IP
  1/1    targetPort: Running8080  # Application port
0      protocol: TCP
  29s nginx2-deployment-56d6f87fc9-9m7h2   name: http
  selector:
      1/1     Running     0          29s


app: nginx2

(6) 위에서 만든 yaml을 이용하여 pod 및 svc를 생성 합니다

코드 블럭
[root@m-k8s vagrant]# curl 10.105.151.217
Request served by nginx1-deployment-8458b98748-75hlx

GET / HTTP/1.1

Host: 10.105.151.217
Accept: */*
User-Agent: curl/7.29.0

curl 10.98.154.210


[root@m-k8s vagrant]# curl 10.106.195.22
Request served by nginx2-deployment-767fbbfc95-g42jr

GET / HTTP/1.1

Host: 10.106.195.22
Accept: */*
User-Agent: curl/7.29.0

(7) L7기반의 라우팅을 해주는 ingress정책을 생성 합니다

  • ingress svc로 들어온 패킷의 L7레이어 즉 도메인 주소를 체크하여 트래픽을 전달합니다.

    • 도메인 주소가 a.com이라면 nginx-service-clusterip로 연결합니다.

    • 도메인 주소가 b.com이라면 nginx2-service.clusterip로 연결합니다.

009.ing.yaml

코드 블럭
languageyaml
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: ingress
spec:
  ingressClassName: nginx
  rules:
  - host: "a.com"
    http:
      paths:
      - pathType: Prefix
        path: "/"k apply -f 07-ingress-backend.yml
deployment.apps/nginx1-deployment created
service/nginx-service-clusterip created
deployment.apps/nginx2-deployment created
service/nginx2-service-clusterip created

  • pod와 Service가 잘 생성되었으며, 생성된 Service로 통신 시도 시 연결된 Pod 이름을 확인합니다.

코드 블럭
kubectl get svc
NAME                           TYPE           CLUSTER-IP       EXTERNAL-IP     PORT(S)        AGE
nginx1-service-clusterip    ClusterIP      10.105.151.217   <none>          80/TCP         20s
nginx2-service-clusterip backend:  ClusterIP      10.106.195.22   service: <none>          80/TCP  name: nginx-service-clusterip      20s

kubectl get pod
NAME      port:               number: 80   - host: "b.com"     http:       paths:     READY  - pathType:STATUS Prefix     RESTARTS    path: "/"AGE
nginx1-deployment-545749bf4d-h7qfx          backend:    1/1     Running  service:   0          name:29s
nginx2-service-clusteripdeployment-56d6f87fc9-9m7h2              1/1   port:  Running     0          number: 80

(8) 009.ing.yaml을 이용하여 ingress정책을 생성 합니다

코드 블럭
29s


[root@m-k8s ~vagrant]# kubectl create -f 009.ing.yaml
ingress.networking.k8s.io/ingress created

(9) ingress가 제대로 설정되어있는지 확인 합니다.

코드 블럭
[root@m-k8s vagrant]# k get ing
NAME      CLASS    HOSTS         ADDRESS          PORTS   AGE
ingress   nginx   a.com,b.com    172.20.200.101   80      5m23s

(10) 클러스터 외부에서 host파일을 변조하여 a.com과 b.com의 주소를 LB external ip로 지정한 후 접속을 시도하여 L7 기반의 로드밸런싱+라우팅이 제대로 작동되는지 확인 합니다.

노트북의 host파일에 아래와 같은 설정을 합니다

노트패드를 관리자권한으로 열어서 아래폴더를 수정하면 됩니다.

코드 블럭
c:Windows/System32/drivers/etc/hosts
코드 블럭
cat /etc/hosts |grep com
192.168.1.101 a.com
192.168.1.101 b.com
  • 이제 노트북에서 a.com와 b.com을 호출 합니다/

코드 블럭
$curl a.com


Hostname: nginx1-deployment-545749bf4d-h7qfx

Pod Informationcurl 10.105.151.217
Request served by nginx1-deployment-8458b98748-75hlx

GET / HTTP/1.1

Host: 10.105.151.217
Accept: */*
User-Agent: curl/7.29.0

curl 10.98.154.210


[root@m-k8s vagrant]# curl 10.106.195.22
Request served by nginx2-deployment-767fbbfc95-g42jr

GET / HTTP/1.1

Host: 10.106.195.22
Accept: */*
User-Agent: curl/7.29.0

(7) L7기반의 라우팅을 해주는 ingress정책을 생성 합니다

  • ingress svc로 들어온 패킷의 L7레이어 즉 도메인 주소를 체크하여 트래픽을 전달합니다.

    • 도메인 주소가 a.com이라면 nginx-service-clusterip로 연결합니다.

    • 도메인 주소가 b.com이라면 nginx2-service.clusterip로 연결합니다.

6/08-ingress.yaml

코드 블럭
languageyaml
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: ingress
spec:
  ingressClassName: nginx
  rules:
  - host: "a.com"
    http:
      paths:
      - pathType: Prefix
-no pod information available-  Server values:  path: "/"
     server_version=nginx: 1.13.3 - luabackend:
10008  Request Information:       service:
 client_address=10.233.235.153         method=GET  name: nginx1-service-clusterip
     real path=/      port:
  query=         request_version=1.1   number: 80
  -  request_uri=http://a.com:8080/

Request Headershost: "b.com"
    http:
      paths:
 accept=*/*     - pathType: Prefix
   host=a.com     path: "/"
  user-agent=curl/7.71.1      backend:
  x-forwarded-for=192.168.9.237         x-forwarded-host=a.comservice:
         x-forwarded-port=80         x-forwarded-proto=http
 name: nginx2-service-clusterip
      x-real-ip=192.168.9.237      port:
  x-request-id=6b0169dcff0fd35fa780b600967dffb1         x-scheme=http  Request Bodynumber: 80

(8) ingress정책을 생성 합니다

코드 블럭
[root@m-k8s ~]# kubectl create     -no body in request-

$ curl b.com


Hostname: nginx2-deployment-56d6f87fc9-9m7h2

Pod Information:f 08-ingress.yaml
ingress.networking.k8s.io/ingress created

(9) ingress가 제대로 설정되어있는지 확인 합니다.

코드 블럭
[root@m-k8s vagrant]# k get ing
NAME      CLASS    -noHOSTS pod information available-  Server values:     ADDRESS    server_version=nginx: 1.13.3 - lua: 10008  RequestPORTS Information:  AGE
ingress   nginx   client_address=10.233.235.153a.com,b.com    192.168.1.150     method=GET80         real path=/
        query=
        request_version=1.1
        request_uri=http://b.com:8080/

Request Headers:
        accept=*/*
        host=b.com
        user-agent=curl/7.71.1
        x-forwarded-for=192.168.9.237
        x-forwarded-host=b.com
        x-forwarded-port=80
        x-forwarded-proto=http
        x-real-ip=192.168.9.237
        x-request-id=2a6b6ffa72efe6b80cae87dcaa51db98
        x-scheme=http

Request Body:
        -no body in request-
5m23s

(10) 클러스터 외부에서 host파일을 변조하여 a.com과 b.com의 주소를 LB external ip로 지정한 후 접속을 시도하여 L7 기반의 로드밸런싱+라우팅이 제대로 작동되는지 확인 합니다.

노트북의 host파일에 아래와 같은 설정을 합니다

노트패드를 관리자권한으로 열어서 아래폴더를 수정하면 됩니다.

코드 블럭
c:Windows/System32/drivers/etc/hosts
코드 블럭
cat /etc/hosts |grep com
192.168.1.150 a.com
192.168.1.150 b.com

  • 이제 노트북에서 a.com와 b.com을 호출 합니다/

코드 블럭
$ curl a.com
Request served by nginx1-deployment-98c84c874-hfb7t

GET / HTTP/1.1

Host: a.com
Accept: */*
User-Agent: curl/8.7.1
X-Forwarded-For: 192.168.1.1
X-Forwarded-Host: a.com
X-Forwarded-Port: 80
X-Forwarded-Proto: http
X-Forwarded-Scheme: http
X-Real-Ip: 192.168.1.1
X-Request-Id: 36bbde3cd8e429b0139f6cb71041e293
X-Scheme: http

$ curl b.com
Request served by nginx2-deployment-6cb7564d4f-5gkph

GET / HTTP/1.1

Host: b.com
Accept: */*
User-Agent: curl/8.7.1
X-Forwarded-For: 192.168.1.1
X-Forwarded-Host: b.com
X-Forwarded-Port: 80
X-Forwarded-Proto: http
X-Forwarded-Scheme: http
X-Real-Ip: 192.168.1.1
X-Request-Id: ef73f4cc0d95cb6ea3678abdae8eceec
X-Scheme: http

  • nginx ip로 직접 호출을 해봅니다

    • 레이어상 도메인정보가 없으므로 분기되지 않고 404 페이지가 나타 납니다.

코드 블럭
curl 172192.20168.2001.101150
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx</center>
</body>
</html>

...

  • ingress 설정 시 아래와 같이 서브도메인으로 분기도 가능하므로 활용하도록 합니다

009.ing26/08-ingress2.yaml

코드 블럭
languageyaml
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: ingress2
  namespace: default
spec:
  ingressClassName: nginx
  rules:
  - host: a.com
    http:
      paths:
      - pathType: Prefix
        path: /a
        backend:
          service:
            name: nginx-service-clusterip
            port:
              number: 80
      - pathType: Prefix
        path: /b
        backend:
          service:
            name: nginx2-service-clusterip
            port:
              number: 80

코드 블럭
kubectl apply -f 00908-ingress2.ing2.yaml

  • 위와같이 설정한다면 a.com/a 로 들어온 패킷은 nginx-service-clusterip로 라우팅 됩니다.

  • a.com/b 로 들어온 패킷은 nginx2.service-clusterip로 라우팅 됩니다

코드 블럭
$ curl a.com/a
Request served Hostname:by nginx1-deployment-545749bf4d98c84c874-mgnt8hfb7t

PodGET Information:
/a HTTP/1.1

Host: a.com
Accept: */*
User-Agent: curl/8.7.1
X-Forwarded-no pod information available-

Server values:
        server_version=nginx: 1.13.3 - lua: 10008

Request Information:
        client_address=10.233.228.72
        method=GET
        real path=/a
        query=
        request_version=1.1
        request_uri=http://a.com:8080/a

Request Headers:
        accept=*/*
        host=a.com
        user-agent=curl/7.71.1
        x-forwarded-for=192.168.9.38
        x-forwarded-host=a.com
        x-forwarded-port=80
        x-forwarded-proto=http
        x-real-ip=192.168.9.38
        x-request-id=6c98f42fba35104849f57ce30a57b2c3
        x-scheme=http

Request Body:
        -no body in request-

curl a.com/b


Hostname: nginx2-deployment-56d6f87fc9-55gsg

Pod Information:
        -no pod information available-

Server values:
        server_version=nginx: 1.13.3 - lua: 10008

Request Information:
        client_address=10.233.228.72
        method=GET
        real path=/bFor: 192.168.1.1
X-Forwarded-Host: a.com
X-Forwarded-Port: 80
X-Forwarded-Proto: http
X-Forwarded-Scheme: http
X-Real-Ip: 192.168.1.1
X-Request-Id: 72079ecd9d108f28bc735853731298f8
X-Scheme: http

$ curl a.com/b
Request served by nginx2-deployment-6cb7564d4f-5gkph

GET /b HTTP/1.1

Host: a.com
Accept: */*
User-Agent: curl/8.7.1
X-Forwarded-For: 192.168.1.1
X-Forwarded-Host: a.com
X-Forwarded-Port: 80
X-Forwarded-Proto: http
X-Forwarded-Scheme: http
X-Real-Ip: 192.168.1.1
X-Request-Id: d7ee6e9f70b8caa258e727fb1fa942ee
X-Scheme: http

  • ingress의 기능은 MSA 아키텍처에 많은 도움을 줄 수 있습니다

  • ingress를 잘 활용 하면 웹서버에 페이지 별로 다른 deploy나 pod그룹을 이용하여 효율적으로 자원을 분배하고 서비스를 배치 하여 관리 할 수 있습니다

정보

ingress의 기능은 msa아키텍처에 많은 도움을 줄 수 있으며, 웹서버에 페이지 별로 다른 deploy나 pod그룹을 이용하여 효율적으로 자원을 분배하고 서비스를 배치 하여 관리 할 수 있습니다.

다음 실습을 위해서 pod를 정리합니다.

코드 블럭
# k delete -f 08-ingress2.yaml
ingress.networking.k8s.io "ingress2" deleted
# k delete -f 08-ingress.yaml
ingress.networking.k8s.io "ingress" deleted
# k delete -f 07-ingress-backend.yaml
deployment.apps "nginx1-deployment" deleted
service "nginx-service-clusterip" deleted
deployment.apps "nginx2-deployment" deleted
service "nginx2-service-clusterip" deleted

...

3. 파드 네트워크

참고) 문서 상 노드 이름 및 역할

  • CNI 종류 및 구성방식에 따라 트래픽 전송 방식에 차이가 있습니다.

  • 어떤 식으로 트래픽이 전달되는지 확인하는 방법을 설명합니다.

192.168.1.10 cp-k8s
192.168.1.101 w1-k8s
192.168.1.102 w2-k8s
192.168.1.103 w3-k8s

3.1 파드 네크워크

...

  • 도커에서 POD 네트워크 설명할 경우와 인터페이스 이름이 다릅니다.

  • 도커의 역할

참고1) https://www.docker.com/products/container-runtime/

3.2 단일 컨테이너 파드

  • Pod (Single Container)의 네트워크 설정을 확인합니다.

6/09-pod-network-ubuntu.yaml

코드 블럭
apiVersion: v1
kind: Pod
metadata:
  name: ubuntu-test
spec:
  containers:
  - name: ubuntu
    image: ubuntu:20.04
    command: ["/bin/sleep", "3650d"]
    imagePullPolicy: IfNotPresent
    volumeMounts:
    - mountPath: /cache
      name: cache-volume
  volumes:
  - name: cache-volume
    emptyDir: {}
  restartPolicy: Always
  dnsConfig:
    nameservers:
      - 8.8.8.8

  • 파드 네트워크 구성에 대해 알아봅니다.

코드 블럭
root@cp-k8s# kubectl get pod -o wide
NAME          READY query=  STATUS    RESTARTS   request_version=1.1AGE     IP    request_uri=http://a.com:8080/b  Request Headers:     NODE    accept=*/*        NOMINATED host=a.comNODE   READINESS GATES
ubuntu-test    user-agent=curl/7.71.1/1     Running    x-forwarded-for=192.168.9.380          x-forwarded-host=a.com150m   172.16.103.134   w2-k8s   x-forwarded-port=80<none>         x-forwarded-proto=http  <none>

###POD 접속
root@cp-k8s## kubectl exec x-real-ip=192.168.9.38
        x-request-id=b5c8a4dfef21d5acc50763232a7f02c1
        x-scheme=http

Request Body:
        -no body in request-

이러한 ingress의 기능은 msa아키텍처에 많은 도움을 줄 수 있습니다

ingress를 잘 활용 하면 웹서버에 페이지별로 다른 deploy나 pod그룹을 이용하여 효율적으로 자원을 분배하고 서비스를 배치 하여 관리 할 수 있습니다

정보

ingress의 기능은 msa아키텍처에 많은 도움을 줄 수 있으며, 웹서버에 페이지 별로 다른 deploy나 pod그룹을 이용하여 효율적으로 자원을 분배하고 서비스를 배치 하여 관리 할 수 있습니다.

3. 파드 네트워크

참고) 문서 상 노드 이름 및 역할

sung-ubuntu01 - Control Plane #1

sung-ubuntu02 - Control Plane #2

sung-ubuntu03 - Control Plane #3

sung-ubuntu04 - Worker Node #1

sung-ubuntu05 - Worker Node #2

3.1 파드 네크워크

...

  • 도커에서 POD 네트워크 설명할 경우와 인터페이스 이름이 다릅니다.

  • 도커의 역할

참고1) https://www.docker.com/products/container-runtime/

3.2 단일 컨테이너 파드

  • Pod (Single Container)의 네트워크 설정을 확인합니다.

코드 블럭
root@sung-ubuntu01:~/tmp# cat ubuntu.yaml
apiVersion: v1
kind: Pod
metadata:
  name: ubuntu-test
spec:
  containers:
  - name: ubuntu
    image: ubuntu:20.04
    command: ["/bin/sleep", "3650d"]
    imagePullPolicy: IfNotPresent
    volumeMounts:
    - mountPath: /cache
      name: cache-volume
  volumes:
  - name: cache-volume
    emptyDir: {}
  restartPolicy: Always
  dnsConfig:
    nameservers:
      - 8.8.8.8


root@sung-ubuntu01:~/tmp# kubectl get pod -o wide
NAME          READY   STATUS    RESTARTS   AGE     IP            NODE  it ubuntu-test -- bash
# apt update
# apt install -y net-tools iputils-ping

root@ubuntu-test:/# ping 8.8.8.8
PING 8.8.8.8 (8.8.8.8) 56(84) bytes of data.
64 bytes from 8.8.8.8: icmp_seq=1 ttl=54 time=39.6 ms
64 bytes from 8.8.8.8: icmp_seq=2 ttl=54 time=38.1 ms
64 bytes from 8.8.8.8: icmp_seq=3 ttl=54 time=38.8 ms
64 bytes from 8.8.8.8: icmp_seq=4 ttl=54 time=39.3 ms

**# 컨테이너의 네트워크 인터페이스 확인**
# root@ubuntu-test:/# ifconfig -a
eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1480
        inet 172.16.103.134  netmask 255.255.255.255  broadcast 0.0.0.0
        ether 36:d7:04:b0:6a:0b  txqueuelen 1000  (Ethernet)
        RX packets 9667  bytes 32353517 (32.3 MB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 8976  bytes 492421 (492.4 KB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

lo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536
        inet 127.0.0.1  netmask 255.0.0.0
        loop  txqueuelen 1000  (Local Loopback)
        RX packets 0  bytes 0 (0.0 B)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 0  bytes 0 (0.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
        
#노드와 파드 사이를 연결하는 인터페이스입니다.
tunl0: flags=128<NOARP>  mtu 1480
        tunnel   txqueuelen 1000  (IPIP Tunnel)
        RX packets 0  bytes 0 (0.0 B)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 0  bytes 0 (0.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0ons 0

* loopback ip : host 자신을 가리키는 논리적인 인터페이스
**#노드 네트워크 확인**
root@sung-ubuntu04:~# ifconfig -a
...
tunl0: flags=193<UP,RUNNING,NOARP>  mtu 1480
        inet 172.16.103.128  netmask 255.255.255.255
        tunnel   txqueuelen 1000  (IPIP Tunnel)
        RX packets 111  bytes 15872 (15.8 KB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 91  bytes 14596 (14.5 KB)
        TX NOMINATEDerrors NODE0  dropped READINESS0 GATESoverruns ubuntu-test0  carrier 1/10  collisions 0

Running*mtu 1480인 이유?
0IPIP 터널을 사용하고 있기 때문에, 캡슐화된 패킷의 크기는 원래 패킷보다 6m20s   10.233.99.1   sung-ubuntu04   <none>           <none>


###POD 접속
root@sung-ubuntu01:~/tmp# kubectl exec -it ubuntu-test -- bash
root@ubuntu-test:/#


root@ubuntu-test:/# ping 8.8.8.8
PING 8.8.8.8 (8.8.8.8) 56(84) bytes of data.
64 bytes from 8.8.8.8: icmp_seq=1 ttl=54 time=39.6 ms
64 bytes from 8.8.8.8: icmp_seq=2 ttl=54 time=38.1 ms
64 bytes from 8.8.8.8: icmp_seq=3 ttl=54 time=38.8 ms
64 bytes from 8.8.8.8: icmp_seq=4 ttl=54 time=39.3 ms


# apt update
# apt install -y net-tools iputils-ping


**# 컨테이너의 네트워크 인터페이스 확인**
# root@ubuntu-test:/# ifconfig -a
eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1480
        inet 10.233.99.1  netmask 255.255.255.255  broadcast 0.0.0.0
        ether 06:55:84:5a:ac:6b  txqueuelen 0  (Ethernet)
        RX packets 5718  bytes 24026416 (24.0 MB)크기 때문에 MTU 조절이 필요하다
1480인 이유는 캡슐화된 패킷이 Ethernet 패킷에 포함될 때 전체 크기가 1500을 초과하지 않도록 하기 위해서이다.

3.3 멀티 컨테이너 파드

  • Pod (Multi Container)의 네트워크 설정 확인을 확인합니다.

6/10-pod-network-multicon.yaml

코드 블럭
apiVersion: v1
kind: Pod
metadata:
  name: multi-container
spec:
  containers:
  - name: ubuntu
    image: ubuntu:20.04
    command: ["/bin/sleep", "3650d"]
    imagePullPolicy: IfNotPresent
    volumeMounts:
    - mountPath: /cache
      name: cache-volume
  - name: nginx
    image: nginx
    ports:
    - containerPort: 80
  volumes:
  - name: cache-volume
    emptyDir: {}
  restartPolicy: Always
  dnsConfig:
    nameservers:
      - 8.8.8.8

root@cp-k8s:~# k get pod -o wide
NAME                   RX errors 0  dropped 0  overruns 0  frame 0        READY TX packets 3690STATUS  bytes 250168 (250.1 KB)RESTARTS       AGE   TX errorsIP 0  dropped 0 overruns 0  carrier 0  collisions 0  lo: flags=73<UP,LOOPBACK,RUNNING> NODE  mtu 65536  NOMINATED NODE   READINESS GATES
multi-container inet 127.0.0.1  netmask 255.0.0.0         loop  txqueuelen 1000  (Local Loopback)       2/2  RX packets 0 Running bytes 0 (0.0 B)         RX errors 0  dropped15m 0  overruns 0 172.16.132.6  frame 0  w3-k8s   <none>    TX packets 0  bytes 0 (0.0 B)
 <none>
nfs-client-provisioner-5cf87f6995-vg6fq   1/1     TXRunning errors 0 28 dropped(10m 0ago) overruns 0 7h4m carrier 0 172.16.221.133 collisions 0 w1-k8s   #설명추가<none> tunl0: flags=128<NOARP>  mtu 1480      <none>
ubuntu-test  tunnel   txqueuelen 1000  (IPIP Tunnel)         RX packets 0  bytes 0 (0.0 B)      1/1   RX errors 0Running  dropped 0  overruns 0  frame 0        36m TX packets 0 172.16.103.134 bytes 0 (0.0 B) w2-k8s   <none>       TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0


* loopback ip : host 자신을 가리키는 논리적인 인터페이스


**#노드 네트워크 확인**
root@sung-ubuntu04:~# ifconfig -a
...
tunl0: flags=193<UP,RUNNING,NOARP><none>
  • 컨테이너 내부에서 네트워크 흐름을 알아봅니다.

코드 블럭
**#ubuntu 컨테이너 접속**
root@cp-k8s:~# kubectl exec -it multi-container -c ubuntu -- bash

### POD 안에서
# apt update
# apt install -y net-tools iputils-ping

root@multi-container:/# ifconfig
eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1480
        inet 10172.23316.99132.06  netmask 255.255.255.255  broadcast 0.0.0.0
       tunnel  ether da:6c:e7:bc:8b:f9  txqueuelen 1000  (IPIP TunnelEthernet)
        RX packets 604920  bytes 852841607447 (841.56 KBMB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 663877  bytes 4476217509 (4217.45 KB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0


*mtu 1480인 이유?
IPIP 터널을 사용하고 있기 때문에, 캡슐화된 패킷의 크기는 원래 패킷보다 더 크기 때문에 MTU 조절이 필요하다
1480인 이유는 캡슐화된 패킷이 Ethernet 패킷에 포함될 때 전체 크기가 1500을 초과하지 않도록 하기 위해서이다.

3.3 멀티 컨테이너 파드

  • Pod (Multi Container)의 네트워크 설정 확인을 확인합니다.

코드 블럭
root@sung-ubuntu01:~/tmp# cat multi-con.yaml
apiVersion: v1
kind: Pod
metadata:
  name: multi-container
spec:
  containers:
  - name: ubuntu
    image: ubuntu:20.04
    command: ["/bin/sleep", "3650d"]
    imagePullPolicy: IfNotPresent
    volumeMounts:
    - mountPath: /cache
      name: cache-volume
  - name: nginx
    image: nginx
    ports:
    - containerPort: 80
  volumes:
  - name: cache-volume
    emptyDir: {}
  restartPolicy: Always
  dnsConfig:
    nameservers:
      - 8.8.8.8

root@sung-ubuntu01:~/tmp# kubectl get pod -o wide
NAME    lo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536
        inet 127.0.0.1  netmask 255.0.0.0
        loop  txqueuelen 1000  (Local Loopback)
        RX packets 0  bytes 0 (0.0 B)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 0  bytes 0 (0.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

**# nginx 컨테이너 접속**
root@cp-k8s:~# kubectl exec -it multi-container -c nginx -- bash

### POD 안에서 실행
# apt update
# apt install -y net-tools iputils-ping

root@multi-container:/# ifconfig
eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1480
        inet 172.16.132.6  netmask 255.255.255.255  broadcast 0.0.0.0
        ether da:6c:e7:bc:8b:f9  txqueuelen 1000  (Ethernet)
        RX packets 590  bytes 9590376 (9.1 MiB)
        RX READYerrors 0  STATUSdropped 0  overruns RESTARTS0  frame AGE0
  IP      TX packets 355  bytes 21258 NODE (20.7 KiB)
        TX errors NOMINATED0 NODE dropped 0 READINESSoverruns GATES0 multi-container carrier 0 2/2 collisions 0

 Runninglo: flags=73<UP,LOOPBACK,RUNNING>  mtu 065536
         25minet 127.0.0.1  netmask 10255.2330.780.30
  sung-ubuntu05   <none>   loop  txqueuelen 1000  (Local Loopback)
 <none> ubuntu-test      RX 1/1packets 0  bytes 0 Running (0.0 B)
 0       RX errors 0 57m dropped 0 10.233.99.1 overruns 0 sung-ubuntu04 frame 0
<none>        TX packets 0 <none>

...

 bytes 0 (0.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

  • 노드 네트워크 확인

코드 블럭
root@w3-k8s:~# ifconfig -a
cali9794446aa53: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1480
 

...

 

...

  

...

 

...

  

...

 

...

ether 

...

ee:

...

ee:

...

ee:

...

ee:

...

ee:

...

ee  txqueuelen 

...

1000  (Ethernet)
        RX packets 

...

34654  bytes 

...

5118573 (

...

5.

...

1 MB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 

...

41396  bytes 

...

9084184 (

...

9.

...

0 

...

MB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

...

calib4cfe5eb958: flags=

...

4163<UP,BROADCAST,

...

RUNNING,

...

MULTICAST>  mtu 

...

1480
        

...

ether ee:ee:ee:ee:ee:ee  txqueuelen 1000  (

...

Ethernet)
        RX packets 

...

3885  bytes 

...

218205 (

...

218.

...

2 

...

KB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets

...

 5122  bytes 41619671 (41.6 MB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 

...

1500
        inet 10.

...

0.

...

2.

...

15  netmask 255.255.255.

...

0  broadcast 

...

10.0.

...

2.

...

255
        ether 

...

08:

...

00:

...

00:

...

00:

...

00:

...

00  txqueuelen 

...

1000  (Ethernet)
        RX packets 

...

196682  bytes 

...

287889664 (

...

287.

...

8 

...

MB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 

...

13578  bytes 

...

1005482 (

...

1.

...

0 

...

MB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

...

eth1: flags=

...

4163<UP,BROADCAST,

...

RUNNING,

...

MULTICAST>  mtu 

...

1500
        inet 

...

192.

...

168.

...

1.

...

103  netmask 255.255.255.0

...

  broadcast 192.168.1.255
        

...

ether 08:00:27:3f:6d:d5  txqueuelen 1000  (

...

Ethernet)
        RX packets 

...

189996  bytes 

...

54057708 (

...

54.0 

...

MB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 

...

171448  bytes 

...

22285772 (

...

22.

...

2 

...

MB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

...

  • 노드 네트워크 확인

코드 블럭
root@sung-ubuntu05:~#
ifconfig
-a
calib4cfe5eb958lo: flags=4163<UP73<UP,BROADCASTLOOPBACK,RUNNING,MULTICAST>RUNNING>  mtu 148065536
        inet6 fe80::ecee:eeff:feee:eeee  prefixlen 64  scopeid 0x20<link>inet 127.0.0.1  netmask 255.0.0.0
           ether ee:ee:ee:ee:ee:eeloop  txqueuelen 01000  (EthernetLocal Loopback)
        RX packets 3935246745  bytes 26759167681709 (26767.56 KBMB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 6287246745  bytes 3301301467681709 (3367.06 MB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

docker0tunl0: flags=4099<UP193<UP,BROADCASTRUNNING,MULTICAST>NOARP>  mtu 15001480
        inet 172.1716.132.0.1  netmask 255.255.0.0  broadcast 172.17.255.255
        ether 02:42:6a:17:c5:80tunnel   txqueuelen 01000  (EthernetIPIP Tunnel)
        RX packets 0129  bytes 024080 (024.0 BKB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 0  bytes 0 (0.0 B)
        TX errors 0  dropped 0  overruns 0  carrierframe 0
 collisions      0 TX ens3: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>packets 137  mtubytes 150024502 (24.5 KB)
      inet 192.168.110.104 TX netmask 255.255.0.errors 0  broadcast 192.168.255.255
        inet6 fe80::f816:3eff:fe54:bc4  prefixlen 64  scopeid 0x20<link>dropped 0 overruns 0  carrier 0  collisions 0

  • multi-container 관련 컨테이너 확인

코드 블럭
root@w3-k8s:~# crictl ps | grep multi-container
7e77cac0a9ec8       e784f4560448b    ether fa:16:3e:54:0b:c4  txqueuelen20 1000minutes ago (Ethernet)     Running    RX packets 1353299  bytes 1304887824 (1.3 GB)  nginx       RX errors 0  dropped 88603  overruns 0  frame 0         TX packets 191206  bytes 20789350 (20.7 MB) 2c8ad4a63a674       multi-container
2e4672f196a4e TX errors 0  dropped 0 overruns2abc4dfd83182 0  carrier 0  collisions 020 minutes kube-ipvs0: flags=130<BROADCAST,NOARP>ago   mtu 1500  Running       inet 10.233.0.1  netmask 255.255.255.255  broadcast 0.0.0.0ubuntu          ether 66:2d:b3:6c:50:9a  txqueuelen 0       (Ethernet)         RX packets 0 2c8ad4a63a674 bytes 0 (0.0 B)   multi-container

root@w3-k8s:~# crictl ps
CONTAINER RX errors 0  dropped 0  overruns 0  frameIMAGE 0         TX packets 0  bytes 0CREATED (0.0 B)         TX errors 0STATE  dropped 0 overruns 0  carrier 0  collisions 0  lo: flags=73<UP,LOOPBACK,RUNNING> NAME mtu 65536         inet 127.0.0.1  netmask 255.0.0.0 ATTEMPT        inet6 ::1  prefixlen 128 POD scopeidID 0x10<host>         loop  txqueuelen 1000 POD
(Local7e77cac0a9ec8 Loopback)      e784f4560448b   RX packets 162061  bytes20 22298211 (22.2 MB)minutes ago      Running    RX errors 0  dropped 0  overruns 0 nginx frame 0         TX packets 162061  bytes0 22298211 (22.2 MB)         TX errors 0  dropped 0 overruns 02c8ad4a63a674  carrier 0  collisions 0 multi-container
nodelocaldns: flags=130<BROADCAST,NOARP>2e4672f196a4e   mtu 1500   2abc4dfd83182      inet 169.254.25.10  netmask 255.255.255.255  broadcast 0.0.0.0
  20 minutes ago      Running       ether 16:84:53:46:fe:65  txqueuelen 0  (Ethernet)ubuntu         RX packets 0  bytes 0  (0.0 B)         RX errors 0  dropped 0  overruns2c8ad4a63a674 0  frame 0   multi-container
3041e3871fce9     TX packets 0825aff16c20cc  bytes 0 (0.0 B)  3 hours ago     TX errors 0  droppedRunning 0 overruns 0  carrier 0  collisions 0  tunl0: flags=193<UP,RUNNING,NOARP> controller mtu 1480   #터널 인터페이스    0     inet 10.233.78.0  netmask 255.255.255.255         tunnel f13095e35bd52  txqueuelen 1000  (IPIP Tunnel)
  ingress-nginx-controller-568fb54f96-mr8p4
ab79b29f18c4d       RX44f52c09decec packets 69  bytes 9380 (9.3 KB)
  6 hours ago       RX errors 0Running  dropped 0  overruns 0  frame 0    calico-node     TX packets 76  bytes1 5125 (5.1 KB)         TX errors 0  dropped 0 overruns 069f307f64ef92  carrier 0  collisions 0 
  • multi-container 관련 컨테이너 확인

코드 블럭

root@sung-ubuntu05:~# docker ps | grep multi-container
64c1938850a2   nginxcalico-node-9dmp8
6a36a93a5e2fc       738c5d221d601       6 hours ago          "/docker-entrypoint.…"Running    26 minutes ago   Up 25 minutes  speaker           k8s_nginx_multi-container_default_1d0e0776-18b1-4c7f-b05f-20b8c54fb230_0
b4c4045ac777  2   ubuntu                1b868a54d4c49 "/bin/sleep 3650d"     speaker-6hc8s
e1450ce254e91 26 minutes ago   Up 262019bbea5542a minutes      6 hours ago     k8s_ubuntu_multi-container_default_1d0e0776-18b1-4c7f-b05f-20b8c54fb230_0 1eaedb9c9d55   k8s.gcr.io/pause:3.5Running   "/pause"          kube-proxy       27 minutes ago 1  Up 26 minutes             k8s_POD_multi-container_default_1d0e0776-18b1-4c7f-b05f-20b8c54fb230_0

...

Pause Container

...

파드 내부의 container들을 위한 일종의 '부모 container' 로서의 역할을 수행합니다.

...

파드가 실행될 때 Pause Container가 먼저 실행되고 Pause Container의 리눅스 네임스페이스를 파드 내부의 모든 컨테이너들이 상속받아서 사용합니다.

...

  424a7426434a9       kube-proxy-wwdpz
정보

리눅스 namespace

  • 리눅스 커널에서 제공 기능으로 Container의 기반이 되는 기술. 하나의 시스템에서 프로세스를 격리시킬 수 있는 가상화 기술입니다.

3.4 파드 간 통신

image-20220929-070539.pngImage Removedimage-20240525-100509.pngImage Added

Pod 간 route 경로 확인

코드 블럭
root@sungroot@cp-ubuntu01:~/tmp# kubectl get pod -o wide
NAMEk8s:~# kubectl get pod -o wide
NAME                                      READY   STATUS    RESTARTS       AGE     IP               NODE     NOMINATED NODE   READINESS GATES
multi-container                READY   STATUS    RESTARTS   AGE 2/2  IP   Running   0      NODE        23m    NOMINATED NODE 172.16.132.6   READINESS GATES multi-containerw3-k8s   <none>          2/2 <none>
nfs-client-provisioner-5cf87f6995-vg6fq   Running1/1   0  Running   28 (18m ago)   25m7h13m   10172.23316.78221.3133   sungw1-ubuntu05k8s   <none>           <none>
ubuntu-test                               1/1     Running   0            57m  45m     10172.23316.99103.1134   sungw2-ubuntu04k8s   <none>           <none>
;

#ubuntu-test 
root@ubuntu-test:/# apt install traceroute

root@ubuntu-test:/# traceroute 10172.23316.78132.36
traceroute to 10172.23316.78132.36 (10172.23316.78132.36), 30 hops max, 60 byte packets
 1  19210.1680.1102.10315 (19210.1680.1102.10315)  01.202308 ms  0.032025 ms  0.028020 ms
 #sung-ubuntu04 ens3
 2  10172.23316.78132.0 (10172.23316.78132.0)  12.169099 ms  03.990995 ms  03.928182 ms   
      #sung-ubuntu05 tunl0
 3  10172.23316.78132.36 (10172.23316.78132.36)  12.096967 ms  16.111487 ms  1.087 ms          #multi-container IP
5.188 ms
 

노드 route table 확인

코드 블럭
root@sungroot@w2-ubuntu04k8s:~# route
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
default         _gateway10.0.2.2        0.0.0.0         UG    100    0        0 ens3eth0
10.2330.782.0     sung-ubuntu05.c 255.255.255   0.0.0.0   UG    0  255.255.255.0   U 0    100    0 tunl0
10.233.91.0     sung-ubuntu02.c 255.255.255.0   UG    0      0eth0
10.0.2.2        0 tunl0
10.2330.950.0       sung-ubuntu01.c  255.255.255.0255 UH  UG    0  100    0        0 tunl0eth0
10.2330.99.02.3        0.0.0.0         255.255.255.0   U  255 UH   0 100     0        0 *eth0
10172.23316.99.1   103.128  0.0.0.0         255.255.255.255192 U UH    0      0        0 calie3df4d89b13*
10172.23316.99103.2 134    0.0.0.0         255.255.255.255 UH    0      0        0 calia85a668c715calie3df4d89b13
10172.23316.112132.0    sung-ubuntu03.cw3-k8s          255.255.255.0  192 UG    0      0        0 tunl0
169172.25416.169.254 192.168.51.110196.128  cp-k8s          255.255.255.255192 UG   UGH 0  100    0        0 ens3tunl0
172.1716.0221.0128  w1-k8s    0.0.0.0         255.255.0255.0     U 192 UG    0      0        0 docker0tunl0
192.168.01.0     0.0.0.0         255.255.0255.0     U     0      0        0 ens3eth1


root@sungroot@w2-ubuntu04k8s:~# cat /etc/hosts
127.0.0.1 # Ansible inventory hosts BEGIN
localhost
192.168.1101.10010 sung-ubuntu01.cluster.local sung-ubuntu01
cp-k8s
192.168.1101.101 sung-ubuntu02.cluster.local sung-ubuntu02
w1-k8s
192.168.1101.102 sung-ubuntu03.cluster.local sung-ubuntu03w2-k8s
192.168.1101.103 sung-ubuntu04.cluster.local sung-ubuntu04
192.168.110.104 sung-ubuntu05.cluster.local sung-ubuntu05
w3-k8s
  • 참고

https://kubernetes.io/ko/docs/concepts/cluster-administration/networking/

...

  • DNS 응답을 라운드 로빈 방식으로 로드 밸런싱합니다.

CoreDNS 기본 설정

6/11-coredns-cm.yaml

코드 블럭
apiVersion: v1
kind: ConfigMap
metadata:
  name: coredns
  namespace: kube-system
data:
  Corefile: |
    .:53 {
        errors
        health
        ready
        kubernetes cluster.local in-addr.arpa ip6.arpa {
           pods insecure
           fallthrough in-addr.arpa ip6.arpa
        }
        prometheus :9153
        forward . /etc/resolv.conf
        cache 30
        loop
        reload
        loadbalance
    }

...

코드 블럭
kubectl -n kube-system edit configmap coredns

(2) 외부 DNS 서버 추가

...

특정 도메인 목적지 추가

  • host {} 항목을 추가합니다.

코드 블럭
apiVersion: v1
kind: ConfigMap
metadata:
  name: coredns
  namespace: kube-system
data:
  Corefile: |
    .:53 {
        errors
        health
        ready
        kubernetes cluster.local in-addr.arpa ip6.arpa {
            pods insecure
            fallthrough in-addr.arpa ip6.arpa
        }
        prometheus :9153
        forward . /etc/resolv.conf
        cache 30
        loop
        reload
        loadbalance
        hosts {
            172.16.0.3 webservice1.com
            fallthrough
        }
    }

...