CI/CD란?
- CI : Continuous Integration (지속적 통합)
- CD : Continuous Deployment (지속적 배포) 또는 지속적인 서비스 제공(Continuous Delivery)
CI는 빌드/테스트 자동화 과정이다.
- 개발자를 위한 자동화 프로세스인 지속적인 통합(Continuous Integration)을 의미한다.
- CI를 성공적으로 구현할 경우 애플리케이션에 대한 새로운 코드 변경 사항이 정기적으로 빌드 및 테스트되서 공유 레파지토리에 통합되므로 여러 명의 개발자가 동시에 애프리케이션 개발과 관련된 코드 작업을 할 경우 충돌하는 문제를 해결할 수 있다.
- 요약하자면 code 작성 - Build - Test를 짧은 주기로 자동화 하는것
CD는 배포 자동화 과정이다.
- 애플리케이션에 적용한 변경 사항이 버그 테스트를 거쳐 리포지토리에 업로드 되는 것을 뜻한다.
- Continuous Delivery와 Continuous Deployment는 같은 의미로 쓰이기도 하지만 딱 하나의 차이가 있다.
- 실제 개발에선 개발환경과 운영환경을 구별해서 개발한다. 개발 환경에서는 Delivery와 Deployment 모두 자동화를 한다.
- 하지만 운영환경에선 Delivery는 마지막에 개발자가 수동으로 해줘야 하는 부분을 남겨놓고 Deployment는 운영환경에서도 자동화를 한다.
학습 계기
CI/CD의 핵심은 가능한 작은 단위로 빠르고, 자주 코드를 병합하고, 사용자에게 서비스를 제공하는 것, 그리고 이 과정을 자동화하는 것이다. 이런 특징들을 통해 더 적은 버그와 오류를 가지며, 새로운 기능을 고객에게 더 빨리 출시하여 경쟁 우위를 확보할 수 있으며, 빌드, 테스트, 배포와 같이 반복되는 지루한 과정을 개발자가 직접하지 않고 자동화 함으로써 개발자가 좀 더 핵심적인 역할에 집중할 수 있게 해준다. 이러한 장점으로 많은 기업에서 CI/CD를 사용하여 있으며, 경쟁력을 강화하기 위해 경험해보기로 했다.
가장 많이 쓰이는 도구는 Jenkins인데 환경 호환성을 위해 도커 이미지에서 실행해야 한다는 점과, 서버 설치 필요 등의 다양한 설정이 있기 때문에 간단하게 GitHub에서 제공하는 완전 관리형 서비스인 Git Actions를 사용해보았습니다.
Jenkins vs Git Actions
Jenkins | GitHub Actions |
서버 설치 필요 | 클라우드가 있으므로, 별도 설치 필요없음 |
작업 또는 작업이 동기화되어 제품을 시장에 배포하는 데 더 많은 시간이 소요 | 비동기 CI / CD 달성 |
계정 및 트리거를 기반으로하며 github 이벤트를 준수하지 않는 빌드를 중심으로합니다. |
모든 github 이벤트에 대한 작업을 제공하고 다양한 언어와 프레임 워크를 지원합니다. |
환경 호환성을 위해 도커 이미지에서 실행해야 함 | 모든 환경과 호환 |
캐싱 메커니즘을 지원하기 위해 플러그인을 사용할 수 있습니다. | 캐싱이 필요한 경우 자체 캐싱 메커니즘을 작성해야합니다. |
공유 할 수있는 능력이 없습니다. | github 마켓 플레이스를 통해 공유 가능 |
전세계많은 사람들이 이용하여 문서가 다양 | 젠킨스에 비해 문서가 없음 |
페이스북, 넥플릭스, 쿠팡, 카페24, 11번가 등... | 업스테이지 AI, Be pro 회사 등... |
1. react 프로젝트 생성 및 firebase hosing사용
# 프로젝트 세팅
npx create-react-app '프로젝트 이름'
# firebase hosting 사용하기
yarn add global firebase-tools
firebase login
처음부터 오류가 발생했는데.. 해당 오류를 아래와 같이 해결했다
✔ [오류 해결] firebase login, command not found 오류
해당 오류가 발생해서 해결하는데 2시간 정도 소요됐는데 해결방법 URL을 참고하여 해결하였다
환경 변수도 추가해보고 했는데도 안돼서 힘들었는데, node를 지우고 다시 설치하니 됐다!
2. Firebase
Firebase 프로젝트 생성
- 저는 yerim-portpolio라는 이름으로 프로젝트를 생성했습니다
- Hosting > 고급에서 사이트 이름 설정
프로젝트 firebase.json 생성
{
"database": {
"rules": "y"
},
"hosting": {
"site": "yerm-react-diary",
"public": "build",
"ignore": [
"firebase.json",
"**/.*",
"**/node_modules/**"
],
"rewrites": [
{
"source": "**",
"destination": "/index.html"
}
]
}
}
firebase init 설정
# vscode
firebase init
설정을 확인하실 분은 아래를 참고해주세요
You're about to initialize a Firebase project in this directory:
D:\react포트폴리오\portfolio
Before we get started, keep in mind:
* You are initializing within an existing Firebase project directory
? Are you ready to proceed? Yes
? Which Firebase features do you want to set up for this directory? Press Space to
select features, then Enter to confirm your choices. Hosting: Set up GitHub Action
deploys
=== Project Setup
First, let's associate this project directory with a Firebase project.
You can create multiple project aliases by running firebase use --add,
but for now we'll just set up a default project.
i Using project yerim-portpolio (yerim-portfolio)
=== Hosting:github Setup
i Detected a .git folder at D:\react포트폴리오\portfolio
i Authorizing with GitHub to upload your service account to a GitHub repository's
secrets store.
Visit this URL on this device to log in:
https://github.com/login/oauth/authorize?client_id=89cf50f02ac6aaed3484&state=95192172&redirect_uri=http%3A%2F%2Flocalhost%3A9005&scope=read%3Auser%20repo%20public_repo
Waiting for authentication...
+ Success! Logged into GitHub as yeafla530
? For which GitHub repository would you like to set up a GitHub workflow? (format:
user/repository) yeafla530/portfolio
+ Created service account github-action-671092702 with Firebase Hosting admin permissions.
+ Uploaded service account JSON to GitHub as secret FIREBASE_SERVICE_ACCOUNT_YERIM_PORTPOLIO.
i You can manage your secrets athttps://github.com/yeafla530/portfolio/settings/secrets.
? Set up the workflow to run a build script before every deploy? Yes
? What script should be run before every deploy? (npm ci && npm run build) npm ci && npm run build
+ Created workflow file D:\react포트폴리오\portfolio\.github/workflows/firebase-hosting-pull-request.yml
? Set up automatic deployment to your site's live channel when a PR is merged? Yes
? What is the name of the GitHub branch associated with your site's live channel?
master
+ Created workflow file D:\react포트폴리오\portfolio\.github/workflows/firebase-hosting-merge.yml
i Action required: Visit this URL to revoke authorization for the Firebase CLI GitHub OAuth App:
https://github.com/settings/connections/applications/89cf50f02ac6aaed3484
i Action required: Push any new workflow file(s) to your repo
i Writing configuration info to firebase.json...
i Writing project information to .firebaserc...
+ Firebase initialization complete!
3. github
push 해주기
git push origin master
github repository의 actions에 들어가면 workflow가 추가된 것을 볼 수 있다
4. CI/CD 작동 확인하기
기존 소스코드를 수정하고 pull request(검토후 병합 요청)를 진행합니다.
저는 master branch로 먼저 push했는데 develop branch를 새로 생성 후 이동하여 test.txt를 추가했습니다.
오류 발생
하지만 쉽지 않았고,,
계속해서
npm ERR! `npm ci` can only install packages when your package.json and package-lock.json or npm-shrinkwrap.json are in sync. Please update your lock file with `npm install` before continuing.
라는 에러가 발생했다!!
이를 해결하기 위해서 아래와 같이 문제를 해결했다.
해결방법
찾다보니 문제의 원인은 package.json과 package-lock.json이 호환되지 않는 문제가 발생한 것이었고, 아래 코드를 통해 호환되도록 했다! 아무래도 맨 처음에 react project의 이름을 변경하면서 package.json과 package-lock.json에 있는 프로젝트 명을 변경하면서 문제가 있었던것 같다
npm install --package-lock-only
workflow 준비
프로젝트 안에 .github/workflow/ci.yml 파일 생성 후 아래 코드를 넣어주었다
진행시 어떤 과정으로 workflow를 진행할지 정의해주는 파일이다
# .github/workflow/ci.yml
name: Our CI
on: push
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- run: npm ci
- run: npm test
- run: npm run build
해당 파일 생성 후 npm ci 를 작동시켜 workflows폴더안에 파일이 생성되는걸 확인한다
firebase-hosting-merge.yml
# firebase-hosting-merge.yml
name: Deploy to Firebase Hosting on merge
'on':
push:
branches:
- 'y'
jobs:
build_and_deploy:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- run: npm ci && npm run build
- uses: FirebaseExtended/action-hosting-deploy@v0
with:
repoToken: '${{ secrets.GITHUB_TOKEN }}'
firebaseServiceAccount: '${{ secrets.FIREBASE_SERVICE_ACCOUNT_YERIM_PORTPOLIO }}'
channelId: live
projectId: yerim-portpolio
firebase-hosting-pull-request.yml
# firebase-hosting-pull-request.yml
name: Deploy to Firebase Hosting on PR
'on': pull_request
jobs:
build_and_preview:
if: '${{ github.event.pull_request.head.repo.full_name == github.repository }}'
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- run: npm ci && npm run build
- uses: FirebaseExtended/action-hosting-deploy@v0
with:
repoToken: '${{ secrets.GITHUB_TOKEN }}'
firebaseServiceAccount: '${{ secrets.FIREBASE_SERVICE_ACCOUNT_YERIM_PORTPOLIO }}'
projectId: yerim-portpolio
이렇게 자동으로 build 되도록 해주었고, 배포까지 진행하는 과정에서 에러가 나서 배포 글은 에러가 해결된 이후에 작성하려한다 언제가 될지,,, 최대한 빠르게 작성해보겠습니다..!
참조
- https://choseongho93.tistory.com/295
- https://velog.io/@youngerjesus/Github-Action%EC%9D%84-%EC%9D%B4%EC%9A%A9%ED%95%9C-CICD-%EA%B0%9C%EB%B0%9C-%EC%A3%BC%EA%B8%B0-%EC%9E%90%EB%8F%99%ED%99%94
- https://devpluto.tistory.com/entry/Firebase-Firebase-hosting%EC%9C%BC%EB%A1%9C-nextjs-%EB%B0%B0%ED%8F%AC-%EC%9E%90%EB%8F%99%ED%99%94%ED%95%98%EA%B8%B0
- https://velog.io/@alvin_you/Setting-up-Github-Action-and-Firebase-Hostinghttps://velog.io/@chaerin00/FirebaseGitbub-Actions%EB%A5%BC-%ED%99%9C%EC%9A%A9%ED%95%9C-CICD-%EA%B5%AC%EC%B6%95
- https://velog.io/@chaerin00/FirebaseGitbub-Actions%EB%A5%BC-%ED%99%9C%EC%9A%A9%ED%95%9C-CICD-%EA%B5%AC%EC%B6%95
- https://velog.io/@2ast/Github-Github-actions%EC%97%90%EC%84%9C-Secrets%EB%A1%9C-%ED%99%98%EA%B2%BD%EB%B3%80%EC%88%98-%EA%B4%80%EB%A6%AC%ED%95%98%EA%B8%B0
- https://www.youtube.com/watch?v=P0x0LmiknJc