Android BOOT_COMPLETED not received when application is closed

我与影子孤独终老i 提交于 2019-12-17 02:35:12

问题


I am aware that this question has been asked a lot on the site, however, I cant seem to find a solution. My BOOT_COMPLETED receiver is not called when the application is not running.

Manifest:

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.startuptest"
    android:versionCode="1"
    android:versionName="1.0"
    android:installLocation="internalOnly">
    <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
    <uses-sdk android:minSdkVersion="8" android:targetSdkVersion="17" />

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
        <activity
            android:name="com.example.startuptest.MainActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

        <receiver android:name="com.example.startuptest.StartUpBootReceiver" >
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED" />
            </intent-filter>
        </receiver>
    </application>
</manifest>

StartUpBootReceiver:

public class StartUpBootReceiver  extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {

        Log.d("startuptest", "StartUpBootReceiver " + intent.getAction());

        if ("android.intent.action.BOOT_COMPLETED".equals(intent.getAction())) {
            Log.d("startuptest", "StartUpBootReceiver BOOT_COMPLETED");
        }
    }
}

If the application is running and I simulate a call with

adb shell
am broadcast -a android.intent.action.BOOT_COMPLETED

The event is received correctly, however, if the application is closed the event is not receieved, nor is it received at start up.

I have installed the application then launched it a couple of times to make sure it is registered. I'm pretty lost on this one so any advice would be highly appreciated.

Edit: I can see in the logs that all the other closed applications (Youtube, FileObserver, etc) receive the boot_completed event, just not mine.


回答1:


I start my app when the BOOT_COMPLETED, so I know it's working. I add Log.d it won't show. I add Toast it show. Small differents in Manifest.xml

<receiver android:name="com.example.startuptest.StartUpBootReceiver" android:enabled="true" android:exported="true">
    <intent-filter>
         <action android:name="android.intent.action.BOOT_COMPLETED" />
         <category android:name="android.intent.category.DEFAULT" />
    </intent-filter>            
</receiver>



回答2:


Starting with Android 3.1 all applications, upon installation, are placed in a "stopped" state.(This is the same state that the application ends up in after the user force-stops the app from the Settings application.)

While in "stopped" state, the application will not run for any reason, except by a manual launch of an activity. (Meaning no BroadcastReceviers(ACTION_PACKAGE_INSTALLED, BOOT_COMPLETED etc.) will be invoked, regardless of the event for which they have registered, until the user runs the app manually.)

This is an anti-malware move by Google. Google has advocated that users should launch an activity from the launcher first, before that application can go do much. Preventing BOOT_COMPLETED from being delivered until the activity is launched is a logical consequence of the that argument.

More details about this:
http://developer.android.com/about/versions/android-3.1.html#launchcontrols
http://commonsware.com/blog/2011/07/05/boot-completed-regression.html
http://devmaze.wordpress.com/2011/12/05/activating-applications/




回答3:


Each answer here add a small piece of information, so here is the summary of it all:

To make sure you will receive the BOOT_COMPLETED make sure you do the following:

  1. Add your receiver to manifest (don't forget the flags):

    <receiver android:name="com.yourpacakge.BootReceiver" android:exported="true" android:enabled="true">
        <intent-filter>
            <action android:name="android.intent.action.BOOT_COMPLETED"/>
            <category android:name="android.intent.category.DEFAULT"/>
        </intent-filter>
    </receiver>
    
  2. Add permission:

    <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>

  3. After installing your app, it needs to be lunch at least once, manually by the user, in order to receive Boot complete event.(More details)




回答4:


Heres a C# version if you guys want it. My tests show that it works pretty much flawlessly and the startup is quite fast. Though do note that adding it both in C# and in AndroidManifest.xml breaks it(for me at least).

I have also added some nice and useful examples that I wished I had found out from someone instead of learning it myself when reading through the documentaries and such.

[BroadcastReceiver(Enabled = true, Exported = true, DirectBootAware = true, Name = "com.nevaran.startup.StartUpBootReceiver")]
[IntentFilter(new string[] {
    Intent.ActionBootCompleted
    , Intent.ActionLockedBootCompleted
    , Intent.ActionMyPackageReplaced
    , Intent.ActionUserInitialize
    , "android.intent.action.QUICKBOOT_POWERON"
    , "com.htc.intent.action.QUICKBOOT_POWERON"
})]
public class BootReceiver : BroadcastReceiver
{
    public override void OnReceive(Context context, Intent intent)
    {
         if(    intent.Action.Equals(Intent.ActionBootCompleted)
             || intent.Action.Equals(Intent.ActionLockedBootCompleted)
             || intent.Action.Equals(Intent.ActionUserInitialize)
             || intent.Action.Equals("android.intent.action.QUICKBOOT_POWERON")
             || intent.Action.Equals("com.htc.intent.action.QUICKBOOT_POWERON")
           )
        {
            //run code here only if its started by the chosen actions
        }
        //some code that doesnt care about which action is triggered by
    }
}



回答5:


was struggling with the same problem, the reason is you are using Log.d to track you application in logcat, unfortunately when you restart your phone the application is receiving the BOOT_Complete but you can't see it because it's not logging to logcat.

try making a Toast with some text instead of Log.d to make sure if BOOT_COMPLETED is or is not received.

hope this Help.




回答6:


If you want to know the actual reason behind why BOOT_COMPLETE is not working or not receiving. I will suggest you to go to the OFFICIAL Android develop site. They have explained with exact solution.

Android developer - BOOT_COMPLETE




回答7:


To resolve this problem, you can use firebaseJobDispatcher to invoke automatically , firebaseJobDispatcher will have code to reactive your services, yes after a certain time services may stopped by OS, but your firebaseJobDispatcher will reactivate your services again. FirebaseJobDispatcher has lots of properties from where you can define the scope of this;

how it works, for more detail https://github.com/firebase/firebase-jobdispatcher-android




回答8:


Basically you need android:enabled="true" android:exported="true" flags in manifest to receive the broadcast.

<receiver android:name=".bootReceiver" android:enabled="true" android:exported="true">
        <intent-filter>
            <action android:name="android.intent.action.BOOT_COMPLETED" />
            <category android:name="android.intent.category.DEFAULT"/>
        </intent-filter>
    </receiver>


来源:https://stackoverflow.com/questions/17226410/android-boot-completed-not-received-when-application-is-closed

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!