package com.solderbyte.openfit;
import android.app.Activity;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.util.Log;
import com.android.vending.billing.IInAppBillingService;
import com.solderbyte.openfit.util.OpenFitIntent;
import org.json.JSONObject;
import java.util.ArrayList;
public class Billing {
private static final String LOG_TAG = "OpenFit:Billing";
public static final int BILLING_REQ = 1001;
public static final int BILLING_RESPONSE_RESULT_OK = 0;
public static final int BILLING_RESPONSE_RESULT_USER_CANCELED = 1;
public static final int BILLING_RESPONSE_RESULT_SERVICE_UNAVAILABLE = 2;
public static final int BILLING_RESPONSE_RESULT_BILLING_UNAVAILABLE = 3;
public static final int BILLING_RESPONSE_RESULT_ITEM_UNAVAILABLE = 4;
public static final int BILLING_RESPONSE_RESULT_DEVELOPER_ERROR = 5;
public static final int BILLING_RESPONSE_RESULT_ERROR = 6;
public static final int BILLING_RESPONSE_RESULT_ITEM_ALREADY_OWNED = 7;
public static final int BILLING_RESPONSE_RESULT_ITEM_NOT_OWNED = 8;
public static final int IABHELPER_ERROR_BASE = -1000;
public static final int IABHELPER_REMOTE_EXCEPTION = -1001;
public static final int IABHELPER_BAD_RESPONSE = -1002;
public static final int IABHELPER_VERIFICATION_FAILED = -1003;
public static final int IABHELPER_SEND_INTENT_FAILED = -1004;
public static final int IABHELPER_USER_CANCELLED = -1005;
public static final int IABHELPER_UNKNOWN_PURCHASE_RESPONSE = -1006;
public static final int IABHELPER_MISSING_TOKEN = -1007;
public static final int IABHELPER_UNKNOWN_ERROR = -1008;
public static final int IABHELPER_SUBSCRIPTIONS_NOT_AVAILABLE = -1009;
public static final int IABHELPER_INVALID_CONSUMPTION = -1010;
public static final int IABHELPER_SUBSCRIPTION_UPDATE_NOT_AVAILABLE = -1011;
public static final String RESPONSE_CODE = "RESPONSE_CODE";
public static final String RESPONSE_GET_SKU_DETAILS_LIST = "DETAILS_LIST";
public static final String RESPONSE_BUY_INTENT = "BUY_INTENT";
public static final String RESPONSE_INAPP_PURCHASE_DATA = "INAPP_PURCHASE_DATA";
public static final String RESPONSE_INAPP_SIGNATURE = "INAPP_DATA_SIGNATURE";
public static final String RESPONSE_INAPP_ITEM_LIST = "INAPP_PURCHASE_ITEM_LIST";
public static final String RESPONSE_INAPP_PURCHASE_DATA_LIST = "INAPP_PURCHASE_DATA_LIST";
public static final String RESPONSE_INAPP_SIGNATURE_LIST = "INAPP_DATA_SIGNATURE_LIST";
public static final String INAPP_CONTINUATION_TOKEN = "INAPP_CONTINUATION_TOKEN";
public static final int PURCHASE_STATE_PURCHASED = 0;
public static final int PURCHASE_STATE_CANCELLED = 1;
public static final int PURCHASE_STATE_REFUNDED = 2;
public static final String ITEM_TYPE_INAPP = "inapp";
public static final String GET_SKU_DETAILS_ITEM_LIST = "ITEM_ID_LIST";
public static final String GET_SKU_DETAILS_ITEM_TYPE_LIST = "ITEM_TYPE_LIST";
public static final String PREMIUM = "premium";
private static IInAppBillingService billingService = null;
private static PendingIntent buyIntent = null;
private static boolean isPremium = false;
public static String PREMIUM_PRICE = null;
public static String PREMIUM_SKU = null;
private static Context context = null;
private static Activity activity = null;
public void setContext(Context cntxt) {
Log.d(LOG_TAG, "Setting context");
context = cntxt;
}
public void setService(IInAppBillingService service) {
Log.d(LOG_TAG, "Setting service");
billingService = service;
}
public void setActivity(Activity actvty) {
activity = actvty;
}
public Bundle getQueryBundle() {
ArrayList<String> skuList = new ArrayList<String> ();
skuList.add(PREMIUM);
Bundle querySkus = new Bundle();
querySkus.putStringArrayList(GET_SKU_DETAILS_ITEM_LIST, skuList);
return querySkus;
}
public PendingIntent getBuyIntent() {
return buyIntent;
}
public void getSkuDetails() {
if(billingService != null && context != null) {
new getPremiumTask().execute();
}
else {
Log.d(LOG_TAG, "Cannot getSkuDetails. billingService or context is null");
}
}
public void verifyPremium() {
if(billingService != null && context != null) {
new verifyPremiumTask().execute();
}
else {
Log.d(LOG_TAG, "Cannot getPurchasedPremium. billingService or context is null");
}
}
public void purchasePremium() {
if(billingService != null && context != null || activity != null) {
new purchasePremiumTask().execute();
}
else {
Log.d(LOG_TAG, "Cannot purchasePremium. billingService, context, or activity is null");
}
}
public int getResponseCodeFromBundle(Bundle b) {
Object o = b.get(RESPONSE_CODE);
if(o == null) {
Log.d(LOG_TAG, "Bundle with null response code, assuming OK (known issue)");
return BILLING_RESPONSE_RESULT_OK;
}
else if(o instanceof Integer) {
return ((Integer)o).intValue();
}
else if(o instanceof Long) {
return (int)((Long)o).longValue();
}
else {
Log.d(LOG_TAG, "Unexpected type for bundle response code" + o.getClass().getName());
throw new RuntimeException("Unexpected type for bundle response code: " + o.getClass().getName());
}
}
private class getPremiumTask extends AsyncTask<Void, Void, Void> {
protected Void doInBackground(Void... params) {
Log.d(LOG_TAG, "getPremiumTask:");
Bundle skuDetails;
ArrayList<String> skuList = new ArrayList<String> ();
skuList.add(PREMIUM);
Bundle querySkus = new Bundle();
querySkus.putStringArrayList(GET_SKU_DETAILS_ITEM_LIST, skuList);
try {
skuDetails = billingService.getSkuDetails(3, context.getPackageName(), ITEM_TYPE_INAPP, querySkus);
int response = skuDetails.getInt(RESPONSE_CODE);
if(response == BILLING_RESPONSE_RESULT_OK) {
ArrayList<String> responseList = skuDetails.getStringArrayList(RESPONSE_GET_SKU_DETAILS_LIST);
for(String thisResponse : responseList) {
JSONObject object = new JSONObject(thisResponse);
PREMIUM_SKU = object.getString("productId");
PREMIUM_PRICE = object.getString("price");
Log.d(LOG_TAG, "ProductId: " + PREMIUM_SKU);
}
}
}
catch(Exception e) {
Log.e(LOG_TAG, "getPremiumTask failed: " + e.getMessage());
}
return null;
}
}
private class purchasePremiumTask extends AsyncTask<Void, Void, Void> {
protected Void doInBackground(Void... params) {
Log.d(LOG_TAG, "purchasePremiumTask: " + PREMIUM_SKU);
Bundle buyIntentBundle;
try {
buyIntentBundle = billingService.getBuyIntent(3, context.getPackageName(), PREMIUM_SKU, ITEM_TYPE_INAPP, null);
Log.d(LOG_TAG, "buyIntentBundle: " + buyIntentBundle);
buyIntent = buyIntentBundle.getParcelable(RESPONSE_BUY_INTENT);
activity.startIntentSenderForResult(buyIntent.getIntentSender(), BILLING_REQ, new Intent(), 0, 0, 0);
}
catch(Exception e) {
Log.e(LOG_TAG, "purchasePremiumTask failed: " + e.getMessage());
}
return null;
}
}
private class verifyPremiumTask extends AsyncTask<Void, Void, Void> {
protected Void doInBackground(Void... params) {
Log.d(LOG_TAG, "verifyPremiumTask: ");
Bundle ownedItems;
try {
ownedItems = billingService.getPurchases(3, context.getPackageName(), ITEM_TYPE_INAPP, null);
int response = ownedItems.getInt(RESPONSE_CODE);
if(response == BILLING_RESPONSE_RESULT_OK) {
ArrayList<String> purchaseDataList = ownedItems.getStringArrayList(RESPONSE_INAPP_PURCHASE_DATA_LIST);
ArrayList<String> signatureList = ownedItems.getStringArrayList(RESPONSE_INAPP_SIGNATURE_LIST);
String continuationToken = ownedItems.getString(INAPP_CONTINUATION_TOKEN);
for(int i = 0; i < purchaseDataList.size(); ++i) {
String purchaseData = purchaseDataList.get(i);
//String signature = signatureList.get(i);
JSONObject object = new JSONObject(purchaseData);
String packageName = object.getString("packageName");
String sku = object.getString("productId");
String purchaseTime = object.getString("purchaseTime");
String purchaseState = object.getString("purchaseState");
Intent msg = new Intent(OpenFitIntent.INTENT_BILLING);
msg.putExtra(OpenFitIntent.INTENT_EXTRA_MSG, OpenFitIntent.INTENT_BILLING_VERIFIED);
if(sku.equals(PREMIUM_SKU) && packageName.equals(context.getPackageName())) {
Log.d(LOG_TAG, "Premium purchase found");
Log.d(LOG_TAG, "state: " + purchaseState);
int pState = Integer.parseInt(purchaseState);
if(pState == PURCHASE_STATE_PURCHASED || pState == PURCHASE_STATE_REFUNDED) {
Log.d(LOG_TAG, "purchase verified");
isPremium = true;
msg.putExtra(OpenFitIntent.INTENT_EXTRA_DATA, true);
}
if(pState == PURCHASE_STATE_CANCELLED) {
Log.d(LOG_TAG, "purchase cancelled");
isPremium = false;
}
}
else {
isPremium = false;
msg.putExtra(OpenFitIntent.INTENT_EXTRA_DATA, false);
Log.d(LOG_TAG, "Premium purchase not found");
}
Log.d(LOG_TAG, "Sending context");
context.sendBroadcast(msg);
}
}
else {
Log.d(LOG_TAG, "Premium response not ok");
}
}
catch(Exception e) {
Log.e(LOG_TAG, "verifyPremiumTask failed: " + e.getMessage());
}
return null;
}
}
}