能否通过 Google Billing API 获取订阅试用期?
结论
可以。IInAppBillingService.getSkuDetails() 返回的订阅 SKU JSON 使用以下字段表示试用期和计费周期:
freeTrialPeriod:免费试用期subscriptionPeriod:订阅计费周期
正确的字段名是 freeTrialPeriod 和 subscriptionPeriod,不是 trialPeriod 和 billingPeriod。字段值采用 ISO 8601 时长格式,例如 P7D 表示 7 天,P1M 表示 1 个月。
获取方式
调用 getSkuDetails() 时,将商品类型设置为 "subs",再解析返回结果中 DETAILS_LIST 里的 JSON 字符串:
ArrayList<String> skuList = new ArrayList<>();
skuList.add("monthly_subscription");
Bundle querySkus = new Bundle();
querySkus.putStringArrayList("ITEM_ID_LIST", skuList);
Bundle skuDetails = billingService.getSkuDetails(
3,
context.getPackageName(),
"subs",
querySkus
);
int responseCode = skuDetails.getInt("RESPONSE_CODE");
if (responseCode == 0) {
ArrayList<String> detailsList =
skuDetails.getStringArrayList("DETAILS_LIST");
if (detailsList != null) {
for (String detail : detailsList) {
JSONObject product = new JSONObject(detail);
String productId = product.getString("productId");
String price = product.getString("price");
String subscriptionPeriod =
product.optString("subscriptionPeriod", null);
String freeTrialPeriod =
product.optString("freeTrialPeriod", null);
// 使用 productId、price、subscriptionPeriod 和 freeTrialPeriod
}
}
}
订阅详情的 JSON 通常类似下面这样:
{
"productId": "monthly_subscription",
"type": "subs",
"price": "¥18.00",
"price_amount_micros": 18000000,
"price_currency_code": "CNY",
"title": "月度订阅",
"description": "按月自动续订",
"subscriptionPeriod": "P1M",
"freeTrialPeriod": "P7D"
}
字段含义
subscriptionPeriod 表示正常续订周期,常见取值有:
P1W:1 周P1M:1 个月P3M:3 个月P1Y:1 年
freeTrialPeriod 表示免费试用时长,例如:
P3D:3 天P7D:7 天P1M:1 个月
如果订阅没有配置免费试用,JSON 中通常不会包含 freeTrialPeriod。解析时应使用 optString(),或者先通过 has() 判断字段是否存在,避免直接调用 getString() 引发异常。
注意事项
IInAppBillingService 是旧版 Google Play Billing 接口。新应用应使用 Google Play Billing Library,不宜继续基于旧接口开发。新版订阅模型引入了 base plan、offer 和多个定价阶段等概念,因此不能再假定一个商品只有统一的试用期或计费周期。
使用新版 Billing Library 时,需要从符合条件的 ProductDetails.SubscriptionOfferDetails 中取得报价,再读取相应的 PricingPhase:
for (ProductDetails.SubscriptionOfferDetails offer :
productDetails.getSubscriptionOfferDetails()) {
for (ProductDetails.PricingPhase phase :
offer.getPricingPhases().getPricingPhaseList()) {
String billingPeriod = phase.getBillingPeriod();
int recurrenceMode = phase.getRecurrenceMode();
long priceAmountMicros = phase.getPriceAmountMicros();
boolean isFreeTrial = priceAmountMicros == 0;
}
}
判断免费试用时,不能只看计费周期,还要结合 priceAmountMicros == 0、报价资格和定价阶段的顺序。
客户端返回的是当前用户、地区和商店环境下可以展示的商品报价。订阅权益、购买状态和到期时间应通过服务端验证购买令牌,不能只根据客户端商品详情判断用户是否处于试用期。
备注:内容仅供参考。
