Reputation: 107
I am writing an Android service which is executed every 15 minutes.
It requires an internet connection because it sends a request to a server and if the response of the server is like "ok" the service executes some code.
All works fine if the phone is not in standby (the screen is on), but if the phone is in standby mode the connection is unavailable and the service does not work correctly. I want the service to wait for an available connection and then send the request to a server.
For example the phone is in standby mode and 15 minutes afterwards, the service starts and then tries to send the request to a server but the connection is unavailable. In this case I want the service to wait for a connection to become available and then send the request to server.
Can somebody suggest what it should do?
Ok but I never use alarm manager and broadcast receiver please con you post an example? but alarm manager and broadcast receiver work if phone is in standby? I write write an error I must execute the service every two hours not 15 minutes.
Upvotes: 1
Views: 2694
Reputation: 348
When phone goes in standby, cpu will stop to work, causing all processes to stop their execution. You can avoid this by using PowerManager and lock the cpu to assure that it will stay on even when phone goes in standby:
m_wakeLock = m_powerManager.newWakeLock(
PowerManager.PARTIAL_WAKE_LOCK, "My Tag");
m_wakeLock.acquire();
... cpu is assured to be on during this time ...
m_wakeLock.release();
But since your need is to have service to wake up every 15 min, even when in standby, this could cause an hard use of battery. You can avoid this by using an AlarmManager, that will schedule an event every 15 minutes, and then launch the appropriate BroadcastReceiver. In the BroadcastReceiver you simply send to your service a message through intent (launching service with parameter in intent), acquire cpu, do work, and release cpu.
-------------------------- UPDATE -------------------------
First of all, declare your broadcastReceiver in your manifest:
<receiver
android:name="StartUpReceiver"
<intent-filter>
<action android:name="my.Package.MyEvent" />
<category android:name="android.intent.category.HOME" />
</intent-filter>
</receiver>
Your BroadcastReceiver will look look similar to this:
public class StartUpReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Intent serviceIntent = new Intent();
serviceIntent.setAction("my.Package.MyService");
context.startService(serviceIntent);
}
}
In this way, every time an intent with action "my.Package.MyEvent" is launched using, for example, sendBroadcast(Intent) method (CHECK HERE), your broadcast receiver (namely, just a class that extends the BroadcastReceiver class CHECK HERE) will execute it's onReceive() method. In my code, i simply create an Intent with an appropriate action ("my.Package.MyService"), and then launch MyService.
AlarmManager class simply provide you a way to schedule some intent to be launched in the future, similarly to sendBroadcast() method (CHECK HERE). Cpu will stay on during all execution of the onReceive() method associated to the AlarmManager. You need then to lock the cpu, launch the service which is now sure tu be executed. In the mean time onReceive() method will stop, but your service is assured to be in execution. The only thing you need to do is just to find a workaround on how to let your service communicate with your AlarmManager, to release the cpu lock after the service is executed, as stated in the main page of AlarmManager. That is, you just need to syncronize your service with your broadcast receiver, using an external object to save the information needed (in this case, if cpu is locked at the end of service release the cpu).
Upvotes: 2
Reputation: 475
Before executing the service check if the connectivity is available. The below mentioned code snippet will help you identify if there is any valid network connectivity.
ConnectivityManager connectivity = (ConnectivityManager) context
.getSystemService(Context.CONNECTIVITY_SERVICE);
if (connectivity != null) {
NetworkInfo[] info = connectivity.getAllNetworkInfo();
if (info != null) {
for (NetworkInfo networkInfo : info) {
if (networkInfo.getState() == NetworkInfo.State.CONNECTED) {
return true;
}
}
}
}
return false;
If there is no connectivity suspend the service call and then poll for network connectivity after 30 seconds or so.
Upvotes: 2