[pkos] 쿠버네티스 스터디 - 4주차

xgro·2023년 2월 9일
1

PKOS

목록 보기
5/11

📌 Summary

  • 헬름 차트를 이용하여 인프라 관리에 필요한 리소스를 설치할 수 있습니다.

  • GitOps를 도입하여 단일 진실의 원칙(SSOT)에 의거하여 인프라를 관리할 수 있습니다.


📌 Architecture

쿠버네티스 환경의 애플리케이션 배포를 위해 필요한 인프라를 구축합니다.


이번주 실습에서 성능을 요구하는 파드를 사용합니다.

  1. kops 인스턴스 t3.small & 노드 c5.2xlarge (vCPU 8, Memory 16GiB) 배포

  2. kops 인스턴스 t3.small : 도커 엔진 확인

  3. EC2 instance profiles 설정 및 AWS LoadBalancer 배포 & ExternalDNS 설치 및 배포


📌 Study Notes

👉 Step 01. Harbor

목표 : 하버(Harbor)를 이용하여 로컬 컨테이너 이미지 저장소 구축하기

하버는 온프레미스 환경에서 사용할 수 있는 컨테이너 이미지 저장소 입니다.
pkos 스터디에서는 Helm 차트를 이용하여 Harbor를 구축하였습니다.

하버(Harbor)란?

Harbor는 정책 및 역할 기반 액세스 제어로 아티팩트를 보호하고, 이미지를 스캔하고 취약성이 없도록 하며, 이미지를 신뢰할 수 있는 것으로 서명하는 오픈 소스 레지스트리입니다. CNCF 대학원 프로젝트인 Harbour는 규정 준수, 성능 및 상호 운용성을 제공하여 Kubernetes 및 Docker와 같은 클라우드 네이티브 컴퓨팅 플랫폼에서 아티팩트를 일관되고 안전하게 관리할 수 있도록 지원합니다. - 공식 홈페이지

Prerequisites

  • Hardware
    하드웨어는 다음 사양을 충족하여야 합니다.
    ResourceMinimumRecommended
    CPU2 CPU4 CPU
    Mem4 GB8 GB
    Disk40 GB160 GB
  • Network Ports

    PortProtocolDescription
    443HTTPSHarbor portal and core API accept HTTPS requests on this port.
    4443HTTPSConnections to the Docker Content Trust service for Harbor.
    80HTTPHarbor portal and core API accept HTTP requests on this port.

✅ Helm 차트로 하버 설치

# 사용 리전의 인증서 ARN 확인
aws acm list-certificates --query 'CertificateSummaryList[].CertificateArn[]' --output text
CERT_ARN=`aws acm list-certificates --query 'CertificateSummaryList[].CertificateArn[]' --output text`
echo "alb.ingress.kubernetes.io/certificate-arn: $CERT_ARN"

# 하버 설치
helm repo add harbor https://helm.goharbor.io
helm fetch harbor/harbor --untar
vim ~/harbor/values.yaml
----------------------
expose.tls.certSource=none                        # 19줄
expose.ingress.hosts.core=harbor.<각자 자신의 도메인>    # 36줄
expose.ingress.hosts.notary=notary.<각자 자신의 도메인>  # 37줄
expose.ingress.hosts.core=harbor.xgro.be
expose.ingress.hosts.notary=notary.xgro.be
expose.ingress.controller=alb                      # 44줄
expose.ingress.className=alb                       # 46줄~
expose.ingress.annotations=alb.ingress.kubernetes.io/scheme: internet-facing
expose.ingress.annotations=alb.ingress.kubernetes.io/target-type: ip
expose.ingress.annotations=alb.ingress.kubernetes.io/listen-ports: '[{"HTTPS":443}, {"HTTP":80}]'
expose.ingress.annotations=alb.ingress.kubernetes.io/certificate-arn: ${CERT_ARN}
externalURL=https://harbor.<각자 자신의 도메인>          # 131줄
# 예시) externalURL=https://harbor.xgro.be             
----------------------

# 설치
helm install harbor harbor/harbor -f ~/harbor/values.yaml --namespace harbor --version 1.11.0

# 확인
# registry : 컨테이너 이미지를 저장
# chartmuseum : 하버를 컨테이너 이미지뿐 아니라, 헬름 차트 리포지토리로도 사용
# notary : 서명이 완료된 컨테이너 이미지만 운영 환경에 사용하도록 설정. 서명이 완료된 이미지는 별도로 구분
# trivy : 컨테이너 이미지의 보안 취약점을 스캔, 스캔 기능은 별도 솔루션에서 제공하여 관리자는 보안 스캔용 도구를 선택 가능
helm list -n harbor
kubectl get pod,pvc,ingress,deploy,sts -n harbor
kubectl get ingress -n harbor harbor-ingress -o json | jq
kubectl get-all -n harbor
kubectl krew install df-pv && kubectl df-pv

✅ 하버 웹 접속 및 이미지 업로드

https://harbor.<각자 자신의 도메인> 으로 접속하면 하버 웹페이지를 확인할 수 있습니다.

  • Login : admin / Harbor12345
  • New project → Name(pkos), Access Level(Public Check) ⇒ OK 클릭
    • 신규 프로젝트 생성 : 프로젝트 단위로 컨테이너 이미지 저장소를 관리, 프로젝트 별로 사용자 권한(RBAC) 보안 설정이 가능합니다.

kops-ec2에서 로컬 이미지를 원격 하버 이미지로 업로드

# 컨테이너 이미지 가져오기
docker pull nginx
docker pull busybox 
docker images

# 태그 설정
docker tag busybox harbor.$KOPS_CLUSTER_NAME/pkos/busybox:0.1
docker image ls

# insecure 설정
cat <<EOT> /etc/docker/daemon.json
{
    "insecure-registries" : ["harbor.$KOPS_CLUSTER_NAME"]
}
EOT
cat /etc/docker/daemon.json
systemctl daemon-reload && systemctl restart docker

# 로그인 - 방안1
docker login harbor.$KOPS_CLUSTER_NAME -u admin -p Harbor12345
cat /root/.docker/config.json | jq

# 로그인 - 방안2
echo 'Harbor12345' > harborpw.txt
cat harborpw.txt | docker login harbor.$KOPS_CLUSTER_NAME -u admin --password-stdin
cat /root/.docker/config.json | jq

# 이미지 업로드
docker push harbor.$KOPS_CLUSTER_NAME/pkos/busybox:0.1

이미지가 업로드 되는 과정을 확인할 수 있습니다.

컨테이너 이미지 업로드 시 자동으로 이미지 보안 스캔 기능 사용 해보도록 하겠습니다.

  • 프로젝트에서 Configuration 클릭 후 아래 Automatically... 클릭 후 맨 하단에 Save 선택

이미지 업로드시에 자동으로 취약점을 확인합니다.

👉 Step 02. GitLab

목표 : 깃랩(GitLab)를 이용하여 로컬 깃(Git) 소스 저장소 구축

Gitlab은 온프레미스 환경에서 사용할 수 있는 소스 코드 원격 저장소 입니다.

Helm 차트를 이용하여 Gitlab을 구축하였습니다.

  • 헬름 차트로 깃랩 설치 후 웹 로그인 - HelmChart Docs
    # 모니터링
    kubectl create ns gitlab
    watch kubectl get pod,pvc,ingress -n gitlab
    
    # 설치
    helm repo add gitlab https://charts.gitlab.io/
    helm repo update
    helm fetch gitlab/gitlab --untar
    vim ~/gitlab/values.yaml
    ----------------------
    global:
      hosts:
        domain: <각자자신의도메인>             # 52줄
        https: true
    
      ingress:                             # 66줄~
        configureCertmanager: false
        provider: aws
        class: alb
        annotations:
          alb.ingress.kubernetes.io/scheme: internet-facing
          alb.ingress.kubernetes.io/target-type: ip
          alb.ingress.kubernetes.io/listen-ports: '[{"HTTPS":443}, {"HTTP":80}]'
          alb.ingress.kubernetes.io/certificate-arn: ${CERT_ARN}
          alb.ingress.kubernetes.io/success-codes: 200-399
          alb.ingress.kubernetes.io/group.name: "gitlab"
        tls:                               # 79줄
          enabled: false
    
    certmanager:                           # 833줄 
      installCRDs: false
      install: false
      rbac:
        create: false
    
    nginx-ingress:                         # 847줄 
      enabled: false
    
    prometheus:                            # 904줄 
      install: false
    
    gitlab-runner:                         # 1130줄 
      install: false
    ----------------------
    
    helm install gitlab gitlab/gitlab -f ~/gitlab/values.yaml --namespace gitlab --version 6.8.1
    
    # 확인 - SubCharts
    # gitlab-gitaly : 웹서비스 혹은 ssh 방식으로 진행되는 깃 제목, 브랜치, 태그 등의 깃 요청 등에 대한 작업을 담당
    # gitlab-gitlab-shell : https 가 아닌 ssh 방식으로 깃 명령어 실행 시 해당 요청을 처리
    # gitlab-kas : gitlab agent server
    # gitlab-postgresql : 유저, 권한, 이슈 등 깃랩의 메타 데이터 정보가 저장
    # gitlab-redis-master : 깃랩 작업 정보는 레디스 캐시 서버를 이용하여 처리
    # gitlab-sidekiq-all-in-1-v2 : 레디스와 연동하여 작업 큐 처리 용도로 사용
    # gitlab-webservice-default : 깃랩 웹 서비스를 처리
    helm list -n gitlab
    kubectl get pod,pvc,ingress,deploy,sts -n gitlab
    kubectl get-all -n gitlab
    
    # 웹 root 계정 암호 확인
    kubectl get secrets -n gitlab gitlab-gitlab-initial-root-password --template={{.data.password}} | base64 -d ;echo
    hhBvAjXoANx8kVIVpcwdgvc6A0kFDIIQFxikRDJfwVPBXn0dxmNBgc7zssSBskTj
    
    # 웹 접속 https://gitlab.<각자 자신의 도메인> (root / 웹 root 계정 암호)

✅ [FinOps] Gitlab 설치시 하나의 로드 밸런서로 서비스 하기

헬름 차트 파일의 global.ingress.annotation.alb.ingress.kubernetes.io/group.name: "gitlab"

설정하게 되면, 하나의 로드밸런서만 배포 되며 대상그룹이 그룹화되어 관리됩니다.

( 실무 적용시 로드밸런서의 개수를 줄여 비용 최적화에 기여할 수 있습니다. )

# 4개의 Ingress 가 1개의 ALB를 공유해서 사용 : ALB의 Rule 확인해볼것!
# alb.ingress.kubernetes.io/group.name: "gitlab"
kubectl get ingress -n gitlab
NAME                        CLASS   HOSTS                  ADDRESS                                                             PORTS   AGE
gitlab-kas                  alb     kas.xgro.be            k8s-gitlab-3fbf5c8cab-1066962252.ap-northeast-2.elb.amazonaws.com   80      93s
gitlab-minio                alb     minio.xgro.be          k8s-gitlab-3fbf5c8cab-1066962252.ap-northeast-2.elb.amazonaws.com   80      93s
gitlab-registry             alb     registry.xgro.be       k8s-gitlab-3fbf5c8cab-1066962252.ap-northeast-2.elb.amazonaws.com   80      93s
gitlab-webservice-default   alb     gitlab.xgro.be         k8s-gitlab-3fbf5c8cab-1066962252.ap-northeast-2.elb.amazonaws.com   80      93s

✅ 계정 생성 후 테스트

깃랩을 설치하고 나면, 유저의 이름과 토큰 값을 이용하여 코드 원격 저장소로 사용할 수 있습니다.

  • 생성한 깃랩 프로젝트에 쿠버네티스에서 사용하는 YAML 파일을 업로드 ⇒ 토큰 값 확인
    # Workspace 생성
    mkdir ~/gitlab-test && cd ~/gitlab-test
    
    # git 계정 초기화 : 토큰 및 로그인 실패 시 매번 실행해주자
    git config --system --unset credential.helper
    git config --global --unset credential.helper
    
    # git 계정 정보 확인 및 global 계정 정보 입력
    git config --list
    git config --global user.name "<각자 자신의 Gialba 계정>"
    git config --global user.email "<각자 자신의 Gialba 계정의 이메일>"
    git config --global user.name "xgro"
    git config --global user.email "test01@example.com"
    
    # git clone
    git clone https://gitlab.$KOPS_CLUSTER_NAME/<각자 자신의 Gialba 계정>/test-stg.git
    git clone https://gitlab.$KOPS_CLUSTER_NAME/xgro/test-stg.git
    Cloning into 'test-stg'...
    Username for 'https://gitlab.xgro.be': xgro
    Password for 'https://gasida@gitlab.xgro.be': <토큰 입력>
    
    # 이동
    ls -al test-stg && cd test-stg
    
    # 파일 생성 및 깃 업로드(push) : 웹에서 확인
    echo "gitlab test memo" >> test.txt
    git add . && git commit -m "initial commit - add test.txt"
    git push
    Username for 'https://gitlab.xgro.be': xgro
    Password for 'https://gasida@gitlab.xgro.be': <토큰 입력>


👉 Step 03. ArgoCD

목표 : 아르고시디(ArgoCD)를 활용한 깃옵스(GitOps) 시스템 구축

ArgoCD 란?
GitOps를 구현할 수 있도록 지원하는 CD 도구입니다.
Argo CD is a declarative, GitOps continuous delivery tool for Kubernetes.

ArgoCD를 운영하기전 반드시 인프라 운영을 담당하는 DevOps 엔지니어로서 숙지해야하는 중요한 내용입니다.

지속적인 배포(Continuous Delivery, CD)란 개발자가 소스코드를 변경해서 깃 저장소에 푸시하면 해당 변경 사항이 고객이 사용하는 실제 운영환경의 시스템까지 자동으로 반영함

  • 개발자의 코드가 원격 저장소에 업로드됐을 때 아르고시디가 자동으로 해당 코드를 클러스터 운영환경에 배포합니다.
  • 아르고시티로 배포한 헬름 애플리케이션의 리소스 목록, 각 리소스 간 관계 및 에러 유무를 UI로 보여줍니다.

단일 진실 원천(SSOT, Single Source Of Truth)이란 어떠한 진실(결과)의 원인이 하나의 이유(원천)에서 비롯되는 것을 의미합니다.

  • 쿠버네티스 환경에서 깃옵스의 의미는 실제 운영 중인 클러스터의 상태를 개발자의 로컬 PC혹은 아무런 기록을 남기지 않고 클러스터에서 임의로 수정하게 하지 않고 공용으로 관리하는 깃 저장소에서만 유일하게 변경을 허용함으로써 단일 진실 원천(SSOT)를 구현합니다.
  • 아르고시디를 사용하면 쿠버네티스 매니페스트 소스 파일을 여러 개발자의 개인 PC에 보관하지 않고 중앙의 통합된 깃 저장소에 반드시 업로드하고 동기화하도록 정책을 관리할 수 있습니다.
  • 헬름 차트로 설치 후 웹 로그인 - HelmChart
    # 모니터링
    **kubectl create ns argocd
    watch kubectl get pod,pvc,svc -n argocd**
    
    # 설치
    cd
    helm repo add argo https://argoproj.github.io/argo-helm
    helm repo update
    helm install argocd argo/argo-cd --set server.service.type=LoadBalancer --namespace argocd --version 5.19.14
    
    # 확인
    # argocd-application-controller : 실행 중인 k8s 애플리케이션의 설정과 깃 저장소의 소스 파일에 선언된 상태를 서로 비교하는 컨트롤러. 상태와 다르면 ‘OutOfSync’ 에러를 출력.
    # argocd-dex-server : 외부 사용자의 LDAP 인증에 Dex 서버를 사용할 수 있음
    # argocd-repo-server : 원격 깃 저장소의 소스 코드를 아르고시디 내부 캐시 서버에 저장합니다. 디렉토리 경로, 소스, 헬름 차트 등이 저장.
    helm list -n **argocd**
    kubectl get pod,pvc,svc,deploy,sts -n **argocd**
    kubectl get-all -n **argocd**
    
    # admin 계정의 암호 확인
    ARGOPW=$(kubectl -n argocd get secret argocd-initial-admin-secret -o jsonpath="{.data.password}" | base64 -d)
    echo $ARGOPW
    yv3xaUxPrkwNOdzH
    
    # 웹 접속 로그인 (admin) CLB의 DNS 주소로 접속 http, https
  • 아르고시디로 애플리케이션 배포에 사용할 깃 저장소와 쿠버네티스 클러스터 정보를 등록을 위해, argocd CLI 도구 설치 - 링크 악분일상
    # 최신버전 설치
    curl -sSL -o argocd-linux-amd64 https://github.com/argoproj/argo-cd/releases/latest/download/argocd-linux-amd64
    install -m 555 argocd-linux-amd64 /usr/local/bin/argocd
    chmod +x /usr/local/bin/argocd
    
    # 버전 확인
    argocd version --short
    
    # Help
    # argocd app : 쿠버네티스 애플리케이션 동기화 상태 확인
    # argocd context : 복수의 쿠버네티스 클러스터 등록 및 선택
    # argocd login : 아르고시디 서버에 로그인 
    # argocd repo : 원격 깃 저장소를 등록하고 현황 파악
    argocd
    
    # CLB 도메인 변수 지정
    CLB=**<각자 자신의 argocd 서비스의 CLB 도메인 주소>**
    CLB=adc4dcad7d21743c4b6524f37f2e7ca3-1872175753.ap-northeast-2.elb.amazonaws.com
    
    # argocd 서버 로그인
    argocd login $CLB --username admin --password $ARGOPW
    
    # 기 설치한 깃랩의 프로젝트 URL 을 argocd 깃 리포지토리(argocd repo)로 등록. 깃랩은 프로젝트 단위로 소스 코드를 보관.
    argocd repo add https://gitlab.$KOPS_CLUSTER_NAME/<깃랩 계정명>/test-stg.git --username <깃랩 계정명> --password <깃랩 계정 암호>
    argocd repo add https://gitlab.$KOPS_CLUSTER_NAME/xgro/test-stg.git --username xgro --password P@ssw0rd
     
    # 등록 확인 : 기본적으로 아르고시디가 설치된 쿠버네티스 클러스터는 타깃 클러스터로 등록됨
    argocd repo list
    TYPE  NAME  REPO                                            INSECURE  OCI    LFS    CREDS  STATUS      MESSAGE  PROJECT
    git         https://gitlab.xgro.be/xgro/test-stg.git        false     false  false  true   Successful
    
    # 기본적으로 아르고시디가 설치된 쿠버네티스 클러스터는 타깃 클러스터로 등록됨
    argocd cluster list
    SERVER                          NAME        VERSION  STATUS   MESSAGE                                                  PROJECT
    https://kubernetes.default.svc  in-cluster           Unknown  Cluster has no applications and is not being monitored.
  • ArgoCD를 이용하여 RabbitMQ 헬름 애플리케이션 배포하기 :
    RabbitMQ Helm 깃랩 업로드 - HelmChart
    ```bash
    # test-stg 깃 디렉터리에서 아래 실행
    cd ~/gitlab-test/test-stg
    
    # 깃 원격 오리진 주소 확인
    git config -l | grep remote.origin.url
    
    # RabbitMQ 헬름 차트 설치
    helm repo add bitnami https://charts.bitnami.com/bitnami
    helm repo update
    ****helm fetch bitnami/rabbitmq --untar
    cd rabbitmq/
    cp values.yaml my-values.yaml
    
    # 헬름 차트를 깃랩 저장소에 업로드
    git add . && git commit -m "add rabbitmq helm"
    git push
    
    # argocd CRD 확인
    kubectl get crd | grep argo
    applications.argoproj.io                              2022-01-25T15:46:16Z   # 배포 앱 현재 실행 상태와 깃 저장소의 의도한 상태를 계속 비교
    appprojects.argoproj.io                               2022-01-25T15:46:16Z   # 프로젝트 단위 구분
    argocdextensions.argoproj.io                          2022-01-25T15:46:16Z
    
    # 
    cd ~/
    curl -s -O https://raw.githubusercontent.com/wikibook/kubepractice/main/ch15/rabbitmq-helm-argo-application.yml
    **vim rabbitmq-helm-argo-application.yml**
    --------------------------------------
    apiVersion: argoproj.io/v1alpha1
    kind: Application
    metadata:
      name: rabbitmq-helm
      namespace: argocd
      finalizers:
      - resources-finalizer.argocd.argoproj.io
    spec:
      **destination**:
        namespace: rabbitmq
        server: https://kubernetes.default.svc
      project: default
      **source**:
        repoURL: https://gitlab.**xgro.be/xgro**/test-stg.git
        path: **rabbitmq**
        targetRevision: HEAD
        helm:
          valueFiles:
          - my-values.yaml
      syncPolicy:
        syncOptions:
        - CreateNamespace=true
    --------------------------------------
    
    # 모니터링 : argocd 웹 화면 보고 있기!
    # 배포
    kubectl apply -f rabbitmq-helm-argo-application.yml
    
    # YAML 파일을 적용(apply)하여 아르고시디 ‘Application’ CRD를 생성
    kubectl get applications.argoproj.io -n argocd
    NAME            SYNC STATUS   HEALTH STATUS
    rabbitmq-helm   OutOfSync     Missing
    ```
  • argocd 웹 화면 rabbitmq 클릭 → 헬름 차트 상세 내역 확인 ⇒ 화면 상단 SYNC 클릭해 동기화 실행 : helm install 을 실행하지 않아도 됩니다!

📌 Conclusion

이미지 저장을 위한 Repository(harbor)부터 소스 코드 저장소(gitlab), Continues Deploy(argoCD)까지 GitOps를 구현하기 위한 방안을 스터디 하였습니다.

ECS 환경에서 Jenkins를 이용하여 CI/CD Pipeline을 구축하고 있는 저로서는 K8s 환경에서의 GitOps를 통한 단일 진실 원칙(SSOT)으로 인프라를 편리하게 운영할 수 있다는점에 해당 실습을 통해 많이 배우게 된 것 같습니다.

특히 ArgoCD는 Git 저장소에 위치한 Yaml 파일을 기준으로 ArgoCD가 자체적으로 싱크를 관리하는 점, 그동안 블로그로만 접하던 컨테이너 인사이트에 대한 내용을 경험할 수 있어서 더욱 재미있었던 한주가 된 것 같습니다.


📌 Reference

profile
안녕하세요! DevOps 엔지니어 이재찬입니다. 블로그에 대한 피드백은 언제나 환영합니다! 기술, 개발, 운영에 관한 다양한 주제로 함께 나누며, 더 나은 협업과 효율적인 개발 환경을 만드는 과정에 대해 인사이트를 나누고 싶습니다. 함께 여행하는 기분으로, 즐겁게 읽어주시면 감사하겠습니다! 🚀

0개의 댓글