跳到主內容

使用 Flutter 進行持續交付

如何自動化您的 Flutter 應用的持續構建和釋出。

遵循 Flutter 的持續交付最佳實踐,確保您的應用程式能夠頻繁地交付給 Beta 測試人員並進行驗證,而無需依賴手動工作流。

CI/CD 選項

#

有許多持續整合 (CI) 和持續交付 (CD) 選項可幫助自動化應用程式的交付。

內建 Flutter 功能的一體化選項

#

將 fastlane 整合到現有工作流中

#

您可以將 fastlane 與以下工具結合使用

本指南介紹瞭如何設定 fastlane,並將其整合到您現有的測試和持續整合 (CI) 工作流中。有關更多資訊,請參閱“將 fastlane 整合到現有工作流中”。

fastlane

#

fastlane 是一個開源工具套件,用於自動化應用的釋出和部署。

本地設定

#

建議在遷移到基於雲的系統之前,先在本地測試構建和部署過程。您也可以選擇從本地機器執行持續交付。

  1. 透過 gem install fastlanebrew install fastlane 安裝 fastlane。請訪問 fastlane 文件瞭解更多資訊。
  2. 建立一個名為 FLUTTER_ROOT 的環境變數,並將其設定為 Flutter SDK 的根目錄。(這是 iOS 部署指令碼所必需的。)
  3. 建立 Flutter 專案,準備就緒後,請確保您的專案可以透過以下命令進行構建:
    • Android flutter build appbundle;以及
    • iOS flutter build ipa
  4. 為每個平臺初始化 fastlane 專案。
    • Android 在您的 [project]/android 目錄中,執行 fastlane init
    • iOS 在您的 [project]/ios 目錄中,執行 fastlane init
  5. 編輯 Appfile 以確保它們包含適合您應用的元資料。
    • Android 檢查 [project]/android/fastlane/Appfile 中的 package_name 是否與 AndroidManifest.xml 中的包名匹配。
    • iOS 檢查 [project]/ios/fastlane/Appfile 中的 app_identifier 是否與 Info.plist 的 bundle identifier 匹配。填寫 apple_iditc_team_idteam_id 等相應的賬戶資訊。
  6. 設定您的應用商店本地登入憑據。
    • Android 遵循 Supply 設定步驟,並確保 fastlane supply init 成功從 Play Store 控制檯同步資料。請像對待密碼一樣對待 .json 檔案,不要將其簽入任何公共原始碼管理倉庫。
    • iOS 您的 iTunes Connect 使用者名稱已存在於 Appfileapple_id 欄位中。設定 FASTLANE_PASSWORD Shell 環境變數,並賦予其您的 iTunes Connect 密碼。否則,上傳到 iTunes/TestFlight 時系統會提示您輸入密碼。
  7. 設定程式碼簽名。
    • Android 遵循 Android 應用簽名步驟
    • iOS 在 iOS 上,當您準備使用 TestFlight 或 App Store 進行測試和部署時,請建立並使用釋出證書(distribution certificate)進行簽名,而不是開發證書(development certificate)。
      • 在您的 Apple Developer Account 控制檯中建立並下載釋出證書。
      • 執行 open [project]/ios/Runner.xcworkspace/ 並在目標設定面板中選擇釋出證書。
  8. 為每個平臺建立 Fastfile 指令碼。
    • Android 在 Android 上,遵循 fastlane Android Beta 部署指南。您的編輯可能非常簡單,只需新增一個呼叫 upload_to_play_storelane 即可。將 aab 引數設定為 ../build/app/outputs/bundle/release/app-release.aab,以使用 flutter build 已構建好的 app bundle。

    • iOS 在 iOS 上,遵循 fastlane iOS Beta 部署指南。您可以指定存檔路徑以避免重新構建專案。例如:

      ruby
      build_app(
        skip_build_archive: true,
        archive_path: "../build/ios/archive/Runner.xcarchive",
      )
      upload_to_testflight
      

您現在可以在本地執行部署,或者將部署過程遷移到持續整合 (CI) 系統。

在本地執行部署

#
  1. 構建釋出模式的應用。
    • Android flutter build appbundle
    • iOS flutter build ipa
  2. 在每個平臺上執行 Fastfile 指令碼。
    • Android cd android 然後 fastlane [您建立的 lane 名稱]
    • iOS cd ios 然後 fastlane [您建立的 lane 名稱]

雲端構建和部署設定

#

首先,請按照“本地設定”部分所述進行操作,確保流程在遷移到像 Travis 這樣的雲系統之前能夠正常工作。

主要需要考慮的是,由於雲實例是臨時且不可信的,您不應將 Play Store 服務賬戶 JSON 或 iTunes 釋出證書等憑據留在伺服器上。

持續整合 (CI) 系統通常支援使用加密環境變數來儲存私有資料。在構建應用時,可以使用 --dart-define MY_VAR=MY_VALUE 傳遞這些環境變數。

請務必注意,不要在測試指令碼中將這些變數值回顯到控制檯。 這些變數在合併到主分支之前在拉取請求 (Pull Request) 中是不可用的,以確保惡意行為者無法透過建立拉取請求來列印這些機密資訊。請謹慎對待您所接受和合並的拉取請求中與這些機密資訊的互動。

  1. 使登入憑據臨時化。

    • Android 在 Android 上:
      • Appfile 中刪除 json_key_file 欄位,並將 JSON 的字串內容儲存在 CI 系統的加密變數中。在您的 Fastfile 中直接讀取該環境變數。
        upload_to_play_store(
          ...
          json_key_data: ENV['<variable name>']
        )
        
      • 序列化您的上傳金鑰(例如使用 base64),並將其儲存為加密環境變數。您可以在安裝階段在 CI 系統上對其進行反序列化:
        bash
        echo "$PLAY_STORE_UPLOAD_KEY" | base64 --decode > [path to your upload keystore]
        
    • iOS 在 iOS 上:
      • 將本地環境變數 FASTLANE_PASSWORD 移動到 CI 系統上的加密環境變數中。
      • CI 系統需要訪問您的釋出證書。建議使用 fastlane 的 Match 系統來同步不同機器間的證書。
  2. 建議在 CI 系統上使用 Gemfile,而不是每次都執行不確定的 gem install fastlane,以確保 fastlane 依賴項在本地和雲端機器之間穩定且可重現。不過,此步驟是可選的。

    • 在您的 [project]/android[project]/ios 資料夾中,建立一個包含以下內容的 Gemfile
      source "https://rubygems.org"
      
      gem "fastlane"
      
    • 在這兩個目錄中,執行 bundle update 並將 GemfileGemfile.lock 簽入版本控制。
    • 在本地執行時,請使用 bundle exec fastlane 而不是 fastlane
  3. 在您的倉庫根目錄中建立 CI 測試指令碼,例如 .travis.yml.cirrus.yml

    • 檢視 fastlane CI 文件以獲取 CI 特定的設定。
    • 對指令碼進行分片 (Shard),以便在 Linux 和 macOS 平臺上執行。
    • 在 CI 任務的設定階段,執行以下操作:
      • 確保使用 gem install bundler 可以獲取 Bundler。
      • [project]/android[project]/ios 中執行 bundle install
      • 確保 Flutter SDK 可用並已設定在 PATH 中。
      • 對於 Android,確保 Android SDK 可用且已設定 ANDROID_SDK_ROOT 路徑。
      • 對於 iOS,您可能需要指定 Xcode 依賴項(例如 osx_image: xcode9.2)。
    • 在 CI 任務的指令碼階段:
      • 根據平臺執行 flutter build appbundleflutter build ios --release --no-codesign --config-only
      • cd androidcd ios
      • bundle exec fastlane [lane 名稱]

Xcode Cloud

#

Xcode Cloud 是一項持續整合和交付服務,用於構建、測試和分發適用於 Apple 平臺的應用和框架。

要求

#

自定義構建指令碼

#

Xcode Cloud 支援自定義構建指令碼,可在指定時間執行額外任務。它還包含一組預定義環境變數,例如 $CI_WORKSPACE(即克隆的倉庫所在位置)。

克隆後腳本 (Post-clone script)

#

利用在 Xcode Cloud 克隆您的 Git 倉庫後執行的“克隆後自定義構建指令碼”,請使用以下說明:

建立一個檔案 ios/ci_scripts/ci_post_clone.sh 並新增以下內容。

sh
#!/bin/sh

# Fail this script if any subcommand fails.
set -e

# The default execution directory of this script is the ci_scripts directory.
cd $CI_PRIMARY_REPOSITORY_PATH # change working directory to the root of your cloned repo.

# Install Flutter using git.
git clone https://github.com/flutter/flutter.git --depth 1 -b stable $HOME/flutter
export PATH="$PATH:$HOME/flutter/bin"

# Install Flutter artifacts for iOS (--ios), or macOS (--macos) platforms.
flutter precache --ios

# Install Flutter dependencies.
flutter pub get

# Install CocoaPods using Homebrew.
HOMEBREW_NO_AUTO_UPDATE=1 # disable homebrew's automatic updates.
brew install cocoapods

# Install CocoaPods dependencies.
cd ios && pod install # run `pod install` in the `ios` directory.

exit 0

此檔案應新增到您的 git 倉庫並標記為可執行。

git add --chmod=+x ios/ci_scripts/ci_post_clone.sh

工作流配置

#

Xcode Cloud 工作流定義了在觸發工作流時 CI/CD 過程中執行的步驟。

要在 Xcode 中建立新工作流,請使用以下說明:

  1. 選擇 Product > Xcode Cloud > Create Workflow 以開啟 Create Workflow 面板。

  2. 選擇工作流應附加到的產品(應用),然後點選 Next 按鈕。

  3. 下一個面板會顯示 Xcode 提供的預設工作流概覽,可透過點選 Edit Workflow 按鈕進行自定義。

分支更改 (Branch changes)

#

預設情況下,Xcode 會建議“分支更改”條件,該條件會在 Git 倉庫的預設分支發生每次更改時啟動新構建。

對於您應用的 iOS 變體,您可能希望在修改 flutter 包,或者修改 lib\ios\ 目錄內的 Dart 或 iOS 原始檔後,讓 Xcode Cloud 觸發您的工作流。

這可以透過使用以下“檔案和資料夾”條件來實現:

Xcode Workflow Branch Changes

下一個構建編號

#

Xcode Cloud 預設將新工作流的構建編號設為 1,並在每次成功構建後遞增。如果您使用的是具有更高構建編號的現有應用,則只需在迭代中指定 Next Build Number(下一個構建編號),即可配置 Xcode Cloud 使用正確的構建編號進行構建。

檢視 為 Xcode Cloud 構建設定下一個構建編號以獲取更多資訊。