AlarmManager и BroadcastReceiver вместо Сервиса - являются этим плохо? (Тайм-аут)

ИНФОРМАЦИЯ О ФОНЕ:

Я должен обновить некоторые данные из сети о каждом часе или так, даже когда мое приложение закрывается. Обновление самих данных занимает приблизительно 40 секунд к 1 минуте. Это затем сохраняется как сериализуемое в файл. Этот файл читается, когда мое приложение запускается.

ЭТО - ПОДХОД, который я ПРОЯВИЛ В НАСТОЯЩИЙ МОМЕНТ (не использующий Сервис)

используйте AlarmManager и BroadcastReceiver как это:

private void set_REFRESH_DATA_Alarm(){
    mContext = Main.this;
    alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
    broadcast_intent = new Intent(mContext, 
            RepeatingAlarmReceiver_REFRESH_DATA.class);
    pendingIntent = PendingIntent.getBroadcast(mContext, 0,  broadcast_intent, 0);
    // do a REFRESH every hour, starting for the first time in 30 minutes from now ...
    Calendar now = Calendar.getInstance();
    long triggerAtTime = now.getTimeInMillis()+ (1 * 30 * 60 * 1000); // starts in 30 minutes
    long repeat_alarm_every = (1 * 60 * 60 * 1000); // repeat every 60 minutes
    alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, triggerAtTime, 
            repeat_alarm_every, pendingIntent);
}

Мой RepeatingAlarmReceiver_REFRESH_DATA.class заботится об обновлении Данных из сети:

public class RepeatingAlarmReceiver_REFRESH_DATA extends BroadcastReceiver {

    public static Context mContext;
    ConnectivityManager mConnectivity;

    @Override
    public void onReceive(Context context, Intent intent) {
        mContext = context;
        // if Network connection is OK (Wifi or Mobile) then Load data ...
        mConnectivity = (ConnectivityManager) context
                .getSystemService(Context.CONNECTIVITY_SERVICE);
        Log.i("Hub",
                "mConnectivity.getNetworkInfo(0)="
                        + mConnectivity.getNetworkInfo(0));
        Log.i("Hub",
                "mConnectivity.getNetworkInfo(1)="
                        + mConnectivity.getNetworkInfo(1));
        if ((mConnectivity.getNetworkInfo(0).getState() == NetworkInfo.State.CONNECTED)
                || (mConnectivity.getNetworkInfo(1).getState() == NetworkInfo.State.CONNECTED)) {
            Log.i("Hub", "Connectivity OK ...");
            Refresh_HIST_DATA();
        } else {
            // else Show Dialog "No network connection" ...
            Log.i("Hub",
                    "No network connection for the moment... will try again later!");
        }
    }

    // =========================================================================
    private void Refresh_HIST_DATA() {
        Log.i("Hub", "Refresh_HIST_DATA()... Starting ...");
        // etc...
    }
}

В Декларации я имею:


ПРОБЛЕМА:

Предупреждение запущено вовремя, и обновление запускается, но затем приблизительно после 10 секунд оно останавливается (Тайм-аут):

06-25 11:55:05.278: WARN/ActivityManager (76): Тайм-аут широковещательной передачи BroadcastRecord {44bb4348 пустой указатель} - receiver=android.os. BinderProxy@44bcc670

06-25 11:55:05.278: WARN/ActivityManager (76): Получатель во время тайм-аута: ResolveInfo {44bb42c0 com.cousinHub.myapp. RepeatingAlarmReceiver_REFRESH_DATA p=0 o=0 m=0x0}

06-25 11:55:05.278: ИНФОРМАЦИЯ/ПРОЦЕСС (76): Отправка сигнала. PID: 819 SIG: 9

06-25 11:55:05.298: INFO/ActivityManager (76): com.cousinHub.myapp:remote Процесса (pid 819) умер.

PS: странно достаточно этого "Тайм-аута" не происходит приблизительно после 10 секунд на моем HTC Hero (все еще на Android 1.5 - уровень API 4), но хорошо на моем (2.1-update1) Nexus One

Вопросы:

  1. Почему этот тайм-аут? Какой-либо простой способ избежать этого?
  2. Я создавал свой BroadcastReceiver правильно в декларации? Я должен добавить что-то (для предотвращения этого тайм-аута)?
  3. Я должен абсолютно пойти для Сервиса для этого вида "Обновления с сети" функциональность? (рассматривающий эту статью: http://www.androidguys.com/2009/09/09/diamonds-are-forever-services-are-not/), Если ДА (я должен переключиться на сервис): Любые хорошие отрывки кода/учебного руководства для этого...

Как всегда, спасибо за Вашу справку.

H.

14
задан Mr_and_Mrs_D 1 April 2013 в 13:09
поделиться

2 ответа

Почему этот тайм-аут?

Вы работаете в основном потоке приложения. Вы не можете работать в основном потоке приложения дольше нескольких секунд. Кроме того, при этом вы снижаете производительность устройства (потому что вы работаете с приоритетом переднего плана ), например, вызывая потерю частоты кадров в играх или видео.

Есть ли простой способ избежать этого?

Не выполняйте значительную работу (> 100 мс) в основном потоке приложения. Пусть ваш BroadcastReceiver делегирует IntentService , возможно, WakefulIntentService .

Настроил ли я свой BroadcastReceiver? правильно в манифесте?

Пожалуйста, пожалуйста, пожалуйста, избавьтесь от android: process =: remote . Он вам не нужен, он вам не помогает и еще больше снижает производительность устройства.

Стоит ли мне обращаться за Услугами? для такого рода «Обновить из Интернета» функциональность? (учитывая это статья : http://www.androidguys.com/2009/09/09/diamonds-are-forever-services-are-not/ ) Если ДА (я должен переключиться на услугу): Любые хорошие фрагменты кода / учебника для это ...

ИМХО, да. Опять же, я написал это сообщение в блоге. Для примера см. Проект WakefulIntentService .

18
ответ дан 1 December 2019 в 13:21
поделиться

Для информации, я попробовал с новым потоком, и он работает, когда на Wifi (занимает около 1'30" для обновления данных, когда телефон спит, он не "убивается"!

//let's try with a new separate thread ?
        new Thread(new Runnable() {
            public void run() {
                Refresh_HIST_DATA();
            }
          }).start();

но НЕ работает на мобильном (GPRS), так как его убивают примерно через 10 секунд!

На данный момент это полурешение, и я попробую решение CommonsWare для более чистого/более устойчивого подхода...

Посмотрим, работает ли решение с новым потоком всегда хорошо или это просто удача (я тестировал только в течение пары часов) ...

Если у кого-то есть другое предложение, пожалуйста, опубликуйте его.

1
ответ дан 1 December 2019 в 13:21
поделиться
Другие вопросы по тегам:

Похожие вопросы: