DevOps에 관하여

BitBucket/ Jenkins / Docker / Harbor(Kubernetes) / ArgoCD / CI&CD/ TDD

Untitled

DevOps란

DevOps는 Dev(개발)와 Ops(운영)의 합성어

개발에서 운영 (plan → code → build → test → release → deploy → operate → monitor) 까지의 전반적인 영역을 아울러 통칭하는 말.

현재 내부망 DevOps 환경

  • 형상관리: SVN
  • 배포 : 패키지

아래는 외부망에 구축할 DevOps 환경임.

개요

BitBucket (코드)

→ Jenkins (Docker 이미지 빌드/배포)

→ Harbor (Docker 이미지 저장소)

→ ArgoCD (Docker 이미지 외부로 연결)

1. BitBucket

Untitled

Bitbucket 은 Atlassian 이 소유한 Git 기반 소스 코드 저장소 호스팅 서비스 

host 10.1.4.71 bitbucket.jinhaksa.net

접속할 때 URL (포트번호 : 7990) http://bitbucket.jinhaksa.net:7990/

****************************Login은 AD계정으로 하면 된다.****************************

위에 host 등록하고 사용

후에는 BitBucket Cloud 로 형상관리가 이전될 예정.

저장소

  • Repository : 가장 기본이 되는 소스 저장소 ex) consultingadmin-front : 입학상담앱 Front / consultingadmin-back : 입학상담앱 Back
  • Project : 리포지토리의 모음 ex) consultingadmin : 입학상담앱 Projcet

사용법

git 과 동일하다.

(참고) git 명령어

분류 명령어 내용 설명
<새로운 저장소="" 생성=""> $ git init .git 하위 디렉토리 생성(폴더를 만든 후, 그 안에서 명령 실행 => 새로운 git저장소 생성)
<저장소 복제/다운로드(clone)> $ git clone https:.. URL 기존 소스 코드 다운로드/복제
<추가 및 확정(commit)> $ git add -A 커밋에 파일의 변경 사항을 한번에 모두 포함
  $ git commit -m “커밋 메시지” 커밋 생성(실제 변경사항 확정)
$ git branch 브랜치 목록
  $ git branch <브랜치이름> 새 브랜치 생성 (local로 만듦)
  $ git checkout -b <브랜치이름> 브랜치 생성 & 이동
  $ git checkout master master branch로 되돌아 옴
  $ git branch -d <브랜치이름> 브랜치 삭제
  $ git push origin <브랜치이름> 만든 브랜치를 원격 서버에 전송
  $ git push -u < remote > <브랜치이름> 새 브랜치를 원격 저장소로 push
  $ git pull < remote > <브랜치이름> 원격에 저장된 git 프로젝트의 현재 상태를 다운받고 + 현재 위치한 브랜치로 병합
<변경 사항 발행(push)> $ git push origin master 변경사항 원격 서버에 업로드
  $ git push < remote > <브랜치이름> 커밋을 원격 서버에 업로드
  $ git push -u < remote > <브랜치이름> 커밋을 원격 서버에 업로드
  $ git remote add origin <등록된 원격="" 서버="" 주소=""> 클라우드 주소 등록 및 발행(git에게 새로운 원격 서버 주소 알림)
  $ git remote remove <등록된 클라우드="" 주소=""> 클라우드 주소 삭제
<갱신 및 병합(merge)> $ git pull 원격 저장소의 변경 내용이 현재 디렉토리에 가져와지고(fetch) 병합(merge)됨
  $ git merge <다른 브랜치이름=""> 현재 브랜치에 다른 브랜치의 수정사항 병합
  $ git add <파일명> 각 파일을 병합할 수 있음
  $ git diff <브랜치이름><다른 브랜치이름=""> 변경 내용 merge 전에 바뀐 내용을 비교할 수 있음
<태그tag 작업=""> $ git log 현재 위치한 브랜치 커밋 내용 확인 및 식별자 부여됨
<로컬 변경사항="" return="" 작업=""> $ git checkout – <파일명> 로컬의 변경 사항을 변경 전으로 되돌림
  $ git fetch origin 원격에 저장된 git프로젝트의 현 상태를 다운로드

※ Docker

Untitled

Docker란 ?

Application을 Packaging할 수 있는 Tool

예를들어 백엔드 웹서버 API 코드를 작성해서 이제 웹 서버에 올리려고 한다.

그러면, Node js, 도 필요하고, NPM 의 여러 패키지(Dependencies) 들도 필요할 것이다.

이 모든 환경을 묶어서 이미지로 만들어서 배포할 수 있도록 해주는 애가 Docker라고 생각하면 된다.

용어정리

  • Docker 이미지 : 위의 개발 환경들을 묶어둔 집합
  • Container : 이미지를 읽어와서 개발 환경들을 바탕으로 구동하게 되는 모듈

※ 이미지 : 붕어빵 틀/ 컨테이너 : 붕어빵과 같다고 생각하면 됨.

DockerFile

Docker 이미지 를 만들어주는 스크립트

  • 복사해야하는 파일 및 디렉토리
  • 개발에 필요한 패키지들 설치
  • 환경변수 설정
  • 실행 스크립트

예시코드)

# Base Node
FROM node:16 AS base

# Direct Setting
RUN mkdir /consulting-admin-server
WORKDIR /consulting-admin-server

# Package Copy
COPY package.json .
COPY .env.local .
COPY .env.development .

# Environment Variable Setting
ARG NODE_ENV
ENV NODE_ENV=${NODE_ENV}

# Dependencies
FROM base AS dependencies

# Node Packages Setup
RUN npm set progress=false && npm config set depth 0
RUN npm install

# Builder
FROM base AS builder
COPY --from=dependencies /consulting-admin-server/node_modules ./node_modules
COPY ./src ./src

# Expose PORT and define CMD
EXPOSE 3000
CMD ["sh", "-c", "npm run lego"]

위의 코드를 사용하여 consulting-admin-server 를 배포할 때 사용하는 이미지를 만들어준다.

2. Jenkins

Untitled

Jenkins란 소스 빌드 및 배포 할 수 있는 코드통합 Tool 이다.

Untitled

위의 그림과 같이 Git에 올라간 코드를 바탕으로 Docker로 이미지를 만들어 배포해주는 기능을 한다.

※ Jenkins는 외부망(개발서버용)과 내부망(운영서버용)이 나뉘어져 있다.

외부망 HOST, URL

host 10.1.4.48 jenkins.jinhakapply.com

접속 URL (포트번호 8080) http://jenkins.jinhakapply.com:8080/login?from=%2F

내부망 HOST, URL

host 172.20.7.118 jenkins.jinhakapply.com

접속 URL (포트번호 8080) jenkins.jinhakapply.com:8080

************************Login은 AD계정으로 하면 된다.************************

사용법

새로운 프로젝트를 만들어 세팅하는 방법을 아래와 같이 진행하여 주면 된다.

  1. 프로젝트 만들기
    1. 새로운 아이템 만들기

      슬라이드1-1.png

    2. 프로젝트 이름 / 프로젝트 타입 선택

      슬라이드2.PNG

  2. 프로젝트 구성
    1. General

      슬라이드3.PNG

    2. 소스코드 관리

      슬라이드4.PNG

    3. 빌드유발

      슬라이드5.PNG

    4. 빌드환경

      슬라이드6.PNG

      참고로 Dockerfile 을 불러와서 실행시키는 방식인데

      Dockerfile 은 위에 Git 저장소 최상단에 위치해야 한다.

    5. 빌드 & 배포

    슬라이드7.PNG

    전체적으로는 위와 같이 구성해주고 진행하면 된다.

    ## 3. Harbor

    Untitled

    이미지 저장소(Registry)

    Jenkins에서 빌드/배포 작업까지 진행이 되면 Harbor 에 Docker Image 가 저장된 것을 볼 수 있는데 다음과 같이 확인할 수 있다.

    Login은 AD 계정으로 하면 된다

    host 10.1.4.45 harbor.jinhaksa.net

    접근 URL (포트 : 30003) https://harbor.jinhaksa.net:30003/account/sign-in

    • Project

      슬라이드8.PNG

    • JobName

      슬라이드9.PNG

    ### 4. ArgoCD

    Untitled

    배포한 이미지를 외부와 연결하는 용도

    dockerbuild 라는 프로젝트에 YAML 파일이 있음

    http://bitbucket.jinhaksa.net:7990/scm/jat/dockerbuild.git

    YAML 파일로 외부로 연결할 때 필요한 설정값을 세팅한다.

    YAML파일의 종류는 대략 아래와 같다.

    • deploy : 도커 이미지 배포를 위함.
    • service : 이미지를 외부와 연결하기 위한 전초작업
    • ingress : 이미지 외부와 연결해줌

    각각 yaml 파일은 아래와 같은데, 대부분 이름만 변경해주면 되고

    주의해야할 점은 namespace 같은 경우는 수일팀장님이 ArgoCD 에 명령어로 추가해줘야 한다.

    (솔직히 YAML 파일 내부적으로 설정하는 방법을 자세히 알지는 못합니다..)

    consulting-admin-server-service.yaml

     apiVersion: v1
     kind: Service
     metadata:
       labels:
         app: consulting-admin-server-service
         app.kubernetes.io/instance: consulting-admin-server-deploy
       name: consulting-admin-server
       namespace: consulting
     spec:
       type: ClusterIP
       internalTrafficPolicy: Cluster
       ipFamilies:
       - IPv4
       ipFamilyPolicy: SingleStack
       ports:
       - protocol: TCP
         targetPort: 3000
         port: 3000
       selector:
         app: consulting-admin-server-service
    

    consulting-admin-server-deploy.yaml

     apiVersion: apps/v1
     kind: Deployment
     metadata:
       name: consulting-admin-server
       labels:
         app: consulting-admin-server-service
        
     spec:
       progressDeadlineSeconds: 300
       replicas: 1
       selector:
         matchLabels:
           app: consulting-admin-server-service
        
       template:
         metadata:
           labels:
             app: consulting-admin-server-service
        
         spec:
           containers:
             - name: consulting-admin-server-service-container
               image: harbor.jinhaksa.net:30003/k8s-apply/consulting-admin-server
               env:
                 - name: MY_NODE_NAME
                   valueFrom:
                     fieldRef:
                       fieldPath: spec.nodeName
               ports:
               - name: flask-port
                 containerPort: 3000
               imagePullPolicy: Always
           hostAliases:
    

    ingress-consulting.yaml

     apiVersion: networking.k8s.io/v1
     kind: Ingress
     metadata:
       name: ingress-consulting
       annotations:
         kubernetes.io/ingress.class: "nginx"
         nginx.ingress.kubernetes.io/proxy-body-size: 50m
     spec:
       rules:
       - host: consulting-service.jinhakapply.com
         http:
           paths:
           - path: /
             pathType: ImplementationSpecific
             backend:
               service:
                 name: consulting-backend
                 port:
                   number: 3001
    

    대충 갔다 쓰고, argoCD로 접속 (접근 권한 신청서를 써야 함)

    host 10.1.4.45 argocd.jinhaksa.net

    접근 URL(포트 : 30987) https://argocd.jinhaksa.net:30987/login

    Untitled

    1. Repository 등록

    Untitled

    Untitled

    1. App 만들기

    Untitled

    Untitled

  3. Sync 맞춰주기

Untitled

  1. Ingress-App 만들어주기 → 동일하게 Sync 맞춰줌.

Untitled

5. CI&CD (총괄)

Untitled

  1. Plan : JIRA (추후 BitBucket Cloud 로 가면 사용할 예정)
  2. Code : BitBucket (형상관리)
  3. Build : Jenkins를 통한 Docker Build
  4. Release : Jenkins를 통해 이미지 릴리즈
  5. Deploy : ArgoCD 통해 배포

CI & CD 란? (Continously Integration & Continously Deploy)

위의 모든 과정(빌드, 테스트, 배포)를 그냥 BitBucket에 커밋하면 자동으로 이뤄지게 하겠다.

그러려면 정말 필요한게 TEST Module!

코드를 배포하면 TEST Module이 자동으로 돌면서 추가된 소스가 테스트를 통과했는지 알려주며

테스트를 통과하면 배포되고, 통과하지 못하면 배포 되지 못하도록 막는 방식

6. TDD (Test Driven Development)

테스트 주도 개발

개발하기 전에 테스트 코드를 먼저 만들어 두고, 개발을 시작한다.

Puppeteer

Untitled

E2E 테스트 모듈을 만들어 진행해보려 하고 있음.