포스트

[GitHub 100일 챌린지] Day 87 - 캐시와 Artifacts 활용

[GitHub 100일 챌린지] Day 87 - 캐시와 Artifacts 활용

100일 챌린지 Day 87 - 캐시와 Artifacts로 Workflow 속도를 향상시킵니다.

배울 내용

  1. 캐시로 빌드 속도 향상
  2. Artifacts로 파일 저장
  3. 최적화 전략

캐시 (Cache)

개념

반복적으로 다운로드하는 파일을 저장

1
2
3
4
5
6
7
8
9
캐시 대상:
- npm/yarn/pnpm 패키지
- pip/poetry 패키지
- Maven/Gradle 의존성
- 빌드 결과물

효과:
Before: npm install 2분
After: npm install 10초 (캐시 Hit 시)

기본 캐시 사용

actions/cache

1
2
3
4
5
6
7
8
- uses: actions/cache@v3
  with:
    path: |
      ~/.npm
      node_modules
    key: ${{ runner.os }}-node-${{ hashFiles('**/package-lock.json') }}
    restore-keys: |
      ${{ runner.os }}-node-

파라미터:

1
2
3
- path: 캐시할 디렉토리
- key: 캐시 키 (고유 식별자)
- restore-keys: 대체 키 (Fallback)

캐시 키 전략

1
2
3
4
5
6
7
8
# 패키지 변경 시만 새로 설치
key: ${{ runner.os }}-npm-${{ hashFiles('**/package-lock.json') }}

# OS + Node 버전 포함
key: ${{ runner.os }}-node-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}

# 날짜 기반 (주간 갱신)
key: ${{ runner.os }}-${{ hashFiles('**/package-lock.json') }}-${{ github.run_number }}

언어별 캐시 설정

Node.js

1
2
3
4
5
6
7
8
9
10
- uses: actions/setup-node@v4
  with:
    node-version: '20'
    cache: 'npm'  # 자동 캐시!

# 또는 수동
- uses: actions/cache@v3
  with:
    path: ~/.npm
    key: ${{ runner.os }}-node-${{ hashFiles('**/package-lock.json') }}

Python

1
2
3
4
5
6
7
8
9
10
- uses: actions/setup-python@v4
  with:
    python-version: '3.11'
    cache: 'pip'  # 자동 캐시!

# 또는 수동
- uses: actions/cache@v3
  with:
    path: ~/.cache/pip
    key: ${{ runner.os }}-pip-${{ hashFiles('**/requirements.txt') }}

Gradle

1
2
3
4
5
6
- uses: actions/cache@v3
  with:
    path: |
      ~/.gradle/caches
      ~/.gradle/wrapper
    key: ${{ runner.os }}-gradle-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }}

Artifacts

개념

Workflow에서 생성한 파일을 저장/공유

1
2
3
4
5
6
7
8
9
10
Artifacts 용도:
- 빌드 결과물 저장
- 테스트 리포트 보관
- Job 간 파일 전달
- 디버깅용 로그 저장

보관 기간:
- 기본 90일 (설정 가능)
- Private repo: 최대 400일
- Public repo: 최대 90일

Artifacts 업로드

actions/upload-artifact

1
2
3
4
5
6
7
8
- name: 빌드
  run: npm run build

- name: Artifacts 업로드
  uses: actions/upload-artifact@v3
  with:
    name: build-files
    path: dist/

여러 경로:

1
2
3
4
5
6
7
- uses: actions/upload-artifact@v3
  with:
    name: my-artifacts
    path: |
      dist/
      reports/
      *.log

제외 패턴:

1
2
3
4
5
6
- uses: actions/upload-artifact@v3
  with:
    name: build
    path: |
      dist/
      !dist/**/*.map

Artifacts 다운로드

같은 Workflow 내

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - run: npm run build
      
      - uses: actions/upload-artifact@v3
        with:
          name: dist
          path: dist/
  
  test:
    needs: build
    runs-on: ubuntu-latest
    steps:
      - uses: actions/download-artifact@v3
        with:
          name: dist
          path: dist/
      
      - run: npm run test:e2e

GitHub UI에서

1
Actions 탭 → Workflow 실행 → Artifacts 섹션 → 다운로드

실전 예제

빌드 + 테스트 + 배포

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
name: Build and Deploy

on: push

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      
      # 캐시로 속도 향상
      - uses: actions/setup-node@v4
        with:
          node-version: '20'
          cache: 'npm'
      
      - run: npm ci
      - run: npm run build
      
      # 빌드 결과 저장
      - uses: actions/upload-artifact@v3
        with:
          name: dist
          path: dist/
          retention-days: 7
  
  test:
    needs: build
    runs-on: ubuntu-latest
    steps:
      # 빌드 결과 가져오기
      - uses: actions/download-artifact@v3
        with:
          name: dist
          path: dist/
      
      - uses: actions/setup-node@v4
        with:
          node-version: '20'
          cache: 'npm'
      
      - run: npm ci
      - run: npm test
      
      # 테스트 리포트 저장
      - uses: actions/upload-artifact@v3
        if: always()
        with:
          name: test-report
          path: coverage/
  
  deploy:
    needs: [build, test]
    runs-on: ubuntu-latest
    if: github.ref == 'refs/heads/main'
    steps:
      - uses: actions/download-artifact@v3
        with:
          name: dist
          path: dist/
      
      - name: 배포
        run: |
          # dist/ 디렉토리를 서버에 배포
          echo "배포 중..."

캐시 최적화 전략

1. 레이어드 캐시

1
2
3
4
5
6
7
8
9
- uses: actions/cache@v3
  with:
    path: |
      ~/.npm
      node_modules
    key: ${{ runner.os }}-npm-${{ hashFiles('**/package-lock.json') }}
    restore-keys: |
      ${{ runner.os }}-npm-
      ${{ runner.os }}-

동작:

1
2
3
1. 정확한 키 찾기
2. 없으면 restore-keys 순서대로 시도
3. 부분 캐시라도 재사용

2. 선택적 캐시

1
2
3
4
5
6
7
8
9
10
11
12
- uses: dorny/paths-filter@v2
  id: filter
  with:
    filters: |
      deps:
        - 'package-lock.json'

- uses: actions/cache@v3
  if: steps.filter.outputs.deps == 'true'
  with:
    path: ~/.npm
    key: ${{ hashFiles('**/package-lock.json') }}

3. 빌드 캐시

1
2
3
4
5
6
- uses: actions/cache@v3
  with:
    path: .next/cache
    key: ${{ runner.os }}-nextjs-${{ hashFiles('**/package-lock.json') }}-${{ hashFiles('**.[jt]s', '**.[jt]sx') }}
    restore-keys: |
      ${{ runner.os }}-nextjs-${{ hashFiles('**/package-lock.json') }}-

캐시 관리

캐시 크기 제한

1
2
3
4
제한:
- 저장소당 최대 10GB
- 7일간 미사용 시 자동 삭제
- 초과 시 오래된 캐시부터 삭제

캐시 삭제

1
2
3
4
5
6
7
GitHub → Actions → Caches → 개별 삭제

또는 API:
gh api \
  repos/OWNER/REPO/actions/caches \
  --jq '.actions_caches[] | .id' \
  | xargs -I {} gh api --method DELETE repos/OWNER/REPO/actions/caches/{}

Artifacts vs Cache

1
2
3
4
5
6
7
8
9
10
11
Cache:
- 의존성, 빌드 도구
- 속도 향상 목적
- 자동 삭제
- 여러 Workflow 공유

Artifacts:
- 빌드 결과, 리포트
- 저장/공유 목적
- 수동 관리
- 특정 Workflow만

정리

완료 체크:

  • 캐시 설정으로 속도 향상
  • Artifacts로 파일 저장
  • Job 간 파일 전달

핵심 요약:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
캐시:
- actions/cache@v3
- path, key, restore-keys
- 의존성 설치 속도 향상
- setup-* actions 자동 캐시

Artifacts:
- upload-artifact@v3
- download-artifact@v3
- 빌드 결과, 리포트 저장
- Job 간 파일 전달

최적화:
- 레이어드 캐시
- 선택적 캐시
- 적절한 보관 기간

다음: Day 88 - Matrix 전략 심화 →


← Day 87 | 전체 커리큘럼 | Day 88 →

이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.