brunch

You can make anything
by writing

C.S.Lewis

by Master Seo Jul 11. 2021

쿠버1탄-19. 쿠버네티스 - 인그레스=ALB=L7

다음은 쿠버네티스 스터디 자료를 참고해  정리한 내용입니다.


인그레스는 L7 로드 밸런서로 생각하면 되겠다.

HTTP 와  HTTPS 에 대해 서비스 한다.

카나리 업데이트도 가능

마스터 노드에 인그레스 생성, Node Port로 외부 노출

요청에 따른 Path 라우팅



<1> 구성 

<2> 디플로이먼트와 서비스 생성

<3> 인그레스 생성

<4> 인그레스 컨트롤러 생성

<5>  데이트 흐름을 쉽게 보는 플러그인 설치 (옵션)

<6> 다음 편



<1> 구성 


1

실습 환경

쿠버네티스-도메인 없이 kops로 aws쿠버설치

https://brunch.co.kr/@topasvga/1681


2

로드 밸런서 구성?

사용자 연결 ------- Ingress --- Service ------Pod

// Ingress 앞에 보안장비등이 필요하다.


3

카나리 배포 구성 가능 ?

점진적 배포 

10%만 배포 하고, 이상 없으면 나머지 배포를 늘린다.


사용자 연결 ------- Ingress --- Service (90%) ------Pod 

                               Ingress --- Service (10%) ------Pod 


4

/customer  /order     등  경로에 따라 다른  Pod   연결 가능


5

인그레스 컨트롤러?

NGINX, Kong 


6

LB , 카나리 배포, HTTPS 처리함




<2> 디플로이먼트와 서비스 생성


1

구성도 ?

NodePort 로 외부에 노출

마스터 노드에 인그레스 컨트롤러(Nginx) 파드를 생성 - 실제 서비스에서는 별도 네트워크에 구성


클라이언트 ------- Service (여기서는 NodePort  사용)----- 인그레스 구성


디플로이먼트 파드 1개, 파드 2개, 파드 3개 생성



2

터미널2로 모니터링

watch -d 'kubectl get pods,svc -o wide'


3

터미널1에서 실습

디플로이먼트 파드 1개, 파드 2개, 파드 3개 생성 ?


svc1-pod.yaml

svc2-pod.yaml

svc3-pod.yaml



cat << EOF > svc1-pod.yaml

apiVersion: apps/v1

kind: Deployment

metadata:

  name: deploy1-websrv

spec:

  replicas: 1   // pod 1개 생성

  selector:

    matchLabels:

      app: websrv

  template:

    metadata:

      labels:

        app: websrv

    spec:

      containers:

      - name: pod-web

        image: nginx

---

apiVersion: v1

kind: Service

metadata:

  name: svc1-web

spec:

  ports:

    - name: web-port

      port: 9001

      targetPort: 80

  selector:

    app: websrv

  type: ClusterIP

EOF



4

cat << EOF > svc2-pod.yaml

apiVersion: apps/v1

kind: Deployment

metadata:

  name: deploy2-guestsrv

spec:

  replicas: 2   // pod 2개 생성

  selector:

    matchLabels:

      app: guestsrv

  template:

    metadata:

      labels:

        app: guestsrv

    spec:

      containers:

      - name: pod-guest

        image: gcr.io/google-samples/kubernetes-bootcamp:v1

        ports:

        - containerPort: 8080

---

apiVersion: v1

kind: Service

metadata:

  name: svc2-guest

spec:

  ports:

    - name: guest-port

      port: 9002

      targetPort: 8080

  selector:

    app: guestsrv

  type: NodePort

EOF



3

cat << EOF > svc3-pod.yaml

apiVersion: apps/v1

kind: Deployment

metadata:

  name: deploy3-adminsrv

spec:

  replicas: 3      // pod 3개 생성

  selector:

    matchLabels:

      app: adminsrv

  template:

    metadata:

      labels:

        app: adminsrv

    spec:

      containers:

      - name: pod-admin

        image: k8s.gcr.io/echoserver:1.5

        ports:

        - containerPort: 8080

---

apiVersion: v1

kind: Service

metadata:

  name: svc3-admin

spec:

  ports:

    - name: admin-port

      port: 9003

      targetPort: 8080

  selector:

    app: adminsrv

EOF




4

터미널 2에서  모니터링

watch -d 'kubectl get pods,svc -o wide'


watch -d 'kubectl get ns,no,po,svc,deploy,rs,ing,ep -o wide'


alias k=kubectl

complete -F __start_kubectl k

k get ns,no,po,svc,deploy,rs,ing,ep




5

kubectl apply -f svc1-pod.yaml

kubectl apply -f svc2-pod.yaml

kubectl apply -f svc3-pod.yaml


6

kubectl get pod,svc

NAME                                    READY   STATUS    RESTARTS   AGE

pod/deploy1-websrv-574449b8df-z587n     1/1     Running   0          5m35s

pod/deploy2-guestsrv-6f7f766988-bpqj9   1/1     Running   0          5m35s

pod/deploy2-guestsrv-6f7f766988-d2v6h   1/1     Running   0          5m35s

pod/deploy3-adminsrv-7bd5d589b9-228k9   1/1     Running   0          5m33s

pod/deploy3-adminsrv-7bd5d589b9-h6qbq   1/1     Running   0          5m33s

pod/deploy3-adminsrv-7bd5d589b9-lbtqf   1/1     Running   0          5m33s


NAME                 TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)          AGE

service/kubernetes   ClusterIP   100.64.0.1       <none>        443/TCP          41m

service/svc1-web     ClusterIP   100.70.174.150   <none>        9001/TCP         5m35s

service/svc2-guest   NodePort    100.71.78.68     <none>        9002:30923/TCP   5m35s

service/svc3-admin   ClusterIP   100.67.207.226   <none>        9003/TCP         5m33s



7

watch -d 'kubectl get pods,svc -o wide'



8

watch -d 'kubectl get ns,no,po,svc,deploy,rs,ing,ep -o wide'




<3> 인그레스 생성


1

cat << EOF > ingress1.yaml

apiVersion: networking.k8s.io/v1beta1

kind: Ingress

metadata:

  name: ingress-1

  annotations:

    kubernetes.io/ingress.class: "nginx"

    #nginx.ingress.kubernetes.io/upstream-hash-by: "true"

spec:

  rules:

  - http:

      paths:

      - path: /

        backend:

          serviceName: svc1-web

          servicePort: 80

      - path: /guest

        backend:

          serviceName: svc2-guest

          servicePort: 8080

      - path: /admin

        backend:

          serviceName: svc3-admin

          servicePort: 8080

EOF


// path에 따라서 각각 다른 Pod에 연결 된다.




2

모니터링

watch -d 'kubectl get ing,svc,ep -o wide'



3

정책을 만든다 ?

kubectl apply -f ingress1.yaml


인그레스 정책 1개를  생성함

ingress.networking.k8s.io/ingress-1 created



watch -d 'kubectl get ing,svc,ep -o wide'



4

kubectl get ingress

NAME        CLASS    HOSTS   ADDRESS   PORTS   AGE

ingress-1   <none>   *                 80      2m59s



kubectl describe ingress ingress-1

Name:             ingress-1

Namespace:        default

Address:

Default backend:  default-http-backend:80 (<error: endpoints "default-http-backend" not found>)

Rules:

  Host        Path  Backends

  ----        ----  --------

  *

              /        svc1-web:80 ()

              /guest   svc2-guest:8080 ()

              /admin   svc3-admin:8080 ()

Annotations:  kubernetes.io/ingress.class: nginx

Events:       <none>




<4>  인그레스 컨트롤러 생성



1

인그레스 컨트롤러 ?

dNodePort로  마스터 노드에 생성


2

curl -s -o nginx-ingress.yaml -O -L curl -s -O https://raw.githubusercontent.com/gasida/DKOS/main/6/nginx-ingress.yaml


변경전

k8s-m 


변경후

// 필수

AWS에서 인그레스 컨트롤러 생성하실때는 nginx-ingress.yaml  파일 안에 k8s-m 대신

 AWS master node name으로 바꿔주세요

예) ip-172-20-60-135.ap-northeast-1.compute.interna 로 변경해주세요 !!


4

노드 확인후 변경


kubectl get nodes

NAME                                STATUS   ROLES                  AGE   VERSION

ip-172-20-56-239.ap-northeast-1.compute.internal   Ready    node                   26m   v1.20.8

ip-172-20-60-135.ap-northeast-1.compute.internal   Ready    control-plane,master  29m   v1.20.8

ip-172-20-62-175.ap-northeast-1.compute.internal   Ready    node                   26m   v1.20.8


sed -i 's/k8s-m/ip-172-20-60-135.ap-northeast-1.compute.internal/g' nginx-ingress.yaml


kubectl apply -f nginx-ingress.yaml


5

네임 스페이스 확인

kubectl get namespaces


NAME              STATUS   AGE

default           Active   57m

ingress-nginx     Active   36m

kube-node-lease   Active   57m

kube-public       Active   57m

kube-system       Active   57m


6

ingress-nginx-controller 생성 확인 !!!


kubectl get pod -n ingress-nginx -o wide -l app.kubernetes.io/component=controller


NAME   READY   STATUS    RESTARTS   AGE    IP     NODE     NOMINATED NODE   READINESS GATES

ingress-nginx-controller-584dc4797b-z5g29   1/1     Running   0          2m2s   100.112.248.194   ip-172-20-60-135.ap-northeast-1.compute.internal   <none>           <none>

// Running 확인

 

5

kubectl get pods -n ingress-nginx -l app.kubernetes.io/name=ingress-nginx --watch

NAME                                        READY   STATUS      RESTARTS   AGE

ingress-nginx-admission-create-8fzvj        0/1     Completed   0          42m

ingress-nginx-admission-patch-9qhtt         0/1     Completed   0          42m

ingress-nginx-controller-584dc4797b-z5g29   1/1     Running     0          32m



6

ingress-nginx  네임 스페이스 안에 모든것 보기 ?  all


kubectl get all -n ingress-nginx

NAME                                            READY   STATUS      RESTARTS   AGE

pod/ingress-nginx-admission-create-sx87s        0/1     Completed   0          4m9s

pod/ingress-nginx-admission-patch-v6mmr         0/1     Completed   1          4m9s

pod/ingress-nginx-controller-54c4c897b6-98bbb   0/1     Pending     0          7s


NAME                                         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)                      AGE

service/ingress-nginx-controller  NodePort 100.66.58.13  no   80:30058/TCP,443:31570/TCP 4m

service/ingress-nginx-controller-admission ClusterIP 100.65.233.82 <none> 443/TCP   4m9s


NAME                                       READY   UP-TO-DATE   AVAILABLE   AGE

deployment.apps/ingress-nginx-controller   0/1     1            0           4m9s


NAME                                                  DESIRED   CURRENT   READY   AGE

replicaset.apps/ingress-nginx-controller-54c4c897b6   1         1         0       4m9s


NAME                                       COMPLETIONS   DURATION   AGE

job.batch/ingress-nginx-admission-create   1/1           9s         4m9s

job.batch/ingress-nginx-admission-patch    1/1           9s         4m9s



7

nginx 컨트럴러 pod ip 는 ?

라벨값이 있어 라벨값으로 확인


kubectl get pod -n ingress-nginx -o wide -l app.kubernetes.io/component=controller

NAME    READY   STATUS    RESTARTS   AGE   IP    NODE      NOMINATED NODE   READINESS GATES

ingress-nginx-controller-584dc4797b-z5g29   1/1     Running   0          33m   100.112.248.194   ip-172-20-60-135.ap-northeast-1.compute.internal   <none>           <none>


8

서비스 포트 확인하기?


kubectl get svc -n ingress-nginx

NAME                                 TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)                      AGE

ingress-nginx-controller  NodePort  100.71.111.209  <none>  80:30294/TCP,443:32625/TCP   44m

ingress-nginx-controller-admission   ClusterIP   100.65.182.94    <none>   443/TCP           44m


// 외부에서 node 포트로 들어오는것 30294 포트이다.  TCP http 접속하는것이다.

// 외부에서  32625로 들어오면 https  접속


9

kubectl describe svc -n ingress-nginx ingress-nginx-controller | grep Local

External Traffic Policy:  Local



10

접근 테스트할때 사용하기 위해 http 포트를 변수로 지정 ? 


export IngHttp=$(kubectl get service -n ingress-nginx ingress-nginx-controller -o jsonpath='{.spec.ports[0].nodePort}')

echo $IngHttp

30294


11

https  포트를 변수로 지정 ?


export IngHttps=$(kubectl get service -n ingress-nginx ingress-nginx-controller -o jsonpath='{.spec.ports[1].nodePort}')

echo $IngHttps

32625




<5>  데이트 흐름을 쉽게 보는 플러그인 설치 (옵션)


https://kubernetes.github.io/ingress-nginx/kubectl-plugin/


1

set -x; cd "$(mktemp -d)" && OS="$(uname | tr '[:upper:]' '[:lower:]')" && ARCH="$(uname -m | sed -e 's/x86_64/amd64/' -e 's/\(arm\)\(64\)\?.*/\1\2/' -e 's/aarch64$/arm64/')" && curl -fsSLO "https://github.com/kubernetes-sigs/krew/releases/latest/download/krew.tar.gz" && tar zxvf krew.tar.gz && KREW=./krew-"${OS}_${ARCH}" && "$KREW" install krew



2

cd

echo 'export PATH="${PATH}:${HOME}/.krew/bin"' >> $HOME/.bashrc

source $HOME/.bashrc


3

kubectl krew update

kubectl krew search

kubectl krew update


4

플러그인 설치 ?


kubectl krew install ingress-nginx


5

아래는 확인 하는법 ?

보기 편함 


/ 로 들어오면      svc1-web의 서비스에 80 으로 간다!!! 를 한번에 볼수 있다.

pod가 1개 있다.


kubectl ingress-nginx ingresses

INGRESS NAME   HOST+PATH   ADDRESSES        TLS   SERVICE      SERVICE PORT   ENDPOINTS

ingress-1      /           13.114.225.167   NO    svc1-web     80             1

ingress-1      /guest      13.114.225.167   NO    svc2-guest   8080           2

ingress-1      /admin      13.114.225.167   NO    svc3-admin   8080           3


6

kubectl ingress-nginx ingresses --all-namespaces

NAMESPACE INGRESS NAME  HOST+PATH  ADDRESSES TLS SERVICE  SERVICE PORT   ENDPOINTS

default     ingress-1      /           13.114.225.167   NO    svc1-web     80             1

default     ingress-1      /guest      13.114.225.167   NO    svc2-guest   8080           2

default     ingress-1      /admin      13.114.225.167   NO    svc3-admin   8080           3



<6> 다음 편


https://brunch.co.kr/@topasvga/1708



감사합니다.

브런치는 최신 브라우저에 최적화 되어있습니다. IE chrome safari