Некоторые вопросы о GcmTaskService

Фон

Я хотел использовать новый API JobScheduler, который был представлен на Lollipop, но, к сожалению, у него нет официального порта для pre-Lollipop.

Однако существует GcmTaskService, который обеспечивает очень похожие функции.

Проблема

Этот API довольно новый, поэтому есть очень мало мест для поиска информации о том, как его использовать ( здесь и здесь).

Вопросы

У меня есть несколько вопросов об этом новом API:

  • Кажется, что для этого требуется Google Play Services ( здесь) (кроме случаев использования Lollipop версии Android, который будет использовать обычный JobScheduler). Что делать, если сервисы Google Play недоступны?

  • Кажется, что даже если я использовал "setPersisted (true)" для повторной задачи, при перезагрузке устройства задача не будет вызываться снова. Как так? EDIT: это потому, что я пропустил разрешение RECEIVE_BOOT_COMPLETED.

  • Что такое поведение задачи по умолчанию, если я не использую "setRequiredNetwork"? Это "NETWORK_STATE_ANY"?

  • docs говорят о том, что возвращается из onRunTask, я могу вернуть любые значения "RESULT_FAILURE", "RESULT_RESCHEDULE", "RESULT_SUCCESS" (информация здесь). Кажется, что оба параметра FAILURE и SUCCESS будут делать то же самое - удалите задачу из очереди. Это правда? Если да, то в чем же разница между ними? Они работают по-разному?

  • Используются ли TaskParams только для тега задачи? Могу ли я каким-то образом передать набор задач с помощью API? В противном случае мне нужно будет установить БД для хранения того, что должно быть передано в задачи, не так ли?

  • Возможно ли, чтобы приложение получило очередь задач? Я знаю, что это возможно с помощью adb, но возможно ли это с помощью API?

  • Говорят ( здесь), что каждая задача имеет wakelock длиной до 3 минут. Что делать, если задача требует больше? Должен ли он приобрести еще один вакелон для себя? Будет ли API предупреждать о выпуске wakelock? Вот что говорят документы:

Планировщик будет держать PowerManager.WakeLock для вашей службы, однако после трех минут выполнения, если ваша задача не была возвращена это будет считаться тайм-аутом, и wakelock будет выпущенный. Перенос вашей задачи на данный момент не будет иметь никакого эффекта. Если вы подозреваете, что ваша задача будет работать дольше, чем вы должны начать свой самостоятельно использовать или использовать какой-либо другой механизм; этот API предназначенный для относительно быстрых сетевых операций.

  1. Говорят ( здесь), что все сетевые задачи удаляются каждый раз, когда приложение обновляется/заменяется, и там это вызов для "onInitializeTasks", когда это происходит, и что вы можете повторно назначить их снова. Как перепланировать задания? Я не думаю, что могу даже получить список задач...

  2. Можно ли задание задавать предпочтение конкретному времени в течение дня? Например, между 14: 00-15: 00?

  3. Я заметил, что если вы планируете задачу, а затем принудительно останавливаете и/или очищаете данные приложения, задача все равно будет выполняться. Как я могу избежать такого поведения?

Ответ 1

вы можете найти ответы на большинство своих вопросов здесь.

https://github.com/jacktech24/gcmnetworkmanager-android-example/blob/master/README.md

Ответы, на которые не ответил,

7: вы не получите уведомление, когда wakelock будет удален, и, как говорится в документации, этот API предназначен только для коротких задач, если у вас есть больше времени, напишите свою собственную реализацию

9: Нет, вы не можете сейчас, API не позволяет это

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

Ответ 2

jacktech24 сделал действительно хорошую работу, но я тоже постараюсь, если будут какие-то затяжные вопросы.

  • Похоже, для этого требуется использовать Google Play Services (здесь) (кроме случаев использования Lollipop версии Android, в которой будет использоваться обычный JobScheduler). Что делать, если сервисы Google Play недоступны? *

    Вы не можете использовать этот API, если Google Play Services недоступен. Скорее, клиентская библиотека Google Play Services предназначена для запроса, чтобы пользователь загружал и устанавливал Службы Google Play, если обнаружил, что он отсутствует, но я не считаю, что GcmNetworkManager делает это.

  • Что такое поведение задачи по умолчанию, если я не использую "setRequiredNetwork"? Это "NETWORK_STATE_ANY"? *

    Описание javadoc, по умолчанию.

  • Документы говорят о том, что возвращается из onRunTask, я могу вернуть любые значения "RESULT_FAILURE", "RESULT_RESCHEDULE", "RESULT_SUCCESS" (информация здесь). Кажется, что оба параметра FAILURE и SUCCESS будут делать то же самое - удалите задачу из очереди. Это правда? Если да, то в чем же разница между ними? Они работают по-разному? *

    Единственное различие между этими 2 заключается в том, что в dumpsys оболочки adb будет отображаться то, что вы вернули, поэтому вы можете использовать это для устранения неполадок. Другая причина заключается в том, что если задача не работает, странно требовать, чтобы клиент возвращал "успех".

  • Используются ли "TaskParams" только для тега задачи? Могу ли я каким-то образом передать набор задач с помощью API? В противном случае мне нужно будет установить БД для хранения того, что должно быть передано задачам, правильно? *

    В следующей версии GmsCore необходимо поддерживать возможность добавления пакета в задачу.

  • Возможно ли, чтобы приложение получило очередь задач? Я знаю, что это возможно с помощью adb, но возможно ли это с помощью API?

    Нет, это невозможно. Вместо этого вы должны выполнить отмену, когда захотите, и если задачи нет, это будет no-op. Точно так же вы должны запланировать задачу в точке вашего кода, где вы бы запросили список задач. используйте setUpdateCurrent = false, чтобы убедиться, что он не обновляет ранее существовавшую задачу. AlarmManager работает аналогичным образом, так как вы устанавливаете будильник независимо от того, был ли уже установлен будильник - api был разработан, чтобы следовать этому.

  • Они говорят (здесь), что каждая задача имеет wakelock длиной до 3 минут. Что делать, если задача требует больше? Должен ли он приобрести еще один вакелон для себя? Будет ли API предупреждать о выпуске wakelock? Вот что говорят документы: *

    Да, приложение должно приобрести собственный wakelock, и все будет хорошо. Причина, по которой планировщик выпускает wakelock через 3 минуты, состоит в том, что на практике неограниченный тайм-аут wakelock приводит только к тому, что очень сложно отслеживать ошибки утечки батареи. Если вам понадобится более 3 минут, у вас есть достаточно сложный прецедент, который вы можете понять, как работают API-интерфейсы PowerManager, и вызывать самостоятельно приобретать()/release() (это действительно довольно просто, тот факт, что сетевой менеджер делает это потому что вы более вежливы, чем что-либо еще).

  • Они говорят (здесь), что все сетевые задачи удаляются каждый раз, когда приложение обновляется/заменяется, и когда это происходит, возникает вызов "onInitializeTasks", и вы можете повторно назначить их снова. Как перепланировать задания? Я не думаю, что могу даже получить список задач... *

    Вы перенести задачи так же, как вы их запланировали. Какую бы функцию вы не планировали, вызовите эту функцию из GcmTaskService # onInitializeTasks. Это было сделано для того, чтобы избежать затяжных задач при изменении логики приложения. Рассмотрим ситуацию, когда разработчик меняет расписание своей задачи и начинает использовать другой тег. Они должны будут отменить отмену (old_tag) после того, как они обнаружат обновление (которое им нужно будет добавить для большего количества кода), что означало бы, что им нужна ссылка на старый (неиспользуемый) тег даже в их новый код. Это означало бы, что тег является стабильным идентификатором, который не должен меняться при обновлении приложений, что не должно быть требованием для этого api.

  • Можно ли задание задавать предпочтение конкретному времени в течение дня? Например, между 14: 00-15: 00? *

    Нет, этот тип фонового планирования вызывает всевозможные проблемы с пастбищем по большим группам устройств. То есть если 1 устройство запускает работу в 15:00, что, вероятно, прекрасно. Но если 1x10e6 внезапно возникнет у вашего сервера серьезные проблемы.

  • Я заметил, что если вы планируете задачу, а затем принудительно останавливаете и/или очищаете данные приложения, задача все равно будет выполняться. Как я могу избежать такого поведения? *

    К сожалению, вы не можете, но это не является преднамеренным и должно быть изменено - не должно быть никакого способа запуска приложения после того, как пользователь явно остановил его.