okaryo.log

Flutterで作ったAndroidアプリをGitHubActionsを使ってAppDistributionに自動デプロイする | okaryo.log

Flutterで作ったAndroidアプリをGitHubActionsを使ってAppDistributionに自動デプロイする

    #Flutter#Firebase#AppDistribution#Android#GitHubActions#GitHub#CI/CD

はじめに

最近subskunというAndroidアプリをリリースした。

機能の追加や修正時に実機でデバッグをするのにAppDistributionを使っているが、これをdevelopブランチにマージがあったタイミングで自動でAppDistributionに配信したいと考えた。

そこで、GitHubActionsを使ってワークフローを組んでみることにした。

組んだワークフロー

ワークフローの全体は以下となった。開発用のブランチであるdevelopブランチへのpushをトリガーにワークフローが走るようにしている。

name: Deploy to App Distribution

on:
  push:
    branches:
      - develop

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v3
      - name: Set up Flutter
        uses: subosito/flutter-action@v2
        with:
          flutter-version: '3.0.1'
          channel: 'stable'
          cache: true
      - name: Run gen-l10n
        run: flutter gen-l10n
      - name: Build aab
        run: |
          echo '${{ secrets.GOOGLE_SERVICES_JSON }}' > android/app/google-services.json
          echo '${{ secrets.ANDROID_JKS_BASE64 }}' | base64 -d > android/app/release.keystore
          export KEY_ALIAS='${{ secrets.KEY_ALIAS }}'
          export KEY_PASSWORD='${{ secrets.KEY_PASSWORD }}'
          export KEYSTORE_PASSWORD='${{ secrets.KEYSTORE_PASSWORD }}'
          flutter build appbundle --release --flavor production --dart-define=FLAVOR=production --build-number='${{ secrets.ANDROID_BUILD_NUMBER }}' --obfuscate --split-debug-info=obfuscate/android
      - name: Upload artifact to Firebase App Distribution
        uses: wzieba/Firebase-Distribution-Github-Action@v1
        with:
          appId: ${{secrets.FIREBASE_APP_ID}}
          token: ${{secrets.FIREBASE_TOKEN}}
          groups: testers
          file: build/app/outputs/bundle/productionRelease/app-production-release.aab

各ステップを解説

actions/checkout@v3

レポジトリをチェックアウトしているだけなので割愛。

Set up Flutter

Flutterの環境構築をしている。subosito/flutter-actionはそのためによく使われるActionだ。

ちなみにsubskunではFlutter3を使っている。

Run gen-l10n

subskunでは多言語対応しているので、以下のコマンドを走らせることでLocalization用のコードをビルドの前に生成しておく必要がある。

flutter gen-l10n

Build aab

ここでやっとビルドを走らせるが、まずはその下準備をする。

subskunではFirebaseを使っているので設定ファイルをGitHub ActionsのSecretsから生成している。

mkdir android/app/src/productionRelease
echo '${{ secrets.GOOGLE_SERVICES_JSON }}' > android/app/src/productionRelease/google-services.json

以下ではAndroidアプリを署名するためのパスワードなどの準備をしている。jksファイルはバイナリなので、base64したものをGitHub ActionsのSecretsに設定し、ここでデコードしている。

echo '${{ secrets.ANDROID_JKS_BASE64 }}' | base64 -d > android/app/release.keystore
export KEY_ALIAS='${{ secrets.KEY_ALIAS }}'
export KEY_PASSWORD='${{ secrets.KEY_PASSWORD }}'
export KEYSTORE_PASSWORD='${{ secrets.KEYSTORE_PASSWORD }}'

ちなみに上記からも分かる通り、パスワードなどは環境変数から読み取る形式にしているのでandroid/app/build.gradlesigningConfigsはこうなっている。

signingConfigs {
    release {
        keyAlias System.getenv('KEY_ALIAS')
        keyPassword System.getenv('KEY_PASSWORD')
        storeFile file('release.keystore')
        storePassword System.getenv('KEYSTORE_PASSWORD')
    }
}

次にやっとビルドだ。

実際にリリースされるものと同じ環境で動作確認したいのでもちろんリリースビルド。dart-defineを使って環境の出し分けをおこない、--obfuscateではコードの難読化をおこなっている。

ビルド番号もSecretsから与えるようにしているが、アプリのバージョン番号から自動でビルド番号を読み取る方式にしようかどうか考え中。個人的にはiOSも含めてビルド番号はコードに依存させずに外部から与えるようにしたいと思っているが、もっと手軽にできるのであればそうしたいとも思っている。

flutter build appbundle --release --flavor production --dart-define=FLAVOR=production --build-number='${{ secrets.ANDROID_BUILD_NUMBER }}' --obfuscate --split-debug-info=obfuscate/android

2022-10-05追記

ビルド番号についてだが、コミット数から設定する方法を教えていただいた。以下の記事で紹介しているのでよければ読んでいただきたい。

FlutterアプリをGitHubActionsでビルドする際にコミット数をビルド番号として設定する

追記おわり

Upload artifact to Firebase App Distribution

最後にAppDistributionへのアップロードだ。

先ほどのビルドによってaabファイルが以下のパスへ生成された。これをアップロードする。

build/app/outputs/bundle/productionRelease/app-production-release.aab

それにはwzieba/Firebase-Distribution-Github-Action@v1というActionを利用させてもらった。

FirebaseのappIdtoken(またはserviceCredentialsFile)を与えてやるだけで簡単にアップロードすることができる。

ちなみにappIdはFirebaseのプロジェクトIDではなく、Firebaseプロジェクト内のAndroidアプリのIDなので注意。また、tokenfirebase login:ciコマンドで取得することができる。

firebaseコマンドを使うにはFirebase CLIをインストールする必要がある。詳しくは公式ドキュメントを参照されたい。

おわり

AppDistributionへのアップロードは作成済みのActionを使うことができたので簡単に実現することができた。

個人開発においてはめんどくさいをどれだけ少なくできるかがモチベーションを維持する上でも重要だと思っており、こういったCI/CDの構築は早めにやっておきたかったので大変助かった。


関連記事
最新記事
プロモーション

This site uses Google Analytics.