# Google Play 订阅跟踪

<Aside type="caution" icon="setting" title="需要开发者协助">
您需要开发团队的帮助来设置此集成。请与他们分享本指南。
</Aside>

## 集成概述

[实时开发者通知 (RTDN)](https://developer.android.com/google/play/billing/rtdn-reference) 是 Google Play 的服务器到服务器服务，每当订阅状态发生变化时，它都会发送实时消息。

通过将 Google Play RTDN 连接到 Pushwoosh，您可以对整个订阅生命周期做出反应，包括购买、续订、取消、账单问题、到期和退款——而无需构建自己的后端基础设施。每当用户的 Google Play 账户中订阅状态发生变化时，Google 都会通知 Pushwoosh，然后 Pushwoosh 会在用户个人资料上触发匹配的 [`PW_Subscription*`](#tracked-events) 事件。

<Aside type="note">
此集成支持 **Android 订阅** (Google Play RTDN)。要跟踪 iOS 订阅，请参阅 [App Store 订阅跟踪](/zh/product/integrations/app-store-subscription-tracking/)。
</Aside>

### 集成类型

**来源：** 实时开发者通知从 Google Play 发送到 Pushwoosh。

### 跟踪的事件

Pushwoosh 将每个受支持的 Google Play 通知映射到一个统一的 `PW_Subscription*` 事件集，因此您可以在订阅生命周期的任何阶段触发营销活动。

| 事件 | 触发时机 |
| ----- | ---------- |
| `PW_SubscriptionStart` | 用户首次购买订阅。 |
| `PW_SubscriptionRenew` | 订阅自动续订一个新的计费周期。 |
| `PW_SubscriptionCancel` | 用户关闭自动续订。订阅在到期前保持有效。 |
| `PW_SubscriptionResume` | 用户在订阅失效前重新启动订阅。 |
| `PW_SubscriptionBillingIssue` | 续订付款失败，订阅进入宽限期。 |
| `PW_SubscriptionRecovered` | 之前失败的续订成功，订阅再次变为有效状态。 |
| `PW_SubscriptionExpired` | 订阅已完全失效，不再有效。 |
| `PW_SubscriptionRefund` | Google Play 撤销订阅（例如，在退款后）。 |

每个事件都带有相同的属性：

- **productID：** 订阅的 Google Play 产品标识符。
- **expiresAt：** 当前付费周期结束的时间，以秒为单位的 Unix 时间戳。当 Google 提供此信息时会包含在内。

<details>

<summary>事件如何映射到实时开发者通知</summary>

对于验证集成的开发者，每个 Pushwoosh 事件对应这些 RTDN `notificationType` 值：

| Pushwoosh 事件 | RTDN `notificationType` |
| --------------- | ----------------------- |
| `PW_SubscriptionStart` | `SUBSCRIPTION_PURCHASED` (4) |
| `PW_SubscriptionRenew` | `SUBSCRIPTION_RENEWED` (2) |
| `PW_SubscriptionCancel` | `SUBSCRIPTION_CANCELED` (3) |
| `PW_SubscriptionResume` | `SUBSCRIPTION_RESTARTED` (7) |
| `PW_SubscriptionBillingIssue` | `SUBSCRIPTION_IN_GRACE_PERIOD` (6) |
| `PW_SubscriptionRecovered` | `SUBSCRIPTION_RECOVERED` (1) |
| `PW_SubscriptionExpired` | `SUBSCRIPTION_EXPIRED` (13) |
| `PW_SubscriptionRefund` | `SUBSCRIPTION_REVOKED` (12) |

其他通知类型，如暂停、价格变动、延迟和暂停，会被确认但不会发布事件。

</details>

### 工作原理

Google Play 通知不携带任何 Pushwoosh 标识符。它只包含一个购买令牌和应用的 `packageName`。因此，您的应用会用 Pushwoosh 需要的标识符标记每次购买，而 Pushwoosh 会在每次通知到达时从购买中读回它。

1.  用户的 Google Play 账户中订阅状态发生变化（购买、续订、取消等）。
2.  Google Play 向 Pushwoosh 的共享主题发布一条 RTDN 消息。
3.  Pushwoosh 读取购买的 `obfuscatedAccountId`，您的应用在购买时已将其设置为 `<AppCode>:<hwid>`。
4.  Pushwoosh 解析 HWID 匹配的设备，找到与之绑定的用户，并为该用户发布匹配的 `PW_Subscription*` 事件。

<Aside type="caution" title="重要">
Google Play 购买与 Pushwoosh 用户之间的匹配依赖于 `obfuscatedAccountId`。如果您的应用在购买时未设置此值，Pushwoosh 会收到通知，但**不会发布任何事件**。它在购买时设置，并且**无法为现有订阅回填**。请参阅[如何在购买时设置账户标识符](#set-the-account-identifier-at-purchase)。
</Aside>

### 使用案例

**赢回流失的订阅者：** 禁用自动续订并不会立即终止访问权限。订阅在付费周期结束前保持有效，这是您赢回用户的窗口。在 `PW_SubscriptionCancel` 事件发生时，启动一个 [Customer Journey](/zh/product/customer-journey/pushwoosh-journey-overview/)，发送一个挽留推送、一封关于他们将失去的功能的[电子邮件](/zh/product/messaging-channels/emails/)，或在访问权限失效前发送一个带有续订折扣的[应用内消息](/zh/product/messaging-channels/in-apps/)。

**引导新订阅者：** 在 `PW_SubscriptionStart` 事件发生时触发一个欢迎系列，帮助用户尽早从他们的计划中获得价值，并为续订做好准备。

**挽救失败的付款：** 当 `PW_SubscriptionBillingIssue` 事件触发时，表示续订付款未成功，订阅正处于宽限期。提示用户在失去访问权限前更新他们的支付方式，并在问题解决后通过 `PW_SubscriptionRecovered` 事件跟进确认。

**重新吸引失效用户：** 在 `PW_SubscriptionExpired` 事件发生时，为已完全流失的订阅者启动一个重新激活活动，提供回头客优惠。

## 设置集成

在开始之前，请确保您有一个已[配置 FCM](/zh/developer/pushwoosh-sdk/android-sdk/firebase-integration/integrate-pushwoosh-android-sdk/) 的 Pushwoosh 应用（推送功能已需要）、一个带有订阅的 Google Play 应用，以及 Play Console 管理员访问权限。

### 在购买时设置账户标识符

Pushwoosh 通过设备的 **HWID** 和您的 **Application Code** 来识别正确的用户。Pushwoosh Android SDK 提供了一个辅助方法 `getSubscriptionAccountId()`，它会返回已格式化为 `<AppCode>:<hwid>` 的值。在启动 Google Play 计费流程时，将其传递给 `BillingFlowParams.setObfuscatedAccountId()`。

<Tabs>
<TabItem label="Kotlin">
```kotlin
val billingParams = BillingFlowParams.newBuilder()
    .setProductDetailsParamsList(productDetailsParamsList)
    // 使用 Pushwoosh 账户标识符 "<AppCode>:<hwid>" 标记购买
    .setObfuscatedAccountId(Pushwoosh.getInstance().subscriptionAccountId)
    .build()

billingClient.launchBillingFlow(activity, billingParams)
```
</TabItem>
<TabItem label="Java">
```java
BillingFlowParams billingParams = BillingFlowParams.newBuilder()
        .setProductDetailsParamsList(productDetailsParamsList)
        // 使用 Pushwoosh 账户标识符 "<AppCode>:<hwid>" 标记购买
        .setObfuscatedAccountId(Pushwoosh.getInstance().getSubscriptionAccountId())
        .build();

billingClient.launchBillingFlow(activity, billingParams);
```
</TabItem>
</Tabs>

<Aside type="note">
在 SDK 初始化后调用 `getSubscriptionAccountId()`。如果 Application Code 或 HWID 尚不可用，它将返回一个空字符串。Google 将混淆的账户 ID 限制为 64 个字符。Pushwoosh 的 `<AppCode>:<hwid>` 值保持在该限制内。
</Aside>

<Aside type="caution">
如果您的应用使用自定义值覆盖了 Pushwoosh HWID，`getSubscriptionAccountId()` 会自动反映它。不要手动构建标识符。请始终使用辅助方法，以确保该值与 Pushwoosh 中设备的 HWID 匹配，否则事件将无法归因。
</Aside>

### 将实时开发者通知指向 Pushwoosh

1.  在 [Google Play Console](https://play.google.com/console/) 中，转到 **变现 → 变现设置**。
2.  找到 **实时开发者通知** 并将 **主题名称** 设置为：

```
projects/pw-playstore-subscriptions/topics/play-rtdn
```

3.  点击 **保存**。发布权限已授予 Google 的通知服务，因此此处无需进行其他配置。

### 授予 Pushwoosh 的服务账户权限

1.  在 Google Play Console 中，转到 **用户和权限 → 邀请新用户**。
2.  输入 Pushwoosh 服务账户电子邮件：

```
play-api@pw-playstore-subscriptions.iam.gserviceaccount.com
```

3.  在 **应用权限** 下，添加您的应用并授予 **查看财务数据、订单和取消调查回复**（以及只读的应用信息权限）。
4.  点击 **保存**。服务账户无需接受邀请。访问权限会立即生效。

### 在 Pushwoosh 中确认事件

Pushwoosh 会在您的项目中首次发生 `PW_Subscription*` 事件时注册该事件，并附带 `productID` 和 `expiresAt` 属性。测试后，打开 **受众 → 事件** 以验证事件是否出现。然后它们就可以用于细分、统计和 Customer Journeys。

### 构建您的营销活动

创建一个 [Customer Journey](/zh/product/customer-journey/pushwoosh-journey-overview/)，其[基于触发器的入口](/zh/product/customer-journey/journey-elements/entry-elements/trigger-based-entry/) 设置为任何 `PW_Subscription*` 事件，例如用于赢回的 `PW_SubscriptionCancel` 或用于引导的 `PW_SubscriptionStart`，然后添加您想要发送的消息。

## 测试

要端到端地验证集成：

1.  在 Google Play Console 中，打开 **变现设置** 并点击 **发送测试通知**。它应该会报告成功，确认主题已正确连接。
2.  按照上述说明设置账户标识符进行订阅购买（这将触发 `PW_SubscriptionStart`），然后从 **Play Store → 订阅 → 取消** 中取消它（这将触发 `PW_SubscriptionCancel`）。
3.  在 Pushwoosh 控制面板中，打开用户个人资料并转到[事件历史记录](/zh/product/audience-data-and-segmentation/user-explorer/#events-history-tab)。
4.  确认事件在片刻之后出现。