Subscription with add-ons

Subscription with add-ons lets you bundle multiple subscription products together that can be purchased, billed and managed together. Your existing product catalog subscriptions can be seamlessly offered as add-ons without any upfront specification or additional configuration. You can launch a purchase flow with multiple existing subscription products, and sell them as add-ons.

Considerations

Consider the following points when using the subscription with add-ons feature:

  • Subscription with add-ons is only supported for auto renewing base plans.

  • All items in the purchase must have the same recurring billing period. For example, you can't have an annually billed subscription with monthly billed add-ons.

  • You can have a maximum of 50 items in a subscription with add-ons purchase.

  • This feature isn't available in the India (IN) and South Korea (KR) regions.

Integrate with Play Billing Library

This section describes how to integrate the subscription with add-ons feature with the Play Billing Library (PBL). It assumes that you are familiar with the initial PBL integration steps such as, adding the PBL dependency to your app, initializing the BillingClient, and connecting to Google Play. This section focuses on the PBL integration aspects that are specific to subscription with add-ons.

Launch a purchase flow

To launch a purchase flow for a subscription with add-ons, do the following steps:

  1. Fetch all your subscription items by using the BillingClient.queryProductDetailsAsync method.

  2. Set the ProductDetailsParams object for each item.

    The item represented by the ProductDetailsParams object, specifies both the ProductDetails indicating the subscription item, and an offerToken selecting a specific subscription base plan or offer.

  3. Specify the item details in the BillingFlowParams.Builder.setProductDetailsParamsList method. The BillingFlowParams class specifies the details of a purchase flow.

    The following sample shows how to launch the billing flow for a subscription purchase with multiple items:

    Java

       BillingClient billingClient = ;
    
        // ProductDetails obtained from queryProductDetailsAsync().
        ProductDetailsParams productDetails1 = ...;
        ProductDetailsParams productDetails2 = ...;
        ArrayList productDetailsList = new ArrayList<>();
        productDetailsList.add(productDetails1);
        productDetailsList.add(productDetails2);
    
        BillingFlowParams billingFlowParams =
            BillingFlowParams.newBuilder()
               .setProductDetailsParamsList(productDetailsList)
               .build();
        billingClient.launchBillingFlow(billingFlowParams);

Rules applicable for items in the purchase

  • To ensure add-on renewal dates eventually align with the base item, Google Play may insert a prorated charge after any trial or intro pricing phases.
  • Offer eligibility will be evaluated separately for each item.

Process purchases

Processing subscription with add-ons is the same as processing of single-item purchases as described in Integrate the Google Play Billing Library into your app. The only difference is that the user can receive multiple entitlements with a single purchase. A purchase of subscription with add-ons returns multiple items which can be retrieved using Purchase.getProducts() in the Google Play Billing Library, and then the lineItems list in purchases.subscriptionsv2.get of the Google Play Developer API.

Modify subscriptions with add-ons

Any changes to your subscription with add-ons, results in an upgrade or a downgrade. For more information, see upgrade or downgrade subscriptions.

To change or restore an existing purchase of subscription with add-ons in your app, you must call the launchBillingFlow API with additional parameters, and ensure the following:

  • Always call setOldPurchaseToken with the purchase token of the current subscription purchase.
  • To upgrade, downgrade, or crossgrade the base item, call setSubscriptionReplacementMode to specify how the plan change should be handled between the base items of the old, and the new purchase of subscription with add-ons. Otherwise, there is no need to set this parameter.
  • When the base item isn't changed, you can still call setSubscriptionReplacementMode to apply a specific proration behavior. For the applicable rules in this case, see Resubscribe or switch plans within the same subscription.
  • New add-ons will apply immediately with a prorated charge to align the next renewal date with the base item in the subscription.
  • Removed add-ons will expire at the end of their current billing periods.
  • When launching the billing flow, you will need to specify all active items in the subscription with add-ons excluding those to be removed, along with any new add-ons.

The following sample shows how to call the launchBillingFlow API when changing an existing purchase of subscription with add-ons:

Java

BillingClient billingClient = ;

int replacementMode =;

// ProductDetails obtained from queryProductDetailsAsync().
ProductDetailsParams productDetails1 = ...;
ProductDetailsParams productDetails2 = ...;
ProductDetailsParams productDetails3 = ...;

ArrayList newProductDetailsList = new ArrayList<>();
newProductDetailsList.add(productDetails1);
newProductDetailsList.add(productDetails1);
newProductDetailsList.add(productDetails1);

BillingFlowParams billingFlowParams =
    BillingFlowParams.newBuilder()
        .setSubscriptionUpdateParams(
          SubscriptionUpdateParams.newBuilder()
              .setOldPurchaseToken(purchaseTokenOfExistingSubscription)
              // No need to set if change does not affect the base item.
             .setSubscriptionReplacementMode(replacementMode)
             .build())
        .setProductDetailsParamsList(productDetailsList)
        .build();

billingClient.launchBillingFlow(billingFlowParams);

Subscription modification scenarios

The following table lists the various modification scenarios for subscription with add-ons, and the corresponding behaviour.

Existing items Modified items Do you need to set the replacement mode? Behavior
A (base item), B A (base item) No Item B is scheduled for deferred removal.
A A (base item), B No Item B is added immediately with a prorated charge.
A (base item), B A (base item), C No
  • B is scheduled for deferred removal.
  • C is added immediately with a prorated charge.
A (base item), B B (base item) No A is scheduled for a deferred removal.
A (base item), B C (base item) Yes
A (base item), B C (base item), B Yes The replacement for A -> C depends on setSubscriptionReplacementMode.
A (base item), B C (base item), D Yes
  • The replacement for A -> C depends on setSubscriptionReplacementMode.
  • B is scheduled for deferred removal.
  • D is added immediately with a prorated charge.

Real-time developer notifications

The subscriptionId field isn't provided in RTDN for purchases of subscription with add-ons, which contain multiple item entitlements. Instead, your can use the Play Developer APIs to get the purchase and see the associated item entitlements.

Price changes for existing subscribers

Changing subscription prices for existing subscribers of a subscription with add-ons purchase is similar to changing the subscription prices of single-item subscriptions as described in Change subscription prices. However, there are some limitations and functional differences as described in this section.

End a legacy price cohort

Ending a legacy cohort also impacts subscription with add-on purchases. The following rules apply:

  • All outstanding opt-in price increases should have the same renewal time with the new price. If an item in a subscription with add-ons purchase has an opt-in price increase which is not yet confirmed by the user, any new opt-in price increase for other items in the purchase will be ignored unless it results in the same renewal time of new price application as the existing price increase in OUTSTANDING state. Once the user confirms the price increase any newer price changes would be registered. And users can only accept all unconfirmed opt-in price increases at once.

    Example:

    • Consider a subscription with add-ons (items A and B), renews on 7th of every month.
    • Item A has an ongoing price migration from $7 to $10, and the price increase is expected to be applicable on July 7.
    • A new price migration from $5 to $6, starts for item B on June 2. Since the opt-in price increase starts 37 days after migration, for earliest price increase for item B will be on Aug 7.

    In this scenario, until the user accepts the price change for item A (until it is in CONFIRMED state), price change for item B isn't registered for this subscription purchase, and SubscriptionPurchaseV2 doesn't return price change details for item B. After the user confirms the price change for item A, the price change of item B starts. The user receives the item B opt-in price increase only after accepting the opt-in increase for item A.

  • Google Play's email contains a list of all the items with price increases or decreases taking effect on the same day.

Cancel subscription with add-ons

Users can cancel the entire purchase of a subscription with add-ons on Play Subscription Center, and you can only cancel the entire purchase of a subscription with add-ons by using the Google Play Developer API.

When a subscription purchase is canceled without being revoked, none of the items in the purchase will auto-renew, but the user will continue to have access to the entitled items until the corresponding billing periods end.

Revoke and refund subscriptions with add-ons

The following are some of the guidelines for revoking and refunding subscriptions:

  • Use Play Console to issue an amount based refund for a specific Order without revoking access to the subscription.

  • Call orders.refund to fully refund specific subscription payments the user has made without revoking access to the subscription.

  • Call purchases.subscriptionsv2.revoke to immediately revoke access to all subscription items. With this API, you can:

    • Revoke access to all the items and provide a prorated refund.

    • When revoking a subscription with add-ons using prorated refunds, a refund will be issued for the latest order of each item with a prorated amount based on the time remaining until the next renewal.

    • Revoke access for all the items and provide a FullRefund.

    • Revoke individual item's access with full refund on the item.

Revoke individual item in a subscription with add-ons

To revoke individual subscription items in a subscription with add-ons without revoking the entire purchase, call purchases.subscriptionsv2.revoke with ItemBasedRefund field set in the RevocationContext. The productId of the item that should be revoked and refunded can be set in the ItemBasedRefund field.

The ItemBasedRefund field can be set for purchases with one or more auto-renewing subscription items.

  • If there are still active items remaining in the subscription purchase after revoking the item specified in ItemBasedRefund, only the item will be revoked, and fully refunded without interrupting the subscription status.
  • If there are no active items remaining in the subscription purchase after revoking the item specified in ItemBasedRefund, the item is revoked, fully refunded, and the subscription is canceled.

Considerations

  • When using the ItemBasedRefund only one item can be revoked at a time. The request can be called multiple times if different items need to be revoked.
  • When the subscription purchase is in any of the payment declined states, or the item specified in ItemBasedRefund is not owned or expired, the item turn down is blocked.
  • Item turn down isn't supported in prepaid subscription.

Item expiration during payment decline

For a purchase of subscription with add-ons, certain renewals may only need to extend a subset of item entitlements, without affecting items with a future expiry date.

Regardless of which items are involved in a renewal, if the renewal payment is declined, the overall subscription purchase will enter grace period and account hold as described in the following documentation.

Recovery period selection

As grace period itself still grants the user entitlement, upon a purchase of subscription with add-ons, renewal payment is declined, the item with the minimum grace period over all active items is selected, and its grace period and account hold period as the recovery period is applied for this renewal.

Active items includes items that were active in the purchase of a subscription with add-ons just prior to the renewal attempt, excludes any newly added items (which won't be entitled until after recovery), and excludes any items that are no longer active due to removal or turndown.

The account hold setting of the item with the minimum grace period selected is applied. If there are more than one items with the minimum grace period, but different account hold periods, the longest account hold period is applied.

Grace period

When a subscription renewal payment is declined, the subscription purchase will enter grace period state. During the grace period, the user will continue to have access to all active items from the previous renewal period. After the grace period, if the payment method hasn't been fixed, the entire subscription purchase goes into account hold. If any other items reach their renewal date during grace period, a new charge attempt will be initiated for those items once the subscription recovers from payment decline.

Account hold

While the subscription purchase is in account hold, access to all subscription items is suspended until payment recovers.

If the subscription in account hold is recovered, the subscription purchase continues existing as is. If the subscription is not recovered, the items in payment decline will expire, and access to the other items will be resumed for the remainder of their billing periods.

Example:

  • A user has a subscription My Base Plan renewing at the 1st of every month, then on Aug 15, adds a $10 per month Add on plan with a seven-day free trial. Neither of the items have grace period set, and they both have 30-day account hold period.

  • On the Aug 22, the user is charged $2.90 (10*9/31) to prorate until Aug 31, but the user's payment method expires before then, and the subscription falls into payment decline on Aug 22.

When the subscription enters account hold due to payment decline, the user does not have access to any of the items in the subscription with add-ons. The remaining time for the items that are not being renewed will be given back to users when the subscription exits account hold, either because payment has been recovered or canceled.

In the previous example, a subscription enters account hold on Aug 22.

  • If the account is recovered on Aug 25, before the broader renewal date on Sep 1, the user regains access to both My Base Plan, and Add on plan the same day. Next billing date is changed to Sep 4.

  • If the account isn't recovered after 30 days, the subscription is canceled on Sep 21 and the user loses access to the Add on plan, and resume access to My Base Plan until Sep 30.

In this example, you must get the updated expiryTime for ALL items in the subscription with add-ons, as some items may resume their entitlement after the grace period and account hold.

Financial reporting and reconciliation

Use the Earnings report to reconcile your active subscriptions with transactions on Play. Each transaction line item has an order ID. With purchases representing several items, the Earnings and Estimated sales reports will include separate rows for each transaction such as charge, fee, tax, and refund, for each item involved.

For dashboards in the Play Console:

  • The revenue statistics presented in the Financial reporting section of the console are broken down by items.

  • Order management reflects purchase of subscription with add-ons, and show itemized lists of what was purchased. From order management, you may revoke, cancel or fully refund a user's purchase.