[Kubernetes in Google Cloud] - Lecture3. Orchestrating the Cloud with Kubernetes

윰진·2023년 4월 26일
0

빅데이터특화과정

목록 보기
3/8

GOAL

  • Kubernetes Engine을 사용하여 전체 Kubernetes cluster를 provisioning 하는 방법
  • kubectl을 사용하여 Docker container를 관리하고 배포하는 방법
  • Kubernetes 배포와 서비스를 사용하여 애플리케이션을 microservices로 분할하는 방법

00. Setting

1 ) zone setting

gcloud config set compute/zone us-central1-b

2 ) cluster 시작

gcloud container clusters create io

3 ) 참고

re-authenticate
cloud shell과 연결이 끊겼을 때 재인증

gcloud container clusters get-credentials io

Kubernetes Engine은 몇몇 가상 머신을 프로비저닝하기 때문에 cluster 생성에 시간이 소요됨

# 결과 
kubeconfig entry generated for io.
NAME: io
LOCATION: us-central1-b
MASTER_VERSION: 1.24.10-gke.2300
MASTER_IP: 104.154.24.73
MACHINE_TYPE: e2-medium
NODE_VERSION: 1.24.10-gke.2300
NUM_NODES: 3
STATUS: RUNNING

01. Get the sample code

1 ) Source Code 복사하기

gsutil cp -r gs://spls/gsp021/* .

2 ) Directory 확인하기

cd orchestrate-with-kubernetes/kubernetes

02. Quick Kubernetes Demo

kubectl create

1 ) nginx container 실행하기

kubectl create deployment nginx --image=nginx:1.10.0

deployment는 pods를 실행시키고, node가 실행에 실패할 때도 운영해준다.

쿠버네티스에서 모든 컨테이너는 pod에서 실행된다.

2 ) 실행 중인 nginx container 보기

kubectl get pods

결과

NAME                     READY   STATUS    RESTARTS   AGE
nginx-68899cc8d6-8j5vj   1/1     Running   0          3m2s

3 ) port forwarding 으로 쿠버네티스 밖으로 노출시키기

kubectl expose deployment nginx --port 80 --type LoadBalancer

# service/nginx exposed

공용 IP address에 외부 Load Balancer가 생성됨

  • 공용 IP address로 접근하면 nginx로 route 됨

4 ) Services 리스트 확인

kubectl get services


NAME         TYPE           CLUSTER-IP    EXTERNAL-IP     PORT(S)        AGE
kubernetes   ClusterIP      10.72.0.1     <none>          443/TCP        18m
nginx        LoadBalancer   10.72.7.104   34.173.46.242   80:32109/TCP   2m25s

5 ) 외부에서 Nginx container 접속 가능한지 확인

curl http://<External IP>:80

03. Pods

Pods는 한 개 이상의 container들의 집합을 나타낸다. 일반적으로 다른 것들과 강한 종속성을 가지는 여러 개의 container들이 있다면 이 container들을 하나의 pod에 묶을 수 있다. (패키지 할 수 있다.)

Pods
한 개 이상의 container들의 집합
각 container 들이 강한 종속성을 보이는 경우에 하나의 pod로 package 할 수 있다.

Volumes
Pod에서 container에 의해 사용될 수 있는 data disk

Pods는 container들에 대해 shared namespace를 제공하고, container 끼리 서로 통신이 가능하며 부착된 volume을 공유한다.

Pods는 network namespace를 공유하며, pod 당 하나의 IP Address를 갖는다.

04. Creating pods

1 ) monolith pod configuration file 살펴보기

cd ~/orchestrate-with-kubernetes/kubernetes
cat pods/monolith.yaml
apiVersion: v1
kind: Pod
metadata:
  name: monolith
  labels:
    app: monolith
spec:
  containers:
    - name: monolith
      image: kelseyhightower/monolith:1.0.0
      args:
        - "-http=0.0.0.0:80"
        - "-health=0.0.0.0:81"
        - "-secret=secret"
      ports:
        - name: http
          containerPort: 80
        - name: health
          containerPort: 81
      resources:
        limits:
          cpu: 0.2
          memory: "10Mi"
  • pod는 하나의 container monolith 로 구성
  • 시작할 때 container에 arguments를 전달
  • http traffic을 위해 80 port 개방

2 ) monolith pod 생성

kubectl create -f pods/monolith.yaml

3 ) Default namespace에서 실행중인 모든 pods를 list 하기

kubectl get pods

NAME                     READY   STATUS    RESTARTS   AGE
monolith                 1/1     Running   0          21s
nginx-68899cc8d6-8j5vj   1/1     Running   0          13m

4 ) monolith pod에 대한 상세 정보 보기 ( IP 주소, event log 등 )

kubectl describe pods monolith

# 결과
Name:             monolith
Namespace:        default
Priority:         0
Service Account:  default
Node:             gke-io-default-pool-b4f4f7b4-qzb7/10.128.0.3
Start Time:       Wed, 26 Apr 2023 16:56:10 +0000
Labels:           app=monolith
Annotations:      <none>
Status:           Running
IP:               10.68.0.4

05. Interacting with pods

기본 값으로, pods는 private IP address에 할당되고 클러스터 밖에서는 접근이 불가능하다.

  • kubectl port-forward로 monolith pod 내의 port와 local port를 맵핑해보자.

1 ) Port forwarding

kubectl port-forward monolith 10080:80

2 ) 접근 확인

curl http://127.0.0.1:10080

# {"message":"Hello"}

3 ) secure를 endpoint로 하면 어떤 일이 생길까 ?

curl http://127.0.0.1:10080/secure

# authorization failed

4 ) auth token을 받아 로그인 시도하기

curl -u user http://127.0.0.1:10080/login

# JWT 토큰이 반환됨 
# 환경 변수에 저장하기
TOKEN=$(curl http://127.0.0.1:10080/login -u user|jq -r '.token')

5 ) secure로 접근해보기

curl -H "Authorization: Bearer $TOKEN" http://127.0.0.1:10080/secure

6 ) monolith 로그 확인하기

kubectl logs monolith
# 실시간 로그 확인
kubectl logs -f monolith

2023/04/26 16:56:14 Starting server...
2023/04/26 16:56:14 Health service listening on 0.0.0.0:81
2023/04/26 16:56:14 HTTP service listening on 0.0.0.0:80
127.0.0.1:51648 - - [Wed, 26 Apr 2023 17:01:57 UTC] "GET / HTTP/1.1" curl/7.74.0
127.0.0.1:54146 - - [Wed, 26 Apr 2023 17:02:07 UTC] "GET /secure HTTP/1.1" curl/7.74.0
127.0.0.1:59542 - - [Wed, 26 Apr 2023 17:04:08 UTC] "GET /login HTTP/1.1" curl/7.74.0

7 ) Monolith Pod와 상호 작용하기 : kubectl exec

Container 내에서 trouble shooting이 필요한 경우 사용할 수 있음

kubectl exec monolith --stdin --tty -c monolith -- /bin/sh
  • 예를 들어, pod 내부에서 외부로 연결성을 확인해볼 수 있다.
ping -c 3 google.com


PING google.com (142.250.152.139): 56 data bytes
64 bytes from 142.250.152.139: seq=0 ttl=114 time=0.937 ms
64 bytes from 142.250.152.139: seq=1 ttl=114 time=0.425 ms
64 bytes from 142.250.152.139: seq=2 ttl=114 time=0.438 ms

--- google.com ping statistics ---
3 packets transmitted, 3 packets received, 0% packet loss
round-trip min/avg/max = 0.425/0.600/0.937 ms

06. Services

Pods들은 영구적이지 않고, 재실행될 때 마다 다른 IP 주소를 가진다.
Pods 간 연결을 위해서는 Services 가 필요하다.

Services
Services는 labels를 이용하여 동작중인 Pods를 결정

  • Lables가 일치하는 pods는 자동으로 선택되고 노출된다.

Service가 pods의 집합에 제공하는 접근 레벨은 Service 의 타입에 의해 결정된다.

  • ClusterIP (internal)
    • Default type으로 Service가 cluster 내에서만 보임을 의미한다.
  • NodePort
    • Cluster 내의 각 노드에 외부에서 접근 가능한 IP를 제공한다.
  • LoadBalancer
    • Cloud provider로 부터 load balancer를 추가한다. Service에서 Nodes 내부로 traffic을 전달한다.

07. Creating a service

1 ) https 를 처리할 수 있는 보안 pod 생성하기

cd ~/orchestrate-with-kubernetes/kubernetes
cat pods/secure-monolith.yaml

# secure-monolith pods와 구성 데이터 생성 
kubectl create secret generic tls-certs --from-file tls/
kubectl create configmap nginx-proxy-conf --from-file nginx/proxy.conf
kubectl create -f pods/secure-monolith.yaml

2 ) Secure-monolith pod를 외부로 노출하기 위해 kubernetes service 생성

cat services/monolith.yaml

kind: Service
apiVersion: v1
metadata:
  name: "monolith"
spec:
  selector:
    app: "monolith"
    secure: "enabled"
  ports:
    - protocol: "TCP"
      port: 443
      targetPort: 443
      nodePort: 31000
  type: NodePort

label 에 해당하는 app:monolith 그리고 secure 설정에 해당하는 secure:enabled가 선택기에 의해 찾아지고 외부로 노출되는데 사용됨

3 ) monolith service 생성하기

kubectl create -f services/monolith.yaml

사용하고 있는 port는 다른 앱에서 사용할 수 없음

4 ) monolith service 의 port 방화벽 풀어주기

gcloud compute firewall-rules create allow-monolith-nodeport --allow=tcp:31000

Creating firewall...working..Created [https://www.googleapis.com/compute/v1/projects/qwiklabs-gcp-04-7e1a6c611d55/global/firewalls/allow-monolith-nodeport].
Creating firewall...done.
NAME: allow-monolith-nodeport
NETWORK: default
DIRECTION: INGRESS
PRIORITY: 1000
ALLOW: tcp:31000
DENY:
DISABLED: False

5 ) port forwarding 없이 서비스 접근 해보기

gcloud compute instances list
curl -k https://<EXTERNAL_IP>:31000

kubectl get services monolith
kubectl describe services monolith
Questions

  • Why are you unable to get a response from the monolith service?
  • How many endpoints does the monolith service have?
  • What labels must a Pod have to be picked up by the monolith service?

08. Adding labels to pods

Monolith service는 endpoints가 없다.
따라서, troubleshoot을 위해서 kubectl get pods와 label query를 사용해야 한다.

1 ) monolith label을 가진 여러 파드가 존재

kubectl get pods -l "app=monolith"


NAME              READY   STATUS    RESTARTS   AGE
monolith          1/1     Running   0          30m
secure-monolith   2/2     Running   0          12m

2 ) app=monolith와 secure=enabled를 만족하는 것은 검색되지 않음

kubectl get pods -l "app=monolith,secure=enabled"

# No resources found in default namespace.

3 ) secure-monolith Pod에 label 추가하기

kubectl label pods secure-monolith 'secure=enabled'
kubectl get pods secure-monolith --show-labels

NAME              READY   STATUS    RESTARTS   AGE   LABELS
secure-monolith   2/2     Running   0          14m   app=monolith,secure=enabled

4 ) monolith service의 endpoint 확인

kubectl describe services monolith | grep Endpoints

# Endpoints:                10.68.0.5:443

5 ) 접근 확인

gcloud compute instances list

NAME: gke-io-default-pool-b4f4f7b4-qt21
ZONE: us-central1-b
MACHINE_TYPE: e2-medium
PREEMPTIBLE:
INTERNAL_IP: 10.128.0.4
EXTERNAL_IP: 34.173.33.39
STATUS: RUNNING

NAME: gke-io-default-pool-b4f4f7b4-qw1s
ZONE: us-central1-b
MACHINE_TYPE: e2-medium
PREEMPTIBLE:
INTERNAL_IP: 10.128.0.5
EXTERNAL_IP: 34.122.109.212
STATUS: RUNNING

NAME: gke-io-default-pool-b4f4f7b4-qzb7
ZONE: us-central1-b
MACHINE_TYPE: e2-medium
PREEMPTIBLE:
INTERNAL_IP: 10.128.0.3
EXTERNAL_IP: 35.188.211.125
STATUS: RUNNING

curl -k https://<EXTERNAL_IP>:31000

09. Deploying applications with Kubernetes

Production에서 container를 관리하고 scaling 할 준비

Deployments
Pods를 관리하는 저레벨의 동작을 추상화
Pods의 실행과 중지를 관리하기 위해 Replica Sets를 사용

Pods가 update 또는 확장이 필요할 때 Deployment가 이를 도울 수 있고, Pods가 down 되었을 경우 재시작을 할 수 있음

10. Creating deployments

monolith app 살펴보기

  • auth : 인가받은 사용자에 대한 JWT 발급
  • hello
  • frontend

1 ) auth deployment

auth deployment configuration file

cat deployments/auth.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: auth
spec:
  selector:
    matchlabels:
      app: auth
  replicas: 1
  template:
    metadata:
      labels:
        app: auth
        track: stable
    spec:
      containers:
        - name: auth
          image: "kelseyhightower/auth:2.0.0"
          ports:
            - name: http
              containerPort: 80
            - name: health
              containerPort: 81

Replica 가 한 개로, 확장하고 싶다면 이 개수를 늘려주면 됨

kubectl create -f deployments/auth.yaml
kubectl create -f services/auth.yaml

2 ) hello deployment

kubectl create -f deployments/hello.yaml
kubectl create -f services/hello.yaml

3 ) frontend deployment

kubectl create configmap nginx-frontend-conf --from-file=nginx/frontend.conf
kubectl create -f deployments/frontend.yaml
kubectl create -f services/frontend.yaml

4 ) 서비스 확인

kubectl get services frontend
curl -k https://<EXTERNAL-IP>

NAME       TYPE           CLUSTER-IP    EXTERNAL-IP   PORT(S)         AGE
frontend   LoadBalancer   10.72.5.188   <pending>     443:30768/TCP   2s

업로드중..

구글 퀵랩 Kubernetes in Google Cloud를 학습하고 정리한 내용입니다.

0개의 댓글