FireBaseSDKを組み込んだiOSプロジェクトをGitHub Actionsでビルドする方法

# 課題
FireBaseSDKを組み込んだiOSプロジェクトでは、`GoogleService-Info.plist`というAPI Keyなどのシークレット情報を含むファイルをプロジェクトに含める必要があります。

シークレット情報なので、そのままGitHubのリポジトリにPushすると情報漏洩する危険があるので、基本的には`GoogleService-Info.plist`はPushしないようにします。

しかしCI環境でビルドする際に、`GoogleService-Info.plist`がないとFireBaseSDKを組み込んだiOSプロジェクトはビルド出来ないため、ビルド時には`GoogleService-Info.plist`をどうにかして参照する必要があるのです。

※FireBaseSDKの導入方法

https://firebase.google.com/docs/ios/setup?hl=ja#add-config-file

今回は後続で記載する環境で、上記課題を解決した方法を記事にしてみます。

# 環境
- Xcode: 16
- CI: GitHub Actions
- Package管理ツール: SPM
- [FireBaseSDK](https://github.com/firebase/firebase-ios-sdk): 11.2.0

# 解決方法
CI環境の環境変数に`GoogleService-Info.plist`の内容を設定し、ビルド前に環境変数を元に`GoogleService-Info.plist`を生成することで解決します。

具体的には以下手順になります。

1. `GoogleService-Info.plist`をBase64でコンコードする
2. エンコードした内容をGitHub Actionsの`Actions secrets and variables`に設定
3. CIのワークフローに`GoogleService-Info.plist`を生成するステップを追加

※参考

https://qiita.com/takagimeow/items/25e5e3be731111c641ce

# 手順1
### `GoogleService-Info.plist`をBase64でコンコードする

以下コマンドの実行結果を控えます

```bash
% base64 < <ファイルパス>/GoogleService-Info.plist
```

# 手順2
### エンコードした内容をGitHub Actionsの`Actions secrets and variables`に設定

`Actions secrets and variables`では安全に秘密の情報を設定することができ、GitHub Actionsではその設定した情報を参照することができます。
下記で`Actions secrets and variables`の設定手順を説明します。

本対応を入れたいGitHubリポジトリのSettingタブを押下します。
![スクリーンショット 2024-10-07 19.49.00.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3359094/34f9ae05-81a7-4d23-9b6d-13931e6e24ed.png)

左メニュのSecurityセクションの下記赤枠部分を押下します。
![スクリーンショット 2024-10-07 19.51.28.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3359094/e603a21b-ec74-f64c-f6fc-80cdd82d21ac.png)

下記赤枠の`New repository secret`を押下します。
![スクリーンショット 2024-10-07 19.52.00.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3359094/37fdeffb-bfd7-7f1e-e9f1-e45b1628011f.png)

`Name`には任意の名前を設定し、`Secret`では手順1で控えたBase64エンコードした値を設定します。
そして以下赤枠ボタンを押下します。
![スクリーンショット 2024-10-07 19.52.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3359094/9d557429-ab8c-a0f7-cb4e-f7d2f2219cc6.png)

これで`Actions secrets and variables`の設定完了です。

# 手順3
### CIのワークフローに`GoogleService-Info.plist`を生成するステップを追加

下記が`GoogleService-Info.plist`を生成するステップの実装です。

```yaml
# GoogleService-Info.plistの復元
      - name: Decode GoogleService-Info.plist
        run: |
          echo ${{ secrets.GOOGLE_SERVICE_INFO_PLIST_CONTENT }} | base64 -o ${{ env.GOOGLE_SERVICE_INFO_PLIST_PATH }} -D          
```

やっていることとしては、`${{ secrets.GOOGLE_SERVICE_INFO_PLIST_CONTENT }}`で`GoogleService-Info.plist`のBase64エンコード内容を取得し、
`base64 -D'コマンドでBase64デコードして元の`GoogleService-Info.plist`の内容を取得して環境変数`GOOGLE_SERVICE_INFO_PLIST_PATH`に設定したパスのファイルに出力します。

これで外部へは`GoogleService-Info.plist`の情報を漏らさないまま、GitHub Actions内では`GoogleService-Info.plist`を参照することができます。

CIワークフローの全体コードの実装例は以下の通りです。

```yaml
name: CI_WORKFLOW

on:
  pull_request:
    branches:
      - "*"
  workflow_dispatch:

env:
  DEVELOPER_DIR: /Applications/Xcode_16.0.app
  WORKSPACE_PATH: XXX.xcworkspace
  TARGET_SCHEME_NAME: XXX
  TARGET_TEST_PLAN_NAME: XXX
  GOOGLE_SERVICE_INFO_PLIST_PATH: XXX/GoogleService-Info.plist

jobs:
  build:
    runs-on: macos-latest

    steps:
      # チェックアウト(リポジトリからソースコードを取得)
      - name: Check Out repository
        uses: actions/checkout@v3

      # Xcodeの一覧出力
      - name: Show Xcode list
        run: ls /Applications | grep 'Xcode'

      # Xcodeのバージョン指定
      - name: Select Xcode version
        run: sudo xcode-select -s ${{ env.DEVELOPER_DIR }}

      # Xcodeのバージョン出力
      - name: Show Xcode version
        run: xcodebuild -version

      # Rudy製ライブラリのキャッシュ
      - name: Cache Gems
        uses: actions/cache@v2
        with:
          path: vendor/bundle
          key: ${{ runner.os }}-gems-${{ hashFiles('**/Gemfile.lock') }}
          restore-keys: |
            ${{ runner.os }}-gems-

      # Rudy製ライブラリのインストール
      - name: Install Bundled Gems
        run: |
          bundle config path vendor/bundle
          bundle install --jobs 4 --retry 3

      # SPMのライブラリのキャッシュ
      - name: Cache Swift Packages
        uses: actions/cache@v2
        with:
          path: SourcePackages
          key: ${{ runner.os }}-spm-${{ hashFiles('*.xcodeproj/project.xcworkspace/ xcshareddata/swiftpm/Package.resolved') }}
          restore-keys: ${{ runner.os }}-spm-

      # GoogleService-Info.plistの復元
      - name: Decode GoogleService-Info.plist
        run: |
          echo ${{ secrets.GOOGLE_SERVICE_INFO_PLIST_CONTENT }} | base64 -o ${{ env.GOOGLE_SERVICE_INFO_PLIST_PATH }} -D

      # テスト
      - name: Xcode virify
        run: set -o pipefail &&
          xcodebuild
          -workspace ${WORKSPACE_PATH}
          -scheme ${TARGET_SCHEME_NAME}
          -testPlan ${TARGET_TEST_PLAN_NAME}
          -sdk iphonesimulator
          -configuration Debug
          -destination "platform=iOS Simulator,OS=17.2,name=iPhone 15 Pro"
          -clonedSourcePackagesDirPath SourcePackages
          -scmProvider xcode
          -allowProvisioningUpdates
          -skipPackagePluginValidation
          -parallel-testing-enabled NO
          clean test |
          bundle exec xcpretty

```

以上がFireBaseSDKを組み込んだiOSプロジェクトをGitHub Actionsでビルドする方法でした。