Android: get battery status at regular intervals using the alarm manager

I want to get the battery status of an Android device at regular intervals.

As a good polling idea for battery changes every couple of minutes, I wanted to use a repeating alarm that might go away, maybe once an hour, to name a class that gets the current battery status.

However, my current implementation gives me an exception:

android.content.ReceiverCallNotAllowedException: IntentReceiver components are not allowed to register to receive intents. 

The class that is called when the alarm time is as follows:

 public class GetBatteryStatusTimeout extends BroadcastReceiver{ private static final String TAG = "GetBatteryStatusTimeout"; @Override public void onReceive(Context context, Intent intent) { BatteryDataManager batteryData = new BatteryDataManager(context); batteryData.getStatus(); Log.e(TAG, "GetBatteryStatus timer expired, getting status"); } } 

The getStatus() method calls the registration code for sticky intent and getting battery status:

 IntentFilter ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED); Intent batteryStatus = context.registerReceiver(null, ifilter); int status = batteryStatus.getIntExtra(BatteryManager.EXTRA_STATUS, -1); boolean isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING; boolean fullyCharged = status == BatteryManager.BATTERY_STATUS_FULL; int level = batteryStatus.getIntExtra(BatteryManager.EXTRA_LEVEL, -1); 

This is the point at which I am registering an exception for this recipient.

I understand what the exception says (I think!), But I don’t call the code to register for sticky intent from another recipient?

The alarm receiver calls another class, which then registers the receiver to change the battery settings .... but obviously this is also forbidden.

Which alternative?

Also, the exception applies only to some devices, and the application works fine on others?

+1
source share
1 answer

This is actually an Android bug. You are not actually trying to register a BroadcastReceiver for an asynchronous callback in this case, but Android still throws this exception.

To get around this, instead of calling

 context.registerReceiver(null, ifilter); 

to get sticky translation do the following:

 context.getApplicationContext().registerReceiver(null, ifilter); 

The Context application has a longer life than the Context receiver, so the call will be allowed.

+8
source

All Articles