Home 안드로이드 자동배포(CI&CD) 구현 with GithubAction, AWS S3, Slack
Post
Cancel

안드로이드 자동배포(CI&CD) 구현 with GithubAction, AWS S3, Slack

목표

github에 새로운 release가 생겼을 때 signed apk(release)를 생성하여 AWS S3에 업로드하고 관련 메세지를 slack에 전송한다.

해결하고자하는 것

  • 기존에도 s3에 debug apk를 업로드하게 구현해뒀으나, 실제 배포환경과 동일한 테스트를 위해 signing apk 배포 필요
    • post signing
  • 고정 URL의 S3에 업로드하는방식은 테스트 버전 파악이 쉽지않다.
    • version name with release 적용.
  • 새로운 버전이 release 되었을때 notify
    • Slack
  • APK 설치가 쉽지않다.
    • QR code & Action button

Workflow 작성

1. 환경 변수 설정

1
2
3
4
5
6
7
8
9
10
- name: Set vars
  id: vars
  run: |
    IFS='/'
    TAG="${GITHUB_REF#refs/*/}"
    read -a strarr <<< "$TAG"
    echo ::set-output name=tag::$TAG
    echo ::set-output name=platform::${strarr[0]}
    echo ::set-output name=version::${strarr[1]}
    echo ::set-output name=filename::**[업로드할 파일이름]**-${strarr[1]}.apk

github action에서 사용할 변수들을 미리 설정해주는 방식으로 작업.

TAG에 release tag값이 지정되며 이를 활용하여 필요한 변수들 저장

2. Signing APK

1
2
3
4
5
6
7
8
9
- name: Signing APK
  id: sign_app
  uses: r0adkll/sign-android-release@v1
  with:
    releaseDirectory: androidApp/build/outputs/apk/release
    signingKeyBase64: $
    alias: $
    keyStorePassword: $
    keyPassword: $

keystore 자체를 repository에 넣어두고 signing을 할 수 있으나 보안상 apk build 후 따로 signing을 진행하는 식으로 작업 assembleRelease시 signing을 진행하는 경우 생략

전체 Workflow

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
66
67
68
69
70
71
72
73
74
75
76
77
78
79
name: Android Deploy

on:
  workflow_dispatch:
  push:
    tags: 'aos/*'

env:
  GITHUB_URL: **[~~~]**
  AWS_REGION: ap-northeast-2

jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v3
      - name: Set vars
        id: vars
        run: |
          IFS='/'
          TAG="${GITHUB_REF#refs/*/}"
          read -a strarr <<< "$TAG"
          SIZE=${#strarr[*]}
          echo $TAG
          echo ::set-output name=tag::$TAG
          echo ::set-output name=platform::${strarr[0]}
          echo ::set-output name=version::${strarr[1]}
          echo ::set-output name=filename::**[~~~]**-${strarr[1]}.apk
      - name: set up JDK 11
        uses: actions/setup-java@v3
        with:
          java-version: '11'
          distribution: 'temurin'
          cache: gradle

      - name: Grant execute permission for gradlew
        run: chmod +x ./gradlew

      - name: Build Release APK with Gradle
        run: ./gradlew :androidApp:assembleRelease

      - name: Signing APK
        id: sign_app
        uses: r0adkll/sign-android-release@v1
        with:
          releaseDirectory: androidApp/build/outputs/apk/release
          signingKeyBase64: $
          alias: $
          keyStorePassword: $
          keyPassword: $

      - name: Rename apk
        run: mv $ $

      - name: Upload apk to s3
        id: upload
        uses: hkusu/s3-upload-action@v2
        with:
          aws-access-key-id: $
          aws-secret-access-key: $
          aws-region: $
          aws-bucket: $
          file-path: $
          bucket-root: '/'
          destination-dir: 'android'
          output-file-url: 'true'
          output-qr-url: 'true'
          qr-width: 500
          public: 'true'

      - name: Notify slack
        env:
          SLACK_BOT_TOKEN: $
          S3_URL: $
          QR_URL: $
          CHANGE_URL: $releases/tag/$
        uses: pullreminders/slack-action@master
        with:
          args: '{\"channel\": ~~~'

Slack

slack message

Block kit을 사용하여 원하는 message payload를 구현하여 전달

References

https://github.com/r0adkll/sign-android-release

https://app.slack.com/block-kit-builder

This post is licensed under CC BY 4.0 by the author.

AWS: Typescript + serverless aws lambda 배포

Spring: Mapstruct SubclassMapping 사용법