[GitHub] CI/CD, Git Actions

πŸ’‘λΉŒλ“œμ™€ ν…ŒμŠ€νŠΈ, 배포에 ν™œμš©λ˜λŠ” CI/CD에 λŒ€ν•˜μ—¬ ν•™μŠ΅ ν›„ μ •λ¦¬ν•˜μ˜€μŠ΅λ‹ˆλ‹€.

 

CI/CD?

  • CI/CDλŠ” μ†Œν”„νŠΈμ›¨μ–΄ 개발 ν”„λ‘œμ„ΈμŠ€λ₯Ό μžλ™ν™”ν•˜κ³  효율적으둜 λ§Œλ“€κΈ° μœ„ν•œ 개발 κ΄€ν–‰μž…λ‹ˆλ‹€.
  • μ½”λ“œλ₯Ό μž‘μ€ λ‹¨μœ„λ‘œ 자주 λ³‘ν•©ν•˜κ³ , μžλ™ν™”λœ ν…ŒμŠ€νŠΈμ™€ 배포λ₯Ό 톡해 μ•ˆμ •μ μ΄κ³  μ‹ μ†ν•œ μ†Œν”„νŠΈμ›¨μ–΄ 릴리슀λ₯Ό κ°€λŠ₯ν•˜κ²Œ ν•˜λŠ” λͺ©ν‘œλ₯Ό 가지고 μžˆμŠ΅λ‹ˆλ‹€.

CI (Continuous Integration)

  • κ°œλ°œμžλ“€μ΄ 자주 μ½”λ“œλ₯Ό ν†΅ν•©ν•˜κ³  λ³€κ²½ 사항을 버전 관리 μ‹œμŠ€ν…œμ— λ³‘ν•©ν•˜λŠ” κ³Όμ •μž…λ‹ˆλ‹€.
  • CI νŒŒμ΄ν”„λΌμΈμ€ μ½”λ“œ λ³€κ²½ 사항이 병합될 λ•Œλ§ˆλ‹€ μžλ™μœΌλ‘œ λΉŒλ“œ, ν…ŒμŠ€νŠΈλ₯Ό μ‹€ν–‰ν•˜μ—¬ μ½”λ“œ ν’ˆμ§ˆμ„ 보μž₯ν•©λ‹ˆλ‹€.

CD (Continuous Delivery/Deployment)

  • Continuous DeliveryλŠ” CI 이후, κ²€μ¦λœ μ½”λ“œκ°€ μžλ™μœΌλ‘œ μ€€λΉ„λœ ν”„λ‘œλ•μ…˜ 배포 λ²„μ ΌμœΌλ‘œ 릴리슀될 수 있게 ν•˜λŠ” κ³Όμ •μž…λ‹ˆλ‹€.
    • μ΅œμ’… λ°°ν¬λŠ” μˆ˜λ™μœΌλ‘œ μ΄λ£¨μ–΄μ§ˆ 수 μžˆμŠ΅λ‹ˆλ‹€.
  • Continuous DeploymentλŠ” Continuous Delivery보닀 ν•œ 단계 더 λ‚˜μ•„κ°€μ„œ, ν…ŒμŠ€νŠΈλ₯Ό ν†΅κ³Όν•œ μ½”λ“œλ₯Ό μžλ™μœΌλ‘œ ν”„λ‘œλ•μ…˜ ν™˜κ²½μ— λ°°ν¬ν•˜λŠ” κ³Όμ •μž…λ‹ˆλ‹€.

ꡬ좕 도ꡬ

  • CI/CD νŒŒμ΄ν”„λΌμΈμ„ κ΅¬μΆ•ν•˜λŠ” λ„κ΅¬λ‘œ Jenkins, GitHub Actions, Bitrise, CircleCI, GitLab CI 등이 ν™œμš©λ©λ‹ˆλ‹€.
  • μ΄λŸ¬ν•œ 도ꡬ듀은 μ½”λ“œκ°€ 컀밋될 λ•Œλ§ˆλ‹€ λΉŒλ“œν•˜κ³  ν…ŒμŠ€νŠΈλ₯Ό μ‹€ν–‰ν•˜λ©°, 성곡적인 λΉŒλ“œ 후에 배포λ₯Ό μ§„ν–‰ν•©λ‹ˆλ‹€.

νŒŒμ΄ν”„λΌμΈ

CI/CD νŒŒμ΄ν”„λΌμΈ ꡬ좕을 μ•ˆλ“œλ‘œμ΄λ“œ μ•± 개발 ν™˜κ²½μ„ μ€‘μ‹¬μœΌλ‘œ μž‘μ„±ν•˜μ˜€μœΌλ©° λΉŒλ“œ, ν…ŒμŠ€νŠΈ, 배포 ν”„λ‘œμ„ΈμŠ€λ₯Ό μžλ™ν™”ν•˜λŠ” 것을 λͺ©ν‘œλ‘œ ν•˜μ˜€μŠ΅λ‹ˆλ‹€.

μ½”λ“œ ν‘Έμ‹œ 트리거

  • κ°œλ°œμžκ°€ Git μ €μž₯μ†Œμ— μ½”λ“œ ν‘Έμ‹œ λ˜λŠ” PR을 생성할 λ•Œλ§ˆλ‹€ νŒŒμ΄ν”„λΌμΈμ΄ μžλ™μœΌλ‘œ μ‹œμž‘λ©λ‹ˆλ‹€.

λΉŒλ“œ μžλ™ν™”

  • Gradle을 ν™œμš©ν•΄ μ•ˆλ“œλ‘œμ΄λ“œ ν”„λ‘œμ νŠΈλ₯Ό λΉŒλ“œν•©λ‹ˆλ‹€.
  • assembleDebug or asRelease와 같은 Gradle λͺ…λ Ήμ–΄λ₯Ό μ‚¬μš©ν•˜μ—¬ APK, AAB νŒŒμΌμ„ 생성할 수 μžˆμŠ΅λ‹ˆλ‹€.
./gradlew assembleDebug

ν…ŒμŠ€νŠΈ μžλ™ν™”

  • μœ λ‹› ν…ŒμŠ€νŠΈμ™€ UI ν…ŒμŠ€νŠΈλ₯Ό μžλ™μœΌλ‘œ μ‹€ν–‰ν•  수 μžˆμŠ΅λ‹ˆλ‹€.
  • Robolectric을 μ‚¬μš©ν•œ μœ λ‹› ν…ŒμŠ€νŠΈ λ˜λŠ” Espressoλ₯Ό μ‚¬μš©ν•œ UI ν…ŒμŠ€νŠΈκ°€ ν¬ν•¨λ©λ‹ˆλ‹€.
./gradlew testDebugUnitTest
./gradlew connectedAndroidTest

ν…ŒμŠ€νŠΈ 컀버리지 및 μ½”λ“œ ν’ˆμ§ˆ 검사

  • μ½”λ“œ 컀버리지 λ„κ΅¬λ‘œ JaCoCo와 같은 도ꡬλ₯Ό μ‚¬μš©ν•˜μ—¬ μ½”λ“œ 컀버리지λ₯Ό μΈ‘μ •ν•©λ‹ˆλ‹€.
  • μ½”λ“œ ν’ˆμ§ˆ 검사 λ„κ΅¬λ‘œ Lint, Detekt, Ktlintλ₯Ό μ‚¬μš©ν•  수 μžˆμŠ΅λ‹ˆλ‹€.
./gradlew lint
./gradlew detekt

APK/AAB 배포

  • Firebase App Distribution, Google Play Console, TestFairy 같은 ν”Œλž«νΌμ„ μ‚¬μš©ν•΄ 앱을 ν…ŒμŠ€ν„°μ—κ²Œ 배포할 수 μžˆμŠ΅λ‹ˆλ‹€.
  • 이 λ‹¨κ³„λŠ” λΉŒλ“œκ°€ μ„±κ³΅μ μœΌλ‘œ μ™„λ£Œλœ 후에 μžλ™μœΌλ‘œ μ‹€ν–‰λ˜κ²Œ ν•  수 μžˆμŠ΅λ‹ˆλ‹€.
./gradlew publishReleaseApk

CI/CD ꡬ좕

μ•ˆλ“œλ‘œμ΄λ“œμ—μ„œ CI/CD ꡬ좕을 톡해 개발자 μ½”λ“œ ν’ˆμ§ˆ μœ μ§€μ™€ ν…ŒμŠ€νŠΈ μžλ™ν™”λ‘œ μ‰½κ²Œ 앱을 배포할 수 μžˆμŠ΅λ‹ˆλ‹€. μžλ™ν™”λœ CI/CD νŒŒμ΄ν”„λΌμΈμ„ 톡해 개발과 배포 속도λ₯Ό 높이고 신뒰성을 확보할 수 μžˆμŠ΅λ‹ˆλ‹€.

ON

  • on은 이벀트 λ°œμƒμ— λŒ€ν•œ CI/CD 싀행을 지정할 수 μžˆμŠ΅λ‹ˆλ‹€.
  • master λΈŒλžœμΉ˜μ— push λ˜λŠ” PR μ΄λ²€νŠΈκ°€ λ°œμƒν•˜λ©΄ CI/CDλ₯Ό μ‹€ν–‰ν•˜λ„λ‘ μ§€μ •ν•©λ‹ˆλ‹€.
on:
  push:
    branches: [ "master" ]
  pull_request:
    branches: [ "master" ]

Jobs

  • JobsλŠ” μ‹€ν–‰ν•  μž‘μ—…λ“€μ„ λ‚˜μ—΄ν•©λ‹ˆλ‹€.
jobs:
  build:

runs-on

  • runs-on은 λΉŒλ“œ μž‘μ—…μ΄ 싀행될 ν™˜κ²½μ„ μ •μ˜ν•©λ‹ˆλ‹€.
  • μ΅œμ‹  λ²„μ „μ˜ Ubuntu ν™˜κ²½(Default)λ₯Ό μ§€μ •ν•˜μ˜€μŠ΅λ‹ˆλ‹€.
runs-on: ubuntu-latest

steps

  • stepsμ—λŠ” μž‘μ—…μ΄ 싀행될 μˆœμ„œλ₯Ό μ •μ˜ν•  수 μžˆμŠ΅λ‹ˆλ‹€.
  • μ‹€ν–‰ν•˜κ³  싢은 μž‘μ—…μ„ λ‚˜μ—΄ν•˜λ©°, Jobs λΈ”λŸ­ μ•ˆμ— μ„ μ–Έν•΄μ•Ό ν•©λ‹ˆλ‹€.
    steps:
    - name: Checkout code
      uses: actions/checkout@v2

    - name: Set up JDK 11
      uses: actions/setup-java@v1
      with:
        java-version: '11'

    - name: Cache Gradle packages
      uses: actions/cache@v2
      with:
        path: |
          ~/.gradle/caches
          ~/.gradle/wrapper
        key: ${{ runner.os }}-gradle-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }}
        restore-keys: |
          ${{ runner.os }}-gradle

    - name: Build with Gradle
      run: ./gradlew build

    - name: Run unit tests
      run: ./gradlew testDebugUnitTest

    - name: Run Android Lint
      run: ./gradlew lint

    - name: Assemble Debug APK
      run: ./gradlew assembleDebug

    - name: Upload APK
      uses: actions/upload-artifact@v2
      with:
        name: app-debug.apk
        path: app/build/outputs/apk/debug/app-debug.apk

μ°Έκ³ 

https://arc.net/l/quote/sustkkrv