こんにちは。
アプリ開発において、テスト配信の自動化は開発スピードを上げるために非常に重要です。
今回は、「mainブランチにプッシュしたら、自動でiOSアプリをビルドしてTestFlightに配信する」仕組みについて、備忘録も兼ねてまとめたいと思います。
ネイティブ(Swift)やReact Nativeでも応用可能ですが、今回はFlutterプロジェクトを例に、便利な codemagic-cli-tools を使ったGitHub Actionsのワークフローを紹介します。
全体の流れ
- App Store Connect APIキーの準備
- 証明書・プロビジョニングプロファイルの用意
- GitHub Actions ワークフローの設定
fastlaneを使う方法もメジャーですが、今回は codemagic-cli-tools (App Store Connect CLI) を使うことで、シンプルに証明書の取得からTestFlightへのアップロードまでを完結させます。
1. 事前準備(App Store Connect APIキー等)
GitHub ActionsからApp Store Connectにアクセスするために、以下の情報を取得し、GitHubリポジトリの Secrets に登録しておく必要があります。
APP_STORE_CONNECT_ISSUER_IDAPP_STORE_CONNECT_KEY_IDENTIFIERAPP_STORE_CONNECT_PRIVATE_KEYAPP_STORE_APPLE_ID(アプリごとのApple ID)APP_STORE_BUNDLE_ID_EFFECTIVE(アプリのBundle ID)
2. GitHub Actions ワークフローの設定
リポジトリ内に .github/workflows/deploy-testflight.yml などのファイルを作成し、以下の内容を記述します。
name: Deploy to TestFlight
on:
push:
branches:
- main
jobs:
deploy-ios:
name: Build & Deploy iOS to TestFlight
runs-on: macos-latest
env:
APP_STORE_CONNECT_ISSUER_ID: ${{ secrets.APP_STORE_CONNECT_ISSUER_ID }}
APP_STORE_CONNECT_KEY_IDENTIFIER: ${{ secrets.APP_STORE_CONNECT_KEY_IDENTIFIER }}
APP_STORE_CONNECT_PRIVATE_KEY: ${{ secrets.APP_STORE_CONNECT_PRIVATE_KEY }}
APP_STORE_APPLE_ID: ${{ secrets.APP_STORE_APPLE_ID }}
APP_STORE_BUNDLE_ID_EFFECTIVE: ${{ secrets.APP_STORE_BUNDLE_ID_EFFECTIVE }}
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Setup Flutter
uses: subosito/flutter-action@v2
with:
channel: 'stable'
- name: Install dependencies
run: flutter pub get
- name: Install Codemagic CLI tools
run: pip install codemagic-cli-tools
- name: Initialize keychain
run: keychain initialize
- name: Fetch signing files from App Store Connect
run: |
app-store-connect fetch-signing-files "$APP_STORE_BUNDLE_ID_EFFECTIVE" \
--type IOS_APP_STORE \
--create
- name: Add signing certificates
run: keychain add-certificates
- name: Apply provisioning profiles
run: xcode-project use-profiles
- name: Resolve build number from TestFlight
id: build-number
run: |
# TestFlight上の最新ビルド番号を取得し、+1する
latest_build_number="$(app-store-connect get-latest-testflight-build-number "$APP_STORE_APPLE_ID" 2>/dev/null || true)"
if [[ -z "$latest_build_number" ]]; then
latest_build_number=0
fi
next_build_number="$((latest_build_number + 1))"
echo "next_build_number=$next_build_number" >> "$GITHUB_OUTPUT"
- name: Build IPA
run: |
flutter build ipa \
--release \
--build-number="${{ steps.build-number.outputs.next_build_number }}"
- name: Publish IPA to TestFlight
run: |
ipa_path="$(find "$PWD/build/ios/ipa" -maxdepth 1 -name '*.ipa' | head -n 1)"
app-store-connect publish \
--path "$ipa_path" \
--testflight
各ステップの解説
Codemagic CLI toolsのインストール
- name: Install Codemagic CLI tools
run: pip install codemagic-cli-tools
これが今回のキーストーンです。Fastlaneの設定ファイル(Fastfile)を用意しなくても、このCLIツール群 (app-store-connect, keychain, xcode-project) を使えば、ターミナルから直接App Store Connectの操作やプロビジョニングプロファイルの適用が可能です。
証明書とプロファイルの自動管理
- name: Fetch signing files from App Store Connect
run: |
app-store-connect fetch-signing-files "$APP_STORE_BUNDLE_ID_EFFECTIVE" \
--type IOS_APP_STORE \
--create
APIキーを使って自動でApp Store Connectと通信し、ディストリビューション証明書やプロビジョニングプロファイルを落としてきてくれます。自動で作成(--create)までやってくれるのが非常に便利です。
落とした証明書は続く keychain add-certificates と xcode-project use-profiles でXcodeプロジェクトに適用されます。
ビルド番号の自動採番
- name: Resolve build number from TestFlight
id: build-number
run: |
latest_build_number="$(app-store-connect get-latest-testflight-build-number ...)"
ビルドごとにビルド番号(CFBundleVersion)をインクリメントしないとアップロード時にエラーとなってしまいますが、これもCLIが最新の番号を取得してくれるので、CI側で単純に +1 すればOKです。
IPAのビルドとアップロード
- name: Publish IPA to TestFlight
run: |
app-store-connect publish \
--path "$ipa_path" \
--testflight
最後にFlutterのビルドコマンドで生成された .ipa ファイルを指定し、publish --testflight コマンドを叩くだけで、TestFlightの配信処理が完了します。
まとめ
mainブランチにマージ(またはプッシュ)するだけで、最新のアプリが関係者のデバイス(TestFlight)に届く状態を作っておくと、QA(品質保証)や動作確認の手間が劇的に下がります。
codemagic-cli-toolsはCodemagicを使っていなくてもGitHub Actionsなどで汎用的に使える優秀なツールなので、ぜひ試してみてください。
今回はここまで。