サブスクリプションの解約理由は返金リクエストより先に届くことが多く、Google Play は Apple よりはるかに多くの情報を渡してくれる
Google Play は解約アンケートでサブスクリプションの解約理由を記録し、Apple は有効期限切れのコードしか送りません。各ストアが何を教えてくれるのか、どのシグナルが返金やチャージバックの前兆なのか、そしてそれぞれにどれだけのコストがかかるのかを解説します。

要点
- Google Play は解約時にサブスクライバーへ理由を尋ね、その回答は purchases.subscriptionsv2 の canceledStateContext.userInitiatedCancellation.cancelSurveyResult を通じて開発者に届きます。
- Google Play の解約アンケートには、開発者が読み取れる回答が 5 つあります。利用頻度が低い、技術的な問題、料金関連、より良いアプリが見つかった、その他です。reasonUserInput の自由記述は、ユーザーが「その他」を選んだ場合にのみ入ります。
- Google Play の SUBSCRIPTION_CANCELED 通知に含まれるのは購入トークンだけです。解約理由は purchases.subscriptionsv2.get で取得する必要があり、ユーザーがサブスクリプションを復元すると Google は解約関連のフィールドをすべて消去します。
- Apple の App Store Server API には解約アンケートがありません。expirationIntent フィールドが返すのは 5 つのコードのいずれかです。顧客による解約、請求エラー、値上げまたはオファー移行への未同意、商品が購入不可、その他です。
- Apple の DID_CHANGE_RENEWAL_STATUS 通知でサブタイプが AUTO_RENEW_DISABLED の場合、顧客が自動更新をオフにしたとは限りません。顧客の返金リクエストを受けて App Store が自動更新をオフにした可能性もあります。
- 解約理由があっても、開発者が返金の判断に関与できるわけではありません。証拠を求めてくるのは、12 時間以内に回答する Apple の CONSUMPTION_REQUEST と、24 時間以内に回答する orders.reviewrefund 経由の Google Play のチャージバック審査だけです。
- 技術的な問題を理由に解約した Google Play のサブスクライバーは、最も返金を求めやすい層です。2026 年 8 月 3 日以降の注文では、チャージバックが認められると、開発者は購入価格から Play のサービス手数料を引いた額に加えて銀行の手数料を負担します。
最終的に返金を受けるサブスクライバーの多くは、まず解約します。その解約には理由がついていますが、2 つのストアが渡してくれる情報量は大きく異なります。Google Play は短いアンケートを実施し、自由記述も含めた回答をサーバーに渡します。Apple が送るのは数値コードだけで、それが示すのはサブスクリプションがどう終わったかであり、顧客がなぜやめたかったかではありません。両方を正しく読めば、まだ手を打てるうちに返金リクエストの兆しに気づけます。
Google Play が教えてくれるサブスクリプションの解約理由
ユーザーが Play の定期購入センターで解約すると、Google は理由を尋ねます。回答は purchases.subscriptionsv2.get で取得するサブスクリプションリソースの canceledStateContext に入ります。このオブジェクトはサブスクリプションが解約済みまたは期限切れの状態のときだけ存在し、誰がサブスクリプションを終了させたかを示します。ユーザー、Google のシステム、開発者、またはプラン変更などによる置き換えのいずれかです。
ユーザーが解約した場合、userInitiatedCancellation オブジェクトには 2 つのフィールドがあります。cancelTime は解約日時、cancelSurveyResult はアンケートの回答です。
| アンケートの理由 | Google の説明 | よく示しているもの |
|---|---|---|
| CANCEL_SURVEY_REASON_NOT_ENOUGH_USAGE | サブスクリプションをあまり利用していない | 利用が少なく、アカウントにかかったコストも小さい |
| CANCEL_SURVEY_REASON_TECHNICAL_ISSUES | アプリ使用中の技術的な問題 | 返金とチャージバックの最も強いシグナル |
| CANCEL_SURVEY_REASON_COST_RELATED | 料金関連の問題 | 価格への敏感さ。予期しない更新の場合もある |
| CANCEL_SURVEY_REASON_FOUND_BETTER_APP | より良いアプリが見つかった | 競合に負けただけで、争いになることはまれ |
| CANCEL_SURVEY_REASON_OTHERS | その他の理由 | reasonUserInput でユーザー自身の言葉を確認する |
| CANCEL_SURVEY_REASON_UNSPECIFIED | 解約アンケートの理由が未指定 | 判断材料となる回答がない |
右端の列は私たちの解釈であり、Google の見解ではありません。最初の 2 列は API リファレンスからそのまま引用しています。
通知には理由が含まれない
サブスクリプションが解約されると、SUBSCRIPTION_CANCELED のリアルタイム デベロッパー通知(type 3)が送られます。Google は、この通知が伝えるのは購入状態が変わったことだけだと明言しています。ペイロードには購入トークン以外に役立つ情報がないため、アンケートの回答を読むにはハンドラーから purchases.subscriptionsv2.get を呼び出す必要があります。
Play Console での確認
合計を見るだけならコードは不要です。Play Console の定期購入レポートには、解約を自発的、非自発的、その他に分ける「解約」カードと、回答を選んだユーザーの「解約アンケートの回答」カードがあります。「その他」を選んだユーザーの自由記述は、「その他の回答」カードから CSV でダウンロードできます。ダウンロードには View financial data の権限が必要で、注文を読み取るツールに付与するものと同じ権限です。
Apple が教えてくれること、教えてくれないこと
Apple には、開発者に結果が届く解約アンケートがありません。最も近いのは署名付き更新情報の expirationIntent ですが、これが表すのはサブスクリプションがどう終わったかであり、顧客がどう考えたかではありません。
| expirationIntent | Apple の定義 | 対応する EXPIRED サブタイプ |
|---|---|---|
| 1 | 顧客がサブスクリプションを解約した | VOLUNTARY |
| 2 | 支払い情報が無効などの請求エラー | BILLING_RETRY |
| 3 | 同意が必要な値上げまたはオファー移行に同意しなかった | PRICE_INCREASE |
| 4 | 更新時に商品が購入できなかった | PRODUCT_NOT_FOR_SALE |
| 5 | その他の理由 | サブタイプなし |
顧客自身の選択を表すのはコード 1 だけで、その動機については何もわかりません。アプリのクラッシュが続いて離れた顧客も、単にプロジェクトを終えただけの顧客も、まったく同じに見えます。
AUTO_RENEW_DISABLED に隠れたシグナル
Apple の通知の中に、注意深く見る価値があるものが 1 つあります。サブタイプが AUTO_RENEW_DISABLED の DID_CHANGE_RENEWAL_STATUS は、通常は顧客が自動更新をオフにしたことを意味します。しかし Apple のドキュメントには 2 つ目のケースも書かれています。顧客が返金をリクエストしたあと、App Store も自動更新をオフにするのです。
つまり iOS では、自動更新オフのイベントが返金リクエストの最初の痕跡になることがあります。購入が消耗型アイテムや自動更新サブスクリプションであれば、続いて CONSUMPTION_REQUEST が届く可能性があり、その時点から消費データを送るまでの猶予は 12 時間です。アプリ内で目立った操作がないのに自動更新オフのイベントが届いたら、そのアカウントの利用データを準備しておく合図として扱う価値があります。
Apple と Google の比較
| Google Play | Apple App Store | |
|---|---|---|
| ユーザーに理由を尋ねるか | はい、解約アンケートあり | 開発者が見られるアンケートはない |
| 理由の格納場所 | purchases.subscriptionsv2 の canceledStateContext | 更新情報の expirationIntent |
| 自由記述 | reasonUserInput、「その他」の場合のみ | なし |
| 誰が解約したか | ユーザー、システム、開発者、置き換え | コードとサブタイプから推測 |
| 通知 | SUBSCRIPTION_CANCELED、その後 get を呼ぶ | DID_CHANGE_RENEWAL_STATUS、EXPIRED |
| 再登録で失われるか | はい、復元時に消去 | 更新情報は現在の状態を反映 |
| ダッシュボード | 「解約アンケートの回答」カード | 理由についてはなし |

解約が返金に変わるところ
解約で止まるのは次回の請求です。前回の請求が戻るわけではありません。お金が戻るかどうかは、顧客が次にどの返金フローにたどり着くかで決まり、そのほとんどは開発者の関与なしに進みます。
- Google Play では、購入者は購入から 48 時間以内なら自分で返金を受けられ、判断するのは Google です。
- Google や Apple のサポート経由の返金は、ストアが判断します。
- Apple の CONSUMPTION_REQUEST は消費データを求めてきます。回答期限は 12 時間です。
- Google Play のチャージバック審査は orders.reviewrefund を通じて証拠を求めてきます。回答期限は 24 時間です。チャージバックに関する銀行の判断は最終的なものです。
解約理由によって、これらのルールが変わることはありません。変わるのは、どの顧客が不満を抱えているかに気づくタイミングと、証拠を求める 2 つのフローのどちらかが届いたときに証拠が準備できているかどうかです。
理由ごとのコスト
アンケートの回答は、そのアカウントにすでにどれだけの提供コストがかかったかの目安にもなります。それは返金されたときに開発者の手元に残る負担額です。
技術的な問題
これが最も高くつくケースです。問題に遭遇するほど製品を使っているということは、セッションのためのコンピューティング、リクエストによるモデル API の呼び出し、作成されたもののストレージ、そして利用したコンテンツのクリエイターへの支払いまで、すでにコストを負担しているということです。そのうえで返金されれば、代金は戻り、コストはそのまま残ります。Google Play で銀行に申し立てられた場合、2026 年 8 月 3 日以降の注文では、購入価格から Play のサービス手数料を引いた額に加えて銀行の手数料を負担することになります。
料金関連
価格への不満は、見た目ほどコストがかかりません。ただし、予期しない更新が隠れている場合は別です。それはチャージバックの典型的なパターンなので、解約が更新の請求直後だったか、更新のリマインダーが送られていたかを確認してください。
利用頻度が低い
利用が少なければ提供コストも小さいので、この場合の返金は、あまりコストをかけずに得たお金を返すことがほとんどです。Apple から消費データを求められた場合も、正直なデータが、顧客が何を使い何を使わなかったかを正確に示してくれます。
より良いアプリが見つかった
このタイプの顧客が争いを起こすことはまれです。競合に移っただけです。この理由はプロダクトの判断には役立ちますが、返金への対策にはほとんど役立ちません。
解約理由を読み取るためのルーチン
- Google Play の SUBSCRIPTION_CANCELED を受け取るたびに purchases.subscriptionsv2.get を呼び出し、canceledStateContext を購入トークンと cancelTime と一緒に保存します。
- 理由が「その他」の場合は、reasonUserInput をそのまま保存します。どちらのストアでも、得られる自由記述はこれだけです。
- Apple の DID_CHANGE_RENEWAL_STATUS(AUTO_RENEW_DISABLED)を受け取るたびにイベントを記録し、CONSUMPTION_REQUEST が続く場合に備えてそのアカウントの利用データを取り出しておきます。
- Apple の EXPIRED 通知を受け取るたびにサブタイプと expirationIntent を記録し、自発的な解約と請求の失敗が混ざらないようにします。
- 技術的な問題を理由にした Google Play の解約については、そのアカウントのエラーログを確認し、顧客が銀行に連絡する前にこちらから連絡します。
- アカウントごとの利用ログを残しておき、CONSUMPTION_REQUEST には 12 時間以内、チャージバック審査には 24 時間以内に回答できるようにします。
よくある質問
- Google Play のサブスクライバーが解約した理由はどうすれば確認できますか?
- purchases.subscriptionsv2.get を呼び出し、canceledStateContext.userInitiatedCancellation.cancelSurveyResult を読み取ります。理由のフィールドにアンケートの回答が入り、ユーザーが「その他」を選んだ場合は reasonUserInput に自由記述が入ります。Play Console の「解約アンケートの回答」カードでも合計を確認できます。
- Apple は顧客がサブスクリプションを解約した理由を開発者に教えてくれますか?
- いいえ。Apple には開発者が見られる解約アンケートがありません。expirationIntent フィールドはサブスクリプションがどう終わったかを示すもので、顧客による解約、請求エラー、値上げへの未同意、商品が購入不可、その他のコードがありますが、顧客の動機は含まれません。
- SUBSCRIPTION_CANCELED 通知に解約理由は含まれますか?
- いいえ。Google Play のリアルタイム デベロッパー通知が伝えるのは、購入状態が変わったことだけです。理由を読むには purchases.subscriptionsv2.get でサブスクリプションを取得し、すぐに保存してください。ユーザーがサブスクリプションを復元すると、Google は解約関連のフィールドを消去します。
- Apple の AUTO_RENEW_DISABLED 通知が返金リクエストを意味することはありますか?
- あります。Apple のドキュメントによると、AUTO_RENEW_DISABLED サブタイプは、顧客が自動更新をオフにした場合と、顧客の返金リクエストを受けて App Store が自動更新をオフにした場合の両方を含みます。
- サブスクライバーが解約したらアクセスを取り消してもよいですか?
- Google Play では、利用する権利が残っている間は取り消せません。Google は、解約したサブスクライバーは請求期間の終わりまでアクセスを保持し、早期にアクセスを取り消すことは Google Play の定期購入ポリシー違反になるとしています。アクセスの終了時期は expiryTime で判断してください。
出典と参考資料
- Google Play Developer API: purchases.subscriptionsv2
- Google Play Billing: Subscription lifecycle
- Google Play Billing: Real-time developer notifications reference
- Play Console Help: Review in-app subscription performance
- Apple Developer: expirationIntent
- Apple Developer: notificationType
- Apple Developer: Send Consumption Information
- Play Console Help: Updates to refund protection and chargeback cost responsibility
RefundHalt
App Store と Google Play の返金を自動処理
続きを読む
過剰な返金リクエストは返金額以上の損失を招く。両ストアがそれを品質シグナルとして扱うからだ
Apple のガイドライン 5.6.4 は、過剰な返金リクエストをアプリが品質基準を満たしていない兆候として挙げています。Google のデベロッパー販売契約も、返金率を根拠に新規デベロッパーのアプリを削除できると定めています。各ストアの規定、削除の実際のコスト、そしてリスクを避ける方法を解説します。
返金に対応する前に App Store サーバー通知を検証する。webhook URL には誰でも POST できるからです
返金通知は、署名を確認するまではただの HTTPS リクエストにすぎません。App Store サーバー通知と Google Play の RTDN メッセージを検証する方法、各ストアが何に署名しているか、そして偽造された返金や誤って拒否された返金がどれだけの損失になるかを解説します。