Выставление счетов Google в приложении, IllegalArgumentException: намерение службы должно быть явным после обновления до Android L Dev Preview

Мой код оплаты в приложении работал нормально, пока я не обновился до Android L Dev Preview. Теперь я получаю эту ошибку при запуске моего приложения. Кто-нибудь знает, что изменилось в L, что вызывает это, или как мне изменить свой код, чтобы исправить это?

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.+'
...
...

Ошибка при запуске приложения:

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)
        ...

           

Строка 709 в InfoPanel.java:

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

comment
Эта строка и код вокруг нее были бы интересны: com.tbse.wnswfree.util.IabHelper.startSetup(IabHelper.java:262)   -  person HHK    schedule 30.06.2014
comment
Ганс. Это код Google, вы можете увидеть его здесь: goo.gl/KLMllR   -  person elliptic1    schedule 30.06.2014
comment
Возможный дубликат Android L (API 21) - java.lang.IllegalArgumentException: намерение службы должно быть явным   -  person regisd    schedule 21.02.2016


Ответы (10)


У меня была та же проблема, и я решил ее явной установкой пакета. Аналогично ответу Алексея, но проще:

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);
person alav    schedule 19.11.2014
comment
Удивительно - даже в последней версии IabHelper.java от Google этого нет. Не уверен, что это только требование для 5.0, но добавить его точно не помешает. - person slott; 28.11.2014
comment
Последний iAbHelper.java теперь включает эту строку (версия 5), однако я все еще получаю ту же самую ошибку!? Поэтому я добавил это в IapHelper: if (ris.get(0) != null && ris.get(0).serviceInfo != null) serviceIntent.setClassName(ris.get(0).serviceInfo.packageName, ris. получить(0).serviceInfo.имя); - person 3c71; 04.01.2015
comment
@ 3c71 где ты взял пятую версию? - person swalkner; 30.01.2015
comment
Небольшое замечание: этот код находится в файле IabHelper.java в вашем пакете util. мне было не очевидно - person Don; 05.07.2015
comment
Сейчас он находится в классе LicenseChecker. - person Noundla Sandeep; 30.10.2015
comment
2017 год, а ошибка осталась. Невероятный. - person Rick77; 19.02.2017
comment
Невероятно, что эта ошибка все еще существует спустя три года. - person Ethan Hohensee; 07.07.2017
comment
Превосходно! Сэкономил мне массу времени. Спасибо! - person tomurka; 09.08.2018

Как указано в ответе ниже, решения заключаются в том, чтобы вручную создать явное намерение:

private Intent getExplicitIapIntent() {
        PackageManager pm = mContext.getPackageManager();
        Intent implicitIntent = new Intent("com.android.vending.billing.InAppBillingService.BIND");
        List<ResolveInfo> 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;
    }

Вот код в источниках предварительного просмотра L для проверки явного намерения. В настоящее время он имеет комментарии, но на Nexus 5 с Предварительный просмотр L все еще работает и выдает исключение для неявных намерений.


Изменить: ответ @alav намного лучше и проще. Просто добавь

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

Все кредиты для его. И здесь — это код в исходниках выпуска L для проверки явного намерения.

person Oleksii Masnyi    schedule 11.10.2014
comment
Это работает (по крайней мере, теперь предупреждение исчезло). Кроме того, вы можете принудительно установить одно приложение, которое разрешает это действие, чтобы также предотвратить пиратство. - person ekawas; 18.10.2014
comment
Также опубликовано более общее решение, вдохновленное этим ответом, если вы столкнулись с этой проблемой в чем-то другом, кроме IAB: blog.android-develop.com/2014/10/ - person Sean; 19.10.2014
comment
использование этого решения действительно устраняет проблему, но для меня создает другую проблему. См. мой вопрос здесь: stackoverflow .com/questions/27495659/ - person ez4nick; 16.12.2014
comment
Официальное решение Google (developer.android.com/google/ play/billing/) — добавить serviceIntent.setPackage(com.android.vending), как в ответе @alav - person marmor; 16.12.2014
comment
Это не работает. Эта строка уже давно находится в последнем IabHelper.java, и я все еще получаю ошибки. - person Stéphane; 06.01.2015

Здесь найдено четкое решение: https://code.google.com/p/android-developer-preview/issues/detail?id=1674

В библиотеке лицензирования Google (LVL) в файле LicenseChecker.java замените вызов «bindService» следующим образом:

 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);

И в наборе AndroidManifest.xml: android:minSdkVersion="4"

Для «setPackage» требуется Android версии 4.

person Roy    schedule 02.12.2014
comment
Мы только что обновили наш целевой SDK и столкнулись с этой проблемой. Спасибо за исправление. Обратите внимание, что это касается только устройств под управлением Android 5.0. Устройства с версией 5.0.1 и выше выглядят нормально. - person Danny Parker; 13.04.2015

В «L» привязка к службе требует использования явного намерения.

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

person cketti    schedule 29.06.2014
comment
Поэтому мне просто интересно, должны ли мы использовать решение, как в блоге, или будет ли обновлен IAP API. Я думаю, что он будет обновлен... - person elliptic1; 30.06.2014
comment
@elliptic1 Вчера это не было исправлено в API 21, поэтому я не уверен, будет ли оно когда-либо изменено. :( - person Sean; 19.10.2014
comment
Также опубликовано более общее решение, вдохновленное отмеченным ответом, если вы столкнулись с этой проблемой не в IAB: blog.android-develop.com/2014/10/ - person Sean; 19.10.2014
comment
Что ж, просто невероятно, что Google еще не обновил свой код IABHelper. Ни одно из этих решений не работает для меня на эмуляторе, работающем под управлением 5.0, который все еще дает сбой в bindService(). - person Alchete; 22.10.2014

Просто замените код

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

со следующим кодом

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);

в классе IabHelper, который вы поместили в папку utils inappbilling (если вы следовали инструкциям руководства Google InApp Billing).

person Harpreet    schedule 17.11.2015
comment
Теперь он работает для версии Lollipop и выше, предыдущий код работал только до Kitkat. - person Harpreet; 17.11.2015

Я получал ту же ошибку от более старого кода установки Google Cloud Messaging. Кажется, самое простое исправление меняется

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

в

Intent registrationIntent = new Intent();
registrationIntent.setClassName("com.google.android.c2dm.intent", "REGISTER");
person Don Park    schedule 19.11.2014

Для меня сработало использование текущего IabHelper из примеров: sdk/extras/google/play_billing/samples/TrivialDrive/src/com/example/android/tributaldrivesample/util/IabHelper.java

Не забудьте сначала запустить диспетчер обновлений sdk, чтобы убедиться, что у вас установлена ​​текущая версия.

person Björn Kechel    schedule 21.11.2014

Ответы на эти конкретные проблемы уже были опубликованы, но только для того, чтобы помочь другим с точно такой же проблемой, но на этот раз для License API.

Вы получаете ту же ошибку в сообщении 5.0, что и в библиотеке IAP, опубликованной выше, но вы можете найти исправление (включающее ручное изменение нескольких строк в LicenseChecker.java (код Google), а затем перекомпиляцию вашего проекта, который будет включать эту библиотеку).

Проверьте: https://code.google.com/p/android/issues/detail?id=78505, чтобы узнать подробности. Надеюсь, кто-нибудь сможет его использовать.

person zaifrun    schedule 25.11.2014

Это сработало для меня, но я хотел бы знать, что это приемлемый способ сделать это:

i.setClass(контекст, MyService.class);

person midiwriter    schedule 17.01.2015

если у вас есть ошибка ниже, установите targetSdkVersion 19 в build.gradle. Когда я установил 19, моя проблема решилась. Для публикации я установил targetSdkVersion 27

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

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

targetSdkВерсия 19

person ethemsulan    schedule 13.12.2017