API de facturación v3 IabHelper NullPointerException
Editar 4/15: La captura de nullpointer en IabHelper parece haber detenido este problema. Ya no veo las excepciones lanzadas, voy a aceptar esto como una respuesta.
Editar 4/04: Un poco de una inmersión más profunda. Existen bloques catch que manejan RemoteExceptions y JSONExceptions para el método queryPurchases, pero no NullPointerException. Lo que voy a tratar es incluir el manejo de excepciones NullPointer para que IabHelper se ve así al intentar querySkuDetails:
- IabResult: Error al actualizar el inventario (consultar elementos propios)
- Reembolso a la compra de aplicaciones en Android
- Facturación en la aplicación de Google Play v3 getSkuDetails () devuelve los resultados almacenados en caché incluso si se modificaron los precios de la IAP
- Determinar la fecha de compra original de una aplicación de Android
- Cómo convertir una aplicación de Android de un modelo de pago gratuito a un desbloqueo de pagos en la aplicación
catch (NullPointerException e) { throw new IabException(IABHELPER_UNKNOWN_ERROR, "NullPointer while refreshing inventory.", e); }
Acabo de presentar un error en esto:
Https://code.google.com/p/marketbilling/issues/detail?id=114
Corregir 3/25: bien, todavía recibir este choque … ahora sucede mientras que intenta conseguir un contexto en la línea 3 del extracto siguiente de IabHelper:
int queryPurchases(Inventory inv, String itemType) throws JSONException, RemoteException { logDebug("Querying owned items, item type: " + itemType); logDebug("Package name: " + mContext.getPackageName());
Esto es frustrante porque en mi manifiesto siempre utilizo el nombre completo de la ruta de acceso de mi aplicación para "nombre".
Ejemplo "com.myappname.blah.ClassName"
También he intentado pasar esto, MyClass.this, getApplicationContext () a mHelper. Sin embargo todos ellos producen los mismos resultados NullPointer aleatoriamente de dispositivos en la naturaleza. También intenté name = ". MyClass" en el manifiesto. Esto es lo que parece actualmente:
mHelper = new IabHelper(MyClass.this, myKey);
Editar 3/18/13: Todavía estoy recibiendo excepciones, incluso con la nueva versión de IabHelper desplegada el 3/17.
Estoy empezando a ver un patrón aquí, que los accidentes son todos al tratar de obtener un contexto al ejecutar mContext.getPackageName (). Tengo curiosidad de saber por qué esto funciona en todos mis dispositivos de prueba, y no puedo reproducir este bloqueo, y sólo parece estar en un pequeño número de dispositivos.
Aquí está el nuevo accidente:
java.lang.NullPointerException at com.myapp.util.IabHelper.queryPurchases(SourceFile:836) at com.myapp.util.IabHelper.queryInventory(SourceFile:558) at com.myapp.util.IabHelper.queryInventory(SourceFile:522) at com.myapp.util.IabHelper$2.run(SourceFile:617) at java.lang.Thread.run(Thread.java:1019)
Causado por IabHelper …
line 836: logDebug("Package name: " + mContext.getPackageName());
Editar 3/17/13: veo que ha habido muchas correcciones de errores publicados en los últimos meses, voy a probar el último código disponible aquí y ver si esto resuelve el problema:
Https://code.google.com/p/marketbilling/source/browse/v3/src/com/example/android/trivialdrivesample/util
En una de mis aplicaciones, utilizo la API de facturación y el código estándar incluido en ella.
Estoy utilizando la última versión de la API de facturación disponible a través del gestor de SDK el 3/16/2013.
En mi actividad, consulta el inventario utilizando lo siguiente:
final List<String> skuList = new ArrayList<String>(); skuList.add("sku1"); skuList.add("sku2"); skuList.add("sku3"); if (skuList != null) { if (skuList.size() > 0) { try { mHelper.queryInventoryAsync(true, skuList, mGotInventoryListener); } catch (Exception e) { ACRA.getErrorReporter().handleException(e); } } }
Estoy recibiendo varios informes de NullPointerException en la naturaleza de la clase IabHelper para los siguientes dispositivos. No puedo reproducir el problema y no puedo encontrar ninguna información sobre estos bloqueos, y es la razón por la que estoy publicando esta pregunta.
Tengo innumerables otras comprobaciones de nulos y try / catch bloques en el "desarrollador" frente a la parte de la API de facturación, incluyendo dentro onQueryInventoryFinished, por lo que sé que esta excepción no se está lanzando desde "mi código" (porque no estoy captando accidentes De cualquiera de las clases de mi aplicación), sino que se está lanzando desde dentro de la propia IabHelper. No he modificado el IabHelper que no sea esta revisión recomendada: https://stackoverflow.com/a/14737699
Crash # 1 Galaxy Nexus
java.lang.NullPointerException at com.myapp.util.IabHelper.querySkuDetails(SourceFile:802) at com.myapp.util.IabHelper.queryInventory(SourceFile:471) at com.myapp.util.IabHelper$2.run(SourceFile:521) at java.lang.Thread.run(Thread.java:856)
Causado por IabHelper …
line 802: Bundle skuDetails = mService.getSkuDetails(3, mContext.getPackageName(), ITEM_TYPE_INAPP, querySkus);
Crash # 2 Samsung GT-S5570L
java.lang.NullPointerException at com.myapp.util.IabHelper.queryPurchases(SourceFile:735) at com.myapp.util.IabHelper.queryInventory(SourceFile:465) at com.myapp.util.IabHelper$2.run(SourceFile:521) at java.lang.Thread.run(Thread.java:1019)
Causado por IabHelper …
line 735: Bundle ownedItems = mService.getPurchases(3, mContext.getPackageName(), ITEM_TYPE_INAPP, continueToken);
- Android In App BIlling v3 no funciona Nexus 7
- ¿En qué condiciones se aplican los cambios de servidor de versión 3 de facturación en la aplicación disponibles en los dispositivos cliente?
- Compra exitosa pero no se encuentra la clase cuando se desmarca: com.google.android.finsky.billing.lightpurchase.PurchaseParams
- ¿Qué cuenta de Google Play utiliza IabHelper?
- Falla de confiabilidad de la aplicación en la aplicación v3
- El retorno de API de Google IAB API3 getSkuDetails () falló 5: Error del programador
- Prueba de facturación de aplicaciones en otros países
- Android IAB - Actividad destruida después de una compra exitosa
Editar 4/15: La captura de nullpointer en IabHelper parece haber detenido este problema. Ya no veo las excepciones lanzadas, voy a aceptar esto como una respuesta.
Editar 4/04: Un poco de una inmersión más profunda. Existen bloques catch que manejan RemoteExceptions y JSONExceptions para el método queryPurchases, pero no NullPointerException. Lo que voy a tratar es incluir el manejo de excepciones NullPointer para que IabHelper se ve así al intentar querySkuDetails:
catch (NullPointerException e) { throw new IabException(IABHELPER_UNKNOWN_ERROR, "NullPointer while refreshing inventory.", e); }
Acabo de presentar un error en esto:
https://code.google.com/p/marketbilling/issues/detail?id=114
Probablemente utilice operaciones asíncronas. El IabHelper actual no es seguro en caso de que utilice los … métodos asíncronos. El problema es que en cualquier momento una operación asíncrona está ejecutando dispo puede ser llamado en el hilo principal. En este caso obtendrá NullPointerExceptions e IllegalStateExceptions.
Aquí está el parche que lo fija:
Index: src/com/evotegra/aCoDriver/iabUtil/IabHelper.java =================================================================== --- src/com/evotegra/aCoDriver/iabUtil/IabHelper.java (revision 1162) +++ src/com/evotegra/aCoDriver/iabUtil/IabHelper.java (working copy) @@ -86,7 +86,10 @@ // Is an asynchronous operation in progress? // (only one at a time can be in progress) - boolean mAsyncInProgress = false; + volatile boolean mAsyncInProgress = false; + + // is set to true if dispose is called while a thread is running. Allows graceful shutdown + volatile boolean mDisposeRequested = false; // (for logging/debugging) // if mAsyncInProgress == true, what asynchronous operation is in progress? @@ -285,6 +288,12 @@ * disposed of, it can't be used again. */ public void dispose() { + // do not dispose while an async Thread is running. Will cause all kinds of exceptions. + // In this case dispose must be called from thread after setting mAsyncInProgress to true + if (mAsyncInProgress) { + mDisposeRequested = true; + return; + } logDebug("Disposing."); mSetupDone = false; if (mServiceConn != null) { @@ -827,6 +836,7 @@ logDebug("Ending async operation: " + mAsyncOperation); mAsyncOperation = ""; mAsyncInProgress = false; + if (mDisposeRequested) IabHelper.this.dispose(); }
O descargue el parche aquí. http://code.google.com/p/marketbilling/issues/detail?id=139&thanks=139&ts=1375614409
Modifique ligeramente el inicio del método queryPurchases
para que se vea así:
int queryPurchases(Inventory inv, String itemType) throws JSONException, RemoteException { // Query purchases //logDebug("Querying owned items, item type: " + itemType); //logDebug("Package name: " + mContext.getPackageName()); boolean verificationFailed = false; String continueToken = null; do { // logDebug("Calling getPurchases with continuation token: " + continueToken); if(mDisposed || mService==null) return IABHELPER_UNKNOWN_ERROR; Bundle ownedItems = mService.getPurchases(3, mContext.getPackageName(), itemType, continueToken);
Gracias a sebastie por señalar la causa de esto.
Tmanthey también requiere
mDisposeRequested = false;
Después de la eliminación
Si usted está recibiendo este error en el emulador, puede ser una cosa muy simple que sucede en más de una mitad de casos.
Comprueba que estás utilizando el SDK de la API de Google y no el SDK normal.