一定時間ごとにAPIを叩くアプリの開発中、端末によってスリープ状態になるとAPIを叩けなくなる問題が発生したのでまとめ。
原因
最初はバックグラウンドでの処理がおかしいのかと思いましたが、ただ単に端末のWi−Fi設定で「スリープ時にWi-Fi接続を維持」の設定が「使用しない」になっており、更にWi-Fiモデルの端末だったのでネットワークに接続できなかっただけでした。
この設定が「使用しない」になっていると端末がスリープになった場合にWi-Fiの接続が切れてしまうようです。
対応
ひとまずは端末の設定を「常に使用する」に変更することで対応しました。
端末やOSによって多少異なると思いますがNexus7(2013) Lolipopでは、
設定 -> Wi-Fi -> メニューの詳細設定 -> スリープ時にWi-Fi接続を維持 -> 常に使用
から変更できました。
(一体なんのためにスリープ時にWi-FiをOFFにする設定が存在するのかと思いましたが電池消費対策でしょうか・・・)
ちなみにこの設定の情報は
try {
ContentResolver contentResolver = getContentResolver();
// Settings.System.WIFI_SLEEP_POLICY は API level 17 から deprecated なので
// Settings.Global.WIFI_SLEEP_POLICY を使用する
int policy = Settings.System.getInt(contentResolver, Settings.Global.WIFI_SLEEP_POLICY);
switch (policy) {
case Settings.Global.WIFI_SLEEP_POLICY_DEFAULT:
// 使用しない
break;
case Settings.Global.WIFI_SLEEP_POLICY_NEVER_WHILE_PLUGGED:
// 電源接続時にのみ使用する
break;
case Settings.Global.WIFI_SLEEP_POLICY_NEVER:
// 常に使用
break;
}
} catch (Settings.SettingNotFoundException e) {
e.printStackTrace();
}
で取得できます。
設定画面への遷移は
startActivity(new Intent(Settings.ACTION_WIFI_IP_SETTINGS));
で出来ました(※Wi-Fiの詳細設定画面までしか遷移できません)
まとめ
スリープ状態で大量の通信をしたり、Wi-Fiモデルでスリープ状態になっても通信ができるようにWIFI_SLEEP_POLICY_NEVER
以外の場合はユーザに通知するというのもよいと思います。
参考
Settings.System : Android Developers
スリープ時にWi-Fi(無線LAN)が切断されないようにするAndroidの設定