📜 ⬆️ ⬇️

Children's launcher 2.x and a single premium account



What's new


After the publication of the first version of the application, we received a large number of reviews. By putting together the wishes of users and our own ideas, we began work on the second version. After two months of hard work, the updated Children's Launcher and Parental Control applications are available for download on Google Play.

Six-digit pin

Pleasantly surprised by young users of the application, who easily picked up a PIN code. I had to increase it to 6 characters.
')
The ability to change the wallpaper

One of the most frequent requests was to include the ability to change the wallpaper. We went a little further and decided to provide this opportunity not only to parents, but also to children - now we can make the child install the wallpaper himself. If necessary, this option is disabled.

Schedule, weekdays and weekends

What if a child plays at night or during lessons? How to set the time limits so that you can play longer on Sunday than on Monday? Obviously, an extended time limit setting is required with creating your own schedule.
In the new version, you can set the time period when you can run an application or category of applications. For example: applications of the “Games” category can be run from 15:00 to 20:00.

It also became possible to set time limits for weekdays and weekends separately, and the user himself determines which days of the week are weekends: Saturday and Sunday, or only Sunday, or some other days.

In addition to individual applications and categories, you can configure time limits for the entire device. For example: the device can be started on weekdays from 3:00 pm to 8:00 pm, the allowed working time is 2 hours; on weekends - from 13:00 to 21:00, the allowed working time is 4 hours. In this case, the allowed running time is the cumulative running time of any applications. Upon expiration of the allowed time of work, or outside the permitted time interval, it is prohibited to launch any applications, except for calls and SMS.

This feature is only available with a premium account.

The history of the child

If before it was possible to see the current location of the child, now the application shows the history of movements in the last 12 hours. As before, the coordinates are updated every 15 minutes, the point is fixed on the map. Information about the movements of the child can be useful even without using the Parental Control application — for example, parents can take the child’s device in the “Tracking” section to see where and at what time it was located.

This feature is also premium. Tracking the current location of the child is still free.



Premium subscription


To monetize the application, we decided to use a premium account that opens functions that are inaccessible to the simple user. Premium functionality purchased through subscriptions in Google Play In-App Billing. Consider briefly what constitutes a subscription, and what are its limitations.

Introduction

When a subscription is made, the user periodically deducts a certain amount of money - the price of the subscription. It is limited to a minimum price of 30 rubles and a maximum of 6,000 rubles and the same size in dollar terms. Google allows you to set only 2 types of frequency: monthly subscription and annual. It is possible to add a trial period from 7 to 999 days. As for the cancellation of the subscription, the user can cancel it at any time, but the money for the current period will not be returned to him. After canceling the subscription, the user can use all the premium features until the end of the paid period. When you delete an application with a subscription, the subscription is not canceled, but Google Play notifies you that the application was deleted, but you will still be withdrawing money until you cancel the subscription.

Single premium for different applications

In our case, the standard subscription option offered by Google is not enough, because we have two applications, and when buying a premium in one of them, it should appear in the second. In addition, children tend not to be in a single copy, and the user may have several children's devices on which the Children's Launcher is installed. In this case, the premium should be included on all children's devices at once. It binds all these devices to each other Google account, respectively, the premium must be tied to the account under which the user is authorized in the application.

Another criterion for developing a mechanism for buying a premium was the ability to give users premiums for free (for advertising purposes or for helping to create and develop a project). Now, when launching a new version, we want to distribute a premium to some of our users who helped to identify bugs.

Implementation

To purchase a subscription on a client, we used classes from TrivialDrive. TrivialDrive is a classic in-app mobile sample application that comes with the Google Play Billing Library. We will not describe in detail how and what to do for in-app purchases, but the part we touch will be in terms of utility classes from TrivialDrive.

Authorization check

The first time we check if the premium is active during authorization, and if it is active and its time has not expired, then we turn on the premium functionality on the client. This is the easiest option.

Buying a Premium Subscription

Another option is that the user does not have a premium when authorizing.



Step 1.
When you click on the “Buy Premium” button, a request is sent to the server to find out if the premium was purchased on another device of the same user. If the premium was purchased earlier and has not ended, turn on the premium functionality on the client.

Step 2.
If the premium was not purchased, then start the process of buying a subscription through IabHelper.launchPurchaseFlow. In addition to other parameters, payload is passed to the function. Payload is a string defined by the developer and uniquely associating the user with this purchase. We pass the user account name to this parameter.

Then google services take over the management and upon completion of the purchase, successful or not, our callback causes. Now we will consider a lucky coincidence of circumstances when the user has not bought a premium before and no errors have occurred. In this case, the Purchase object is returned to the callback, which contains the required fields: payload, purchaseTime, productId, orderId, and purchaseToken. All this data, as well as the device ID, we send to the server part (Step 3) to verify the purchase.

Step 3.
The server, represented by Parse, uses the Google Play Developer API to get data about the subscription just purchased. To use the Google Play Developer API, you need to create an application in the Google Cloud Console, enable the Google Play Developer API and get an access_token (which, unfortunately, is not permanent, but more on that later). You can find out the subscription information by sending a GET request to the https address of the form: " www.googleapis.com/androidpublisher/v1/applications {packageName} / subscriptions / {productId} / purchases / {purchaseToken}? AccessToken = {accessToken}"
In response, JSON comes with information about the dates of the beginning and end of the subscription, as well as whether the subscription will automatically last when the time runs out (apparently, if the user canceled the subscription or not - we did not need this field). Documentation for requests is small, because there is nothing special to write there - developers.google.com/android-publisher/v1/purchases

If the API returns the correct data and the end time of the subscription is more than the current time, then the user paid for the premium, and we can enable it with premium functionality. We only need to remember the subscription end time to know when to check the subscription next time.

Step 4.
Subscription information is returned to the device. We consider the situation when no problems arise, and the user actually bought the subscription, and its validity period could not end, i.e. The client receives data about the activated premium account and the expiry date.

You can use the Children's Launcher in offline mode, which means you need to be able to verify a premium account without the Internet. To do this, we store data about the premium account (expiration date, subscription ID, etc.) locally in the SharedPreference in an encrypted form. Check the status of the premium account every time you enter parent mode. If there is Internet, then after a successful local verification, we ask Parse for confirmation; If Parse confirms a premium account, then we overwrite the local data (it is possible that the subscription end time has been updated). If there is no connection to the network, then we do nothing and consider premium as active, because local verification confirms the purchase of a premium account. The fact of renewing a subscription without connecting to the network cannot be verified, therefore, even if the locally stored subscription time has expired, the premium account remains activated.

Possible situations



Update token.
The third step uses the application in the Google Cloud Console with the included Google Play Developer API. About creating an application and getting tokens (access_token and refresh_token) you can read here - developers.google.com/android-publisher/authorization . Let me just say that access_token is used for all API calls, but it is not eternal and dies pretty quickly. As soon as the access_token time expires, the API will return a 401 error, and using refresh_token we will be able to get a new access_token. Those. step 3 may take a bit of a stretch if the access_token expires.

Premium subscription renewal.
At the stage of authorization or at the stage of checking the premium, a situation may arise that the user activated the premium earlier, but the subscription end time saved on the server has passed; in this case, the server again calls on the Google Play Developer API to obtain new subscription data — see if the subscription has been extended or not. If the subscription is extended, the server overwrites the subscription’s expiration time and sends it to the device. If the subscription is canceled, the server also reports this to the device, and the device overwrites the subscription information in the SharedPreference.

Subscription already purchased.
At the stage of buying a subscription, it may arise that the user has already purchased this subscription. Tell us about this Google Services through a callback passed to the IabHelper.launchPurchaseFlow function. An error with the code BILLING_RESPONSE_RESULT_ITEM_ALREADY_OWNED will return to this callback, in which case you will need to contact Google Services again for a list of all purchased internal purchases / subscriptions. This is done through the IabHelper.queryInventoryAsync function, to which the next callback is passed. From the received list of all made purchases (Inventory) we get the subscription we need by the identifier and we look at its payload; if the payload does not match the current user’s account (and there should not be any other situations, if our mechanism works correctly), then we inform the user that the subscription has already been purchased from him, but for a different account. If, however, the payload coincides with the current user account (no, well, what if?), Then in the google service we perform all the same actions as with a regular purchase, but with Purchase, which had previously returned to the callback.

What's next



Further more. We are waiting for your comments and suggestions. Thank.

PS Article is written in conjunction with belozerow habraiser

Source: https://habr.com/ru/post/203116/


All Articles