0

I am building an Android App to control power outlets with a smartphone. The app features an Android Wear app so people can control their lights right from their wrist.

When the user wants to control a light I send a String action via the MessageApi from the smartwatch to the smartphone, which receives this action in a WearableListenerService and sends the appropriate network signal to the power outlet/gateway in an AsyncTask.

This works fine as long as the phone has not been in idle for too long. However if the phone is still on the table for too long and doze kicks in Wear actions do execute very slow or sometimes not at all. I guess this is in part intended behavior however it is not practical in my case as the user cant wait that long for his lights to turn on if he wants to enter a dark room.

I am aware that doze completely cuts the networking for everything except FCM/GCM if you are not on the doze whitelist. But even when my app is on this whitelist and the networking part works actions can take a long time to execute on the phone.

So my specific question is: Whats the recommended way to handle this scenario, where an action from a wearable device needs to be done via network on the connected smartphone which is in doze mode?

Is there a way to exit doze for a quick amount of time to execute calculations triggered by the wearable companion app faster?

I know the AlarmManager has a new method that works even in doze mode, but will this fix the processing delay too? Firing an alarm after receiving a MessageEvent from MessagApi seems like a workaround to me.

Or maybe is an AsyncTask just the wrong way to handle background networking and thats where the delay comes from?

Markus Ressel
  • 1,127
  • 1
  • 13
  • 14
  • Does the Message API `onMessageReceived` event fire immediately when the handset is in Doze? Or is that what's delayed? – Sterling Aug 30 '16 at 03:41
  • I changed my networking code now to use an IntentService for this kind of actions and it seems like it improved things a bit. @String Yes the onMessageReceived does fire (almost) immediately. I can control my lights when in doze. In my code I decide between using WAN or LAN/WLAN when internet is available. This check (is internet available) seems to take quite some time and the check fails, even though my app is on the whitelist and Internet should be available. – Markus Ressel Aug 31 '16 at 22:42

1 Answers1

0

Actually, there are a few options that you can do to handle Doze's effects as given in Adapting your app to Doze. You may want to consider the following options:

  1. If your app requires a persistent connection to the network to receive messages, you should use Google Cloud Messaging (GCM) if possible.

    GCM is optimized to work with Doze and App Standby idle modes by means of high-priority GCM messages. GCM high-priority messages let you reliably wake your app to access the network, even if the user’s device is in Doze or the app is in App Standby mode.

  2. To help with scheduling alarms, Android 6.0 (API level 23) introduces two new AlarmManager methods: setAndAllowWhileIdle() and setExactAndAllowWhileIdle(). With these methods, you can set alarms that will fire even if the device is in Doze.

    However, please note that with these methods, neither setAndAllowWhileIdle() nor setExactAndAllowWhileIdle() can fire alarms more than once per 9 minutes, per app.

Please try going through Optimizing for Doze and App Standby for a more detailed information or discussion.

In addition to these given documentations, the same options in handling Doze were also given and discussed in Diving into Doze Mode for Developers which might also help.

Teyam
  • 7,686
  • 3
  • 15
  • 22
  • I need a connection to the internet (or at least lan) but not to a server I can control so GCM is not an option (if I understand it correctly). I know about the new alarm methods and I already use them. They work properly. Are you suggesting that this is the correct way to handle this? Firing an additional alarm? – Markus Ressel Aug 30 '16 at 15:59