Play Billing 更新で Kotlin metadata 2.3.0 エラーになる原因
Google Play Billing Library (以下 PBL) を上げたら、Billing とは無関係な Kotlin の metadata エラーでビルドが全滅して止まっていませんか。
PBL のアップグレードは Google 側に強制期限があるため、定期的に避けられない作業です。
私は動作確認用の Android テストアプリを持っていて、PBL が上がるたびに追従しています。
今回、古いバージョンからのメジャーアップグレードを検証する機会があり、7.1.1 から最新の 9.1.0 へ一気に上げてみました。
ちなみに作業には、Google が公開している AI エージェント向けの指示セット Android skills を使っていました。
ところが最初のビルドで出たエラーは、Billing の API とは何の関係もないものでした。
Kotlin の metadata バージョンが合わないという、コンパイラレベルのエラーです。
そして厄介なのは、この要件が公式の移行ガイドにも書かれていないことでした。
前提: billing と billing-ktx の 2 つがある
先に用語を整理しておきます。
PBL は依存が 2 つに分かれています。
com.android.billingclient:billing— 本体。Java で書かれているcom.android.billingclient:billing-ktx— Kotlin 拡張。suspend 関数などを提供する
公式ドキュメントでも「Kotlin を使っているなら KTX モジュールを入れてください」と案内されており、Kotlin で書くなら実質セットで入れるものです。
そして今回の問題を起こすのは、後者の billing-ktx です。
Kotlin で書かれたライブラリなので、コンパイル時の Kotlin バージョンが利用側と噛み合う必要があります。
本体側の billing は Java なので、この問題には関係しません。
Kotlin の metadata が合わずビルドが全滅する
build.gradle の Billing のバージョンを書き換えて、ビルドを実行します。
implementation "com.android.billingclient:billing:9.1.0"
implementation "com.android.billingclient:billing-ktx:9.1.0"すると、大量のエラーが流れます。
e: Incompatible classes were found in dependencies.
Remove them from the classpath or use '-Xskip-metadata-version-check' to suppress errors
e: jetified-billing-ktx-9.1.0-api.jar!/META-INF/....kotlin_module
Module was compiled with an incompatible version of Kotlin.
The binary version of its metadata is 2.3.0, expected version is 1.9.0.
e: MainActivity.kt:10:15 Class 'kotlin.Unit' was compiled with an incompatible version of Kotlin.
The actual metadata version is 2.2.0, but the compiler version 1.9.0 can read versions up to 2.0.0.
e: MainActivity.kt:15:63 Unresolved reference: java
e: BillingActivity.kt:46:24 Unresolved reference: listOfkotlin.Unit が読めない、listOf が未解決、という状態です。
Kotlin の標準ライブラリすら解決できていないので、Billing のコードを直す以前の問題でした。
エラーの本数だけ見ると絶望的ですが、原因は 1 つです。
原因: billing-ktx 8.1.0 から kotlin-stdlib 2.2.10 が必要になっていた
Maven に公開されている POM を見ると、はっきりわかります。
billing-ktx が依存する kotlin-stdlib のバージョンを、各リリースで並べたのが次の表です。
| billing-ktx | 要求する kotlin-stdlib |
|---|---|
| 7.1.1 | 1.4.0 |
| 8.0.0 | 1.4.0 |
| 8.1.0 | 2.2.10 |
| 8.2.0 | 2.2.10 |
| 8.3.0 | 2.2.10 |
| 9.0.0 | 2.2.10 |
| 9.1.0 | 2.2.10 |
8.1.0 で 1.4.0 から 2.2.10 へ、一気に跳ね上がっています。
8.0.0 までは 1.4.0 だったので、Kotlin 1.x 系のプロジェクトでも問題なく使えていました。
境目は 9 系ではなく 8.1.0 です。
私は 7.1.1 から 9.1.0 へ一気に上げたので 9 系で踏んだように見えましたが、8.1.0 に上げた時点でも同じことが起きていたはずです。
つまりこれは「古いプロジェクトだから踏んだ」という話ではありません。
Kotlin 1.x のままで PBL 8.1.0 以降に上げようとすると、誰でも踏みます。
私のプロジェクトの Kotlin プラグインは 1.9.23 でした。
エラーメッセージの expected version is 1.9.0 は、この 1.9.23 を指しています。
対処: Kotlin プラグインを 1.9.23 から 2.2.10 に上げる
ルートの build.gradle で Kotlin プラグインのバージョンを上げます。
plugins {
id 'com.android.application' version '8.4.0' apply false
id 'com.android.library' version '8.4.0' apply false
- id 'org.jetbrains.kotlin.android' version '1.9.23' apply false
+ id 'org.jetbrains.kotlin.android' version '2.2.10' apply false
}これで metadata 関連のエラーは全て消えました。
残ったのは、本来直したかった Billing の API 起因のエラーだけです。
e: BillingActivity.kt:57:36 No value passed for parameter 'p0'.
e: BillingActivity.kt:97:61 Argument type mismatch:
actual type is 'QueryProductDetailsResult', but 'List<ProductDetails>' was expected.
e: SubsActivity.kt:242:23 Unresolved reference 'queryPurchaseHistoryAsync'.ここまで来れば、あとは移行ガイドどおりに直していくだけです。
-Xskip-metadata-version-check で抑制してはいけない
エラーメッセージには、次のような一文が含まれています。
Remove them from the classpath or use ‘-Xskip-metadata-version-check’ to suppress errors
読んだままに -Xskip-metadata-version-check を付けると、確かにエラーは黙ります。
ただしこれは「新しい metadata を古いコンパイラに無理やり読ませる」だけのオプションです。
コンパイルが通っても、実行時に何が起きるかは保証されません。
アプリ内課金という、お金が動く箇所で使うライブラリでこれを選ぶ理由はないと判断しました。
素直に Kotlin を上げるのが正解です。
Kotlin のバージョン要件は移行ガイドにもリリースノートにも書かれていない
ここが今回いちばん引っかかった点です。
PBL 9 の移行ガイドを読み直しましたが、必要な Kotlin のバージョンについての記載はありませんでした。
冒頭で触れたとおり「Kotlin を使っているなら KTX モジュールを入れてください」という案内はあります。
ですが、そのために Kotlin 自体を何バージョン以上にすべきかは書かれていません。
リリースノートにも同様に記載がありません。
移行ガイドが挙げている 9.0.0 の要件は targetSdkVersion を 35 にすることで、こちらは明記されています。
SDK の要件は書くのに、ビルドツールチェーン側の要件は落ちている、という状態でした。
Google 公式の AI 向け skill にも同じ穴があった
今回の作業では、Google が公開している Android skills を使っていました。
AI エージェント向けに Google が提供している指示セットで、play-billing-library-version-upgrade という PBL 専用の skill があります。
Agent Skills のオープン標準に準拠しているため、ファイルを配置するだけで対応エージェントから使えます。
この skill には、環境要件を確認するための記述がちゃんとあります。
references/migration-logic.md の「SDK & Environment Requirements」という節です。
- **PBL 7.0** : Requires `compileSdk 34` or higher.
- **PBL 8.0** : Requires `compileSdk 34` or higher.
- **PBL 9.0** : Requires `compileSdk 35` or higher.
- **Kotlin** : Verify that `kotlin-stdlib` is updated to at least 1.9.x
to support new library coroutine extensions.最後の行に注目してください。
「kotlin-stdlib は 1.9.x 以上であることを確認せよ」と書かれています。
私のプロジェクトは 1.9.23 でした。
skill の要件を満たしているのに、ビルドが通らなかったわけです。
実際に必要だったのは 2.2.10 で、1 メジャー違います。
この skill の last-updated は 2026-08-06 でした。
Kotlin 要件が上がった 8.1.0 のリリースは 2025-11-06 で、skill の更新日より 9 ヶ月も前です。
それだけの期間があっても、Kotlin の要件は 1.9.x のまま取り残されていました。
AI に任せるほど気づきにくくなる
この構造が地味に怖いところです。
公式ドキュメントに書かれていない要件は、それを読んで動く AI エージェントにも当然伝わりません。
さらに公式提供の skill 側にも古い数字が残っていると、エージェントは「要件は満たしている」と判断して先に進みます。
今回それでも解決できたのは、ビルドエラーという逃げ場のない事実が出たからです。
ドキュメントも skill も間違っていましたが、コンパイラは正しいことを言っていました。
ライブラリのアップグレードを AI に任せる場合、ビルドとテストが通ることを最終的な判断基準にするのが結局いちばん確実だと感じました。
指示書の記述を信頼の根拠にはできません。
同じエラーを踏んだときの確認手順
metadata 関連のエラーは他のライブラリでも起きるので、原因の切り分け方をまとめておきます。
- エラーに出ている
jarの名前を見て、どのライブラリが原因かを特定する - そのライブラリの POM を確認し、要求している
kotlin-stdlibのバージョンを調べる - 自分のプロジェクトの Kotlin プラグインのバージョンと比べる
- Kotlin プラグインを上げて、metadata のエラーが消えることを確認する
POM は Google の Maven リポジトリで直接見られます。
この中の kotlin-stdlib の version が、実際に必要な下限です。
ドキュメントを探すより、こちらを見るほうが速くて確実でした。
まとめ
- PBL を上げると
metadata is 2.3.0, expected version is 1.9.0でビルドが落ちることがある。原因は Billing の API ではなく Kotlin のバージョン billing-ktxが要求するkotlin-stdlibは 8.1.0 で 1.4.0 から 2.2.10 に跳ね上がっている。境目は 9 系ではなく 8.1.0 で、8.0.0 までは Kotlin 1.x で問題なかった- 対処は Kotlin プラグインを 2.x に上げること。
-Xskip-metadata-version-checkでの抑制は、課金周りでは選ぶべきではない - この要件は公式の移行ガイドにもリリースノートにも書かれていない。
targetSdkVersionの要件は明記されているのに、ビルドツールチェーン側は落ちている - Google 公式の Android skill にも 「kotlin-stdlib は 1.9.x 以上」という古い記述が残っている。要件を満たしていてもビルドは通らない
- 正確な下限は POM を直接見るのが早い。
dl.google.comの Maven リポジトリで確認できる
ライブラリの更新でハマるとき、原因がそのライブラリ自体ではなく足元のツールチェーンにあることは珍しくありません。
今回は公式ドキュメントと公式 skill の両方に記載がなく、コンパイラのエラーだけが正しい答えを持っていました。
AI に作業を任せる場面が増えても、ビルドが通ったかどうかを最後の砦にしておく価値は変わらないと思います。
アップグレードが終わって Billing の API 側を直す段になったら、アプリ内課金(Google Play Billing)の全体像から定期購入・注文情報・RTDN の各記事へ進めます。
