変更したところに、必要なチェックを。
アプリのコードを変えたとき、ドキュメントを直したとき、同じPRへ続けてコミットしたとき。毎回すべてのワークフローを最後まで動かす必要はありません。
GenuineCI v2.4.0では、変更ファイルに応じたワークフローの選択と、古いコミットのPRビルドを取り消す設定を追加しました。ワークフローごとのFlutterバージョン指定や、Stacked PRで選んだPRまで順にマージする操作も使えるようになりました。
この記事は11月2日〜8日の更新を中心に、前回のv2.3.0(10月23日)以降の変更をまとめています。SDKの新機能は、公開済みの openci_workflow 0.2.3 で利用できます。
変更パスで、実行するワークフローを選ぶ。
CITrigger.push() と CITrigger.pullRequest() に paths を追加しました。指定したパターンのいずれかに変更があった場合に、そのワークフローを実行します。
たとえば、モバイルアプリと共有パッケージに関係するPRだけをチェックする設定は、次のように書けます。
import 'package:openci_workflow/openci_workflow.dart';
Future<void> main() async {
final ci = await OpenCI.init(
workflowName: 'Mobile CI',
ciTriggers: [
CITrigger.pullRequest(
branch: 'main',
paths: [
'apps/mobile/**',
'packages/shared/**',
'openci/mobile_ci.dart',
'**/pubspec.yaml',
'pubspec.lock',
],
),
],
flutterVersion: '3.47.8',
cancelPreviousRuns: true,
);
await ci.dart.checkFormat();
await ci.flutter.staticAnalysis(dir: 'apps/mobile');
await ci.flutter.unitTests(dir: 'apps/mobile');
}openci/mobile_ci.dart に置く例です。アプリと共有パッケージのパスは、リポジトリの構成に合わせて調整してください。
パスはリポジトリルートからの相対指定です。* は同じ階層、** は下の階層も含めて一致します。アプリ本体だけでなく、共通パッケージ、依存関係の定義、ワークフロー自身など、結果に影響するファイルも含めてください。
PRではそのPR全体の差分、pushでは更新前後の差分を使います。対象外のワークフローはGitHub Checksに skipped と表示し、ビルドジョブやVMを作りません。変更一覧を完全に取得できない場合は、必要なチェックを落とさないよう実行します。paths を省略したワークフローは、これまでどおりイベントとブランチが一致すれば動きます。
以前の whenChanged: は paths: に変更してください。 SDK 0.2.0での名前の変更です。
新しいコミットのチェックに切り替える。
OpenCI.init(cancelPreviousRuns: true) を指定すると、新しいコミットのジョブを登録するときに、同じPR・同じワークフローの古いコミットに対する待機中・実行中のジョブを取り消します。
既定値は false です。新旧両方のジョブで有効になっている必要があり、設定を有効にする前のジョブは取り消しません。同じコミットの再実行、別のPR、pushのジョブ、完了済みのジョブは対象外です。paths でスキップされた場合も、以前の実行は取り消しません。
実行中のジョブは通常約15秒間隔の状態確認でキャンセルを検知し、その後VMの片付けとGitHub Checkの更新を行います。PRの解析やテストなど、新しい結果を優先したいワークフローで使ってください。
ワークフローごとに、Flutterバージョンを指定する。
flutterVersion: '3.47.8' のようにリリースを指定すると、CIがFVMでそのバージョンを選んでから、依存関係の取得とワークフローの実行を始めます。イメージにないバージョンは、そのジョブのVM内へインストールします。
バージョンは文字列リテラルで指定します。省略時はイメージの既定値を使い、.fvmrc から自動では読み取りません。ローカルでワークフローを実行する場合は、現在のSDKを使います。
あわせて ci.dart.checkFormat() も追加しました。Dartファイルを書き換えずにフォーマットを確認し、差分があればワークフローを失敗にします。
Stacked PRを、選んだPRまで順にマージする。
依存するPRを管理するStacked PRアプリに Merge stack を追加しました。たとえば main ← A ← B ← C のスタックでBを選ぶと、A、Bの順に、それぞれをmainへマージします。Cや兄弟のPRは対象に含めません。
親をマージした後は次のPRを同期し、更新後のCI・必要なレビュー・GitHubのマージ条件がそろうまで待ちます。進捗はPRコメントで確認でき、Cancel merge で残りを取り消せます。すでにマージしたPRはそのまま残ります。
親のマージに伴うbaseブランチの自動変更からの復旧や、同じスタックの同時更新を防ぐ処理も改善しました。追跡中のスタックがデフォルトブランチにつながっていない場合は、Checkで対象ブランチを示し、接続を直すまで一括マージを止めます。
ビルドを待つ間の処理も見直しました。
実行枠が空いたときは待機中の古いジョブを先に探し、空きがない間の再確認をまとめるようにしました。VMの解放後にも次のジョブの開始を促します。
実行用VMの既定CPU数は4 vCPUになり、ワーカーごとにVMへ割り当てるメモリも設定できるようになりました。ログの取り込みもまとめて処理します。所要時間はジョブの内容とワーカーの空き状況によって変わります。
前回以降の変更と、更新時の確認点。
今回の期間には、チーム管理・GitHub連携・ログ・シークレット・課金・ビルド実行をFirebase Functions、SQL Connect、Cloud Runを使う構成へ移した変更も含まれます。セルフホストにも独立したFirebaseプロジェクトを使う構成を用意しました。旧サーバーと旧ビルドワーカーは削除しているため、運用者の方は セルフホストの案内 と 配置手順 を確認してください。
ワークフローでは、チーム単位の連番を ci.runNumber で読み取れるようになりました。アプリのビルド番号にも使えます。チーム内の全ワークフローで共有する番号で、失敗や再実行によって欠番が生じることがあります。
生成したシークレットは Secret 型になりました。Secrets.apiToken.key で環境変数名、Secrets.apiToken.value で値を取得できます。以前の文字列getterから再生成した場合は、値を渡す箇所に .value を付けてください。
SDKからの LOKI_URL を使った直接送信は削除しました。コマンドの出力は引き続き標準出力・標準エラーへ流れ、CIでは実行側がログを保存します。新しい go-genuine CLIは開発初期段階で、現在の genuineci コマンドからの置き換えは不要です。
変更一覧とリリース対象の注意点は GitHub Release v2.4.0、実装の差分は v2.3.0との比較 で確認できます。SDKの設定例は ワークフローのDocs にまとめています。