依存関係の検証

不正使用された Gradle の依存関係はセキュリティ上のリスクとなります。悪意のある攻撃者は、依存関係の解決中に中間者攻撃を行うなどして、変更された依存関係をビルドプロセスに挿入する可能性があります。

ビルド依存関係(ライブラリ)が侵害された場合、デバイスでのアプリの実行方法に影響する可能性があります。プラグインの依存関係が侵害されると、ビルドの動作が変更されたり、ビルドマシンで外部コマンドが実行されたりする可能性があります。

これを軽減するには、ビルドで依存関係の検証を有効にします。

ライブラリのチェックサムと署名

ライブラリ作成者は、ダウンロードする依存関係の真正性を確認するために役立つ 2 つのメタデータを提供できます。承認する値を指定する gradle/verification-metadata.xml という名前のファイルを定義します。次のようなものが含まれます。

  • チェックサム - アーティファクトのハッシュ。転送中にアーティファクトが破損していないことを確認するために使用できます。チェックサムが信頼できるソースから取得された場合、アーティファクトが変更されていないことを示します。これにより、中間者攻撃を軽減できます。

    欠点は、チェックサムはアーティファクトから計算されるため、リリースごとに変更され、アップグレードするたびに gradle/verification-metadata.xml を更新する必要があることです。

  • 署名 - 依存関係のユーザーが特定のアーティファクトの公開鍵を指定して、そのアーティファクトが、その公開鍵の認証済み所有者であるライブラリ作成者によってビルドされ、署名されたことを検証できるようにします。これはライブラリ作成者にとって負担が増えますが、秘密鍵自体が侵害されていない限り、署名はライブラリが正当であることを示します。

    ライブラリ作成者がアーティファクトの各バージョンに同じ鍵で署名している場合、アップグレード時に gradle/verification-metadata.xml を更新する必要はありません。

依存関係の検証を有効にする

Gradle 依存関係の検証では、ビルド中にチェックサムと署名が比較されます。

次の内容を含む gradle/verification-metadata.xml ファイルを作成します。

<?xml version="1.0" encoding="UTF-8"?>
<verification-metadata
    xmlns="https://schema.gradle.org/dependency-verification"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="https://schema.gradle.org/dependency-verification https://schema.gradle.org/dependency-verification/dependency-verification-1.3.xsd">
    <configuration>
        <!-- verify .pom and .module files -->
        <verify-metadata>true</verify-metadata>
        <!-- verify .asc PGP files that come with the artifacts -->
        <verify-signatures>true</verify-signatures>
        <!-- use human readable keyring format -->
        <keyring-format>armored</keyring-format>
        <!-- read keys in a local file, fewer requests to network -->
        <key-servers enabled="false">
            <key-server uri="https://keyserver.ubuntu.com"/>
            <key-server uri="https://keys.openpgp.org"/>
        </key-servers>
    </configuration>
    <components>
    </components>
</verification-metadata>

これは出発点として使用するものであり、まもなく更新されます。

./gradlew assembleDebug を実行して、ビルドがどのように変更されるかを確認します。次のようなメッセージが表示されます。

* What went wrong:
Error resolving plugin [id: 'com.android.application', version: '8.7.3', apply: false]
> Dependency verification failed for configuration 'detachedConfiguration1'
  One artifact failed verification: com.android.application.gradle.plugin-8.7.3.pom ...
  This can indicate that a dependency has been compromised ...
  
  Open this report for more details: .../dependency-verification-report.html

Gradle は、明示的に承認していない依存関係のバージョンを pull していると報告しています。

チェックサムと署名データをブートストラップする

初期セットの信頼できる鍵とコンポーネントをブートストラップできます。このプロセスでは、プロジェクトで使用されているすべてのライブラリの現在のシグネチャとチェックサムが収集されます。

次のコマンドを実行して、初期メタデータを生成します。

./gradlew --write-verification-metadata pgp,sha256 --export-keys help

このコマンドは、このプロジェクトで使用されるすべての依存関係の PGP キーとフォールバック チェックサムのリストをビルドするよう Gradle に指示します。verification-metadata.xml が変更され、次のようなエントリが追加されます。

<trusted-key id="8461EFA0E74ABAE010DE66994EB27DB2A3B88B8B">
    <trusting group="androidx.activity"/>
</trusted-key>

これにより、Maven グループ androidx.activity からの依存関係が検出された場合、付属の .asc ファイル(リポジトリに保存されている署名)がそのキーと一致するように Gradle に指示します。

ブートストラップでは、ビルドで使用される公開 PGP 鍵を含む gradle/verification-keyring.keys も生成されます。これらのファイルの両方をバージョン トラッキング システムにチェックインします。verification-metadata.xml または verification-keyring.keys を変更する今後の変更は、慎重に確認する必要があります。

信頼できる鍵からバージョンを削除する

ライブラリのリリース間で署名鍵が変更されることはほとんどありません。gradle/verification-metadata.xml ファイルに生成されたデータにはバージョンの詳細が含まれているため、新しい依存関係のバージョンごとにキー情報を再度追加する必要があります。

これを回避し、キーがライブラリのすべてのバージョンに適用されることを指定するには、バージョン仕様を削除します。

Android Studio エディタで、[Edit] > [Find] > [Replace...] を使用して、正規表現で信頼できる鍵のバージョン仕様をすべて置き換えます。

  • 送信元: <trusted-key(.*) version=\".*\"/>
  • 宛先: <trusted-key$1/>

Android Studio の同期

ここまではコマンドライン ビルドが機能していますが、Android Studio で同期しようとすると、次のようなエラーが表示されます。

A build operation failed.
    Dependency verification failed for configuration ':app:detachedConfiguration3'
One artifact failed verification: gradle-8.10.2-src.zip (gradle:gradle:8.10.2) from repository Gradle distributions
If the artifacts are trustworthy, you will need to update the gradle/verification-metadata.xml file. For more on how to do this, please refer to https://docs.gradle.org/8.10.2/userguide/dependency_verification.html#sec:troubleshooting-verification in the Gradle documentation.

Android Studio は、Gradle ソース(他のソースやドキュメントとともに)をダウンロードしようとしています。この問題を修正する最も簡単な方法は、すべてのソースと Javadoc を信頼することです。gradle/verification-metadata.xml<trusted-artifacts> を追加します。

<verification-metadata ...>
   <configuration>
      <trusted-artifacts>
         <trust file=".*-javadoc[.]jar" regex="true"/>
         <trust file=".*-sources[.]jar" regex="true"/>
         <trust group="gradle" name="gradle"/>
      </trusted-artifacts>
      ...
  </configuration>
</verification-metadata>

これで、コマンドラインと Android Studio からビルドが正常に機能するようになります。