Facturación In-App de Google, IllegalArgumentException: la intención del servicio debe ser explícita, después de actualizar a Android L Dev Preview

Mi código de facturación en la aplicación funcionaba bien hasta que me actualicé a Android L Dev Preview. Ahora recibo este error cuando se inicia mi aplicación. ¿Alguien sabe qué ha cambiado en L que causa esto o cómo debería cambiar mi código para solucionarlo?

android { compileSdkVersion 'android-L' buildToolsVersion '20' defaultConfig { minSdkVersion 13 targetSdkVersion 'L' ... ... compile 'com.google.android.gms:play-services:5.+' compile 'com.android.support:support-v13:21.+' compile 'com.android.support:appcompat-v7:21.+' ... ... 

El error cuando la aplicación comienza:

 06-29 16:22:33.281 5719-5719/com.tbse.wnswfree D/AndroidRuntime﹕ Shutting down VM 06-29 16:22:33.284 5719-5719/com.tbse.wnswfree E/AndroidRuntime﹕ FATAL EXCEPTION: main Process: com.tbse.wnswfree, PID: 5719 java.lang.RuntimeException: Unable to start activity ComponentInfo{com.tbse.wnswfree/com.tbse.wnswfree.InfoPanel}: java.lang.IllegalArgumentException: Service Intent must be explicit: Intent { act=com.android.vending.billing.InAppBillingService.BIND } at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2255) at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2317) at android.app.ActivityThread.access$800(ActivityThread.java:143) at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1258) at android.os.Handler.dispatchMessage(Handler.java:102) at android.os.Looper.loop(Looper.java:135) at android.app.ActivityThread.main(ActivityThread.java:5070) at java.lang.reflect.Method.invoke(Native Method) at java.lang.reflect.Method.invoke(Method.java:372) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:836) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:631) Caused by: java.lang.IllegalArgumentException: Service Intent must be explicit: Intent { act=com.android.vending.billing.InAppBillingService.BIND } at android.app.ContextImpl.validateServiceIntent(ContextImpl.java:1603) at android.app.ContextImpl.bindServiceCommon(ContextImpl.java:1702) at android.app.ContextImpl.bindService(ContextImpl.java:1680) at android.content.ContextWrapper.bindService(ContextWrapper.java:528) at com.tbse.wnswfree.util.IabHelper.startSetup(IabHelper.java:262) at com.tbse.wnswfree.InfoPanel.onStart(InfoPanel.java:709) at android.app.Instrumentation.callActivityOnStart(Instrumentation.java:1217) at android.app.Activity.performStart( Activity.java:5736) at android.app.ActivityThread.performLaunchActivity( ActivityThread.java:2218) at android.app.ActivityThread.handleLaunchActivity( ActivityThread.java:2317) at android.app.ActivityThread.access$800( ActivityThread.java:143) at android.app.ActivityThread$H.handleMessage( ActivityThread.java:1258) ... 

Línea 709 en InfoPanel.java:

  mHelper.startSetup(new IabHelper.OnIabSetupFinishedListener() { @Override public void onIabSetupFinished(IabResult result) { ... 

Tuve el mismo problema y establecer explícitamente el paquete lo resolvió. Similar a la respuesta de Aleksey, pero más simple:

 Intent intent = new Intent("com.android.vending.billing.InAppBillingService.BIND"); // This is the key line that fixed everything for me intent.setPackage("com.android.vending"); getContext().bindService(intent, serviceConnection, Context.BIND_AUTO_CREATE); 

Como se señala en la respuesta a continuación, las soluciones serían crear intenciones explícitas de forma manual:

 private Intent getExplicitIapIntent() { PackageManager pm = mContext.getPackageManager(); Intent implicitIntent = new Intent("com.android.vending.billing.InAppBillingService.BIND"); List resolveInfos = pm.queryIntentServices(implicitIntent, 0); // Is somebody else trying to intercept our IAP call? if (resolveInfos == null || resolveInfos.size() != 1) { return null; } ResolveInfo serviceInfo = resolveInfos.get(0); String packageName = serviceInfo.serviceInfo.packageName; String className = serviceInfo.serviceInfo.name; ComponentName component = new ComponentName(packageName, className); Intent iapIntent = new Intent(); iapIntent.setComponent(component); return iapIntent; } 

Aquí está el código en las fonts de vista previa L para comprobar el bash explícito. Se ha comentado actualmente, pero en Nexus 5 con vista previa L todavía se ejecuta y arroja una excepción para los bashs implícitos.

Editar: la respuesta de @Alav es mucho mejor y más simple. Solo agrega

 intent.setPackage("com.android.vending"); 

Todos los créditos para él . Y aquí está el código en las fonts de liberación L para comprobar el bash explícito.

Se encontró una solución clara aquí: https://code.google.com/p/android-developer-preview/issues/detail?id=1674

En Google Licensing Library (LVL), archivo LicenseChecker.java, reemplace la llamada “bindService” por esta:

  Intent serviceIntent = new Intent( new String(Base64.decode("Y29tLmFuZHJvaWQudmVuZGluZy5saWNlbnNpbmcuSUxpY2Vuc2luZ1NlcnZpY2U="))); serviceIntent.setPackage("com.android.vending"); boolean bindResult = mContext .bindService( serviceIntent, this, // ServiceConnection. Context.BIND_AUTO_CREATE); 

Y en el conjunto AndroidManifest.xml: android: minSdkVersion = “4”

El “setPackage” requiere Android versión 4.

En “L”, la vinculación a un servicio requiere el uso de una intención explícita.

Ver http://commonsware.com/blog/2014/06/29/dealing-deprecations-bindservice.html

Simplemente reemplace el código

 boolean attempt = mContext.bindService(new Intent("com.android.vending.billing.InAppBillingService.BIND"), mServiceConn, Context.BIND_AUTO_CREATE); 

con el siguiente código

 Intent serviceIntent = new Intent("com.android.vending.billing.InAppBillingService.BIND"); serviceIntent.setPackage("com.android.vending"); boolean attempt = mContext.bindService(serviceIntent, mServiceConn, Context.BIND_AUTO_CREATE); 

en la clase IabHelper que ha colocado en la carpeta de utilidades de la aplicación (si ha seguido las instrucciones del tutorial de facturación de Google InApp).

Recibí el mismo error del código de configuración anterior de Google Cloud Messaging. La solución más simple parece estar cambiando

 Intent registrationIntent = new Intent( "com.google.android.c2dm.intent.REGISTER"); 

dentro

 Intent registrationIntent = new Intent(); registrationIntent.setClassName("com.google.android.c2dm.intent", "REGISTER"); 

Para mí, funcionó utilizar el IabHelper actual de las muestras: sdk / extras / google / play_billing / samples / TrivialDrive / src / com / example / android / trivialdrivesample / util / IabHelper.java

No olvide ejecutar primero el administrador de actualizaciones de SDK para asegurarse de tener instalada la versión actual.

Las respuestas a estos problemas específicos ya se han publicado, pero solo para ayudar a otras personas con exactamente el mismo problema, pero esta vez para la API de la licencia.

Obtiene el mismo error en el mensaje 5.0 que en la biblioteca IAP publicada anteriormente, pero puede encontrar una solución (que implica cambiar manualmente algunas líneas en LicenseChecker.java (código de Google) y luego recomstackr su proyecto que incluirá esta biblioteca).

Consulte: https://code.google.com/p/android/issues/detail?id=78505 para obtener más información. Espero que cualquiera pueda usarlo.

Esto funcionó para mí, pero me gustaría saber si es una forma aceptable de hacerlo:

i.setClass (context, MyService.class);

si tiene el siguiente error, establezca targetSdkVersion 19 en build.gradle. Cuando configuré el 19 mi problema fue resuelto. Para publicación, configuré targetSdkVersion 27

en com.google.android.vending.licensing.LicenseChecker.checkAccess (LicenseChecker.java:150) en com.google.android.vending.expansion.downloader.impl.DownloaderService $ LVLRunnable.run

 defaultConfig { applicationId "com.brain.math.game.free" minSdkVersion 15 targetSdkVersion 19 

targetSdkVersion 19