Как исправить ошибку регистрации Google Cloud Messaging: SERVICE_NOT_AVAILABLE?

У меня возникла странная проблема: я давно использую GCM в своем приложении, и все работает отлично. Однако перед выпуском в Google Play я изменил имя своего приложения с com.android.testapp на com.android.recognition и после этого GCM прекратил работать. Сначала я получил ошибку GCM sender id not set on constructor и исправил ее, переопределив getSenderIds(Context context) , но теперь я не могу получить идентификатор регистрации. Вот сообщения из logcat: Введите описание изображения здесь

Как я могу это исправить? Когда я переключился на новый пакет, я изменил все в файле манифеста на новый пакет:

 <receiver android:name="com.google.android.gcm.GCMBroadcastReceiver" android:permission="com.google.android.c2dm.permission.SEND" > <intent-filter> <action android:name="com.google.android.c2dm.intent.RECEIVE" /> <action android:name="com.google.android.c2dm.intent.REGISTRATION" /> <category android:name="com.android.recognition" /> </intent-filter> </receiver> 

Так в чем проблема? Может ли переименование пакета приложения вызвать это или есть другая причина?

Solutions Collecting From Web of "Как исправить ошибку регистрации Google Cloud Messaging: SERVICE_NOT_AVAILABLE?"

В этой ошибке SERVICE_NOT_AVAILABLE указано, что GCM Service недоступна в текущем состоянии. Подождите и попробуйте через некоторое время.

Это происходит много раз (как и мой опыт), поэтому не беспокойтесь об этом.


См. Класс GCMConstants GCM Lib.

 /** * The device can't read the response, or there was a 500/503 from the * server that can be retried later. The application should use exponential * back off and retry. */ public static final String ERROR_SERVICE_NOT_AVAILABLE = "SERVICE_NOT_AVAILABLE"; 

Дополнительные сведения см. В разделе handleRegistration() GCMBaseIntentService

 private void handleRegistration(final Context context, Intent intent) { String registrationId = intent.getStringExtra(EXTRA_REGISTRATION_ID); String error = intent.getStringExtra(EXTRA_ERROR); String unregistered = intent.getStringExtra(EXTRA_UNREGISTERED); Log.d(TAG, "handleRegistration: registrationId = " + registrationId + ", error = " + error + ", unregistered = " + unregistered); // registration succeeded if (registrationId != null) { GCMRegistrar.resetBackoff(context); GCMRegistrar.setRegistrationId(context, registrationId); onRegistered(context, registrationId); return; } // unregistration succeeded if (unregistered != null) { // Remember we are unregistered GCMRegistrar.resetBackoff(context); String oldRegistrationId = GCMRegistrar.clearRegistrationId(context); onUnregistered(context, oldRegistrationId); return; } // last operation (registration or unregistration) returned an error; Log.d(TAG, "Registration error: " + error); // Registration failed if (ERROR_SERVICE_NOT_AVAILABLE.equals(error)) { boolean retry = onRecoverableError(context, error); if (retry) { int backoffTimeMs = GCMRegistrar.getBackoff(context); int nextAttempt = backoffTimeMs / 2 + sRandom.nextInt(backoffTimeMs); Log.d(TAG, "Scheduling registration retry, backoff = " + nextAttempt + " (" + backoffTimeMs + ")"); Intent retryIntent = new Intent(INTENT_FROM_GCM_LIBRARY_RETRY); retryIntent.putExtra(EXTRA_TOKEN, TOKEN); PendingIntent retryPendingIntent = PendingIntent .getBroadcast(context, 0, retryIntent, 0); AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE); am.set(AlarmManager.ELAPSED_REALTIME, SystemClock.elapsedRealtime() + nextAttempt, retryPendingIntent); // Next retry should wait longer. if (backoffTimeMs < MAX_BACKOFF_MS) { GCMRegistrar.setBackoff(context, backoffTimeMs * 2); } } else { Log.d(TAG, "Not retrying failed operation"); } } else { // Unrecoverable error, notify app onError(context, error); } } 

На эту проблему ответили, в моем случае это было немного сложнее.

  1. Убедитесь, что у вас есть активное интернет-соединение
  2. Убедитесь, что у вас есть разрешение на использование в вашем манифесте
  3. Убедитесь, что имя пакета правильно, как упоминал Эран
  4. Время устройства настроено правильно. Даже если все будет идеально, оно не сработает, если часы устройства установлены неправильно.

Неправильные часы вызвали проблему для меня. 🙂

Убедитесь, что вы изменили имя пакета в части разрешений манифеста:

 <permission android:name="YOUR_PACKAGE_NAME.permission.C2D_MESSAGE" android:protectionLevel="signature" /> <uses-permission android:name="YOUR_PACKAGE_NAME.permission.C2D_MESSAGE" /> 

У меня была аналогичная ошибка из-за неправильного имени пакета в этой части.

SERVICE_NOT_AVAILABLE – одна из самых неприятных проблем с облачными сообщениями Google. Это исключение, GoogleCloudMessaging.register(SENDER_ID) , вызов функции, который регистрирует устройство для push-уведомлений и возвращает идентификатор регистрации.

  1. SERVICE_NOT_AVAILABLE может означать, что устройство пользователя не может прочитать ответ на запрос регистрации, или код ошибки 500/503 был возвращен с сервера. Разработчики не могут исправить эту ошибку, потому что она находится в конце Google, поэтому мы можем вслепую предположить, что пользователь должен попробовать снова через несколько часов.
  2. SERVICE_NOT_AVAILABLE может произойти на некоторых устройствах, даже если регистрация прошла успешно. Это можно устранить, применяя приемник широковещательной передачи, чтобы поймать токен при сбое вызова. Я применил это решение и, возможно, устранил проблему для некоторых пользователей, но все же я получил много других жалоб SERVICE_NOT_AVAILABLE.
  3. SERVICE_NOT_AVAILABLE может произойти из-за устаревшей или отсутствующей библиотеки Google Play Services на устройстве. В этом случае приложение может теоретически уведомить пользователя об обновлении сервисов Google Play, открыв соответствующее приложение в Google Play. Тем не менее, приложение не знает, что именно поэтому SERVICE_NOT_AVAILABLE был брошен, поэтому он не может вслепую перенаправить пользователя на страницу приложения Google Play Services в Google Play.
  4. SERVICE_NOT_AVAILABLE может возникать, когда часы устройства не синхронизируются с сетью. Опять же, разработчики не знают, что это точная проблема, поэтому мы можем вслепую предложить пользователю проверить синхронизацию их системных часов, надеясь, что они являются одними из немногих, чьи часы не синхронизированы.
  5. SERVICE_NOT_AVAILABLE может произойти, когда корневой пользователь удалил приложение Hangouts / GTalk с их устройства (потому что они считали его вирусом). GCM реализуется и обрабатывается Hangouts / GTalk, поэтому использовать GCM без него невозможно.
  6. SERVICE_NOT_AVAILABLE может возникнуть, если пользователь запускает устройство, на котором не установлены Google API (например, Amazon Kindle). Здесь нечего делать, эти пользователи никогда не получат push-уведомления из вашего приложения.

Подробнее: http://eladnava.com/google-cloud-messaging-extremely-unreliable/

Одних только этих вопросов было достаточно, чтобы заставить меня искать альтернативы GCM. Я получаю 1-звездочный обзор в своем приложении каждый день или два, с комментарием, содержащим сообщение об ошибке, отображаемое при вызове SERVICE_NOT_AVAILABLE. Я ничего не мог сделать, чтобы помочь этим пользователям, потому что большинство из них получало его по причинам, выходящим из-под их контроля.

Альтернатива облачным сообщениям Google

Pushy ( https://pushy.me/ ) – это автономный шлюз push-уведомлений, полностью независимый от GCM. Он поддерживает собственное подключение к фоновому сокету, как и GCM, для получения push-уведомлений. Основным протоколом является MQTT, чрезвычайно легкий протокол pub / sub, использующий очень небольшую пропускную способность сети и аккумулятор.

Огромное преимущество Pushy заключается в том, что код для отправки push-уведомления (с сервера) и регистрации устройства для push-уведомлений фактически взаимозаменяем между GCM и Pushy. Это делает его очень простым переключиться на Pushy после внедрения GCM и вынудить его отказаться от его нестабильности.

(Полное раскрытие: я основал Pushy для своих собственных проектов и понял, что многие приложения выиграют от такой услуги)

Для меня – время устройства было неправильным. Я изменил настройки устройства для использования «Автоматическая дата и время», попробовал снова и все хорошо.

ура

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

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

 public class MyCustomApp extends Application { @Override public void onCreate() { super.onCreate(); PushService.register(this); //BAD IDEA, don't register pushes in Application Class } } 

У меня была аналогичная проблема. Работал отлично на google nexus (Android 4.4.2), но не на галактике Samsung s3 (Android 4.1.2). Я получил SERVICE_NOT_AVAILABLE при регистрации на Samsung. Оказалось, что время на Samsung отключено. Он не был настроен на автоматическое обновление с помощью Network Time. Как только я решил, что GCM работает как шарм. Спасибо – Umesh

В моем случае решение заключалось в том, чтобы добавить манифест нового действия-фильтра-действия, РЕГИСТРАЦИЯ, на https://snowdog.co/blog/dealing-with-service_not_available-google-cloud-messaging/

  <receiver android:name=".RemoteNotificationReceiver" android:permission="com.getset.getset.c2dm.permission.SEND" > <intent-filter> <action android:name="com.getset.getset.c2dm.intent.RECEIVE" /> <action android:name="com.getset.getset.c2dm.intent.REGISTRATION" /> <category android:name="com.getset.getset" /> </intent-filter> </receiver> 

Я должен признать, что я удивлен, что это работает, поскольку оно отсутствует в учебном пособии, но его вывод определенно превращает успешный идентификатор регистрации в исключение.

Примечание: использование эмулятора Nexus 5 API 21 (Lollipop).

Для меня была проблема связи. Изменение интернет-соединения решило мою проблему

Для меня я перешел на «Доступ к фоновым данным» для служб Google, установив флажок «Ограничить исходные данные» в опции «Использование данных» на моем Galaxy S4. Как только я включил его, проблема была решена в сети подвалов. На Wifi он работал нормально.

Для меня проблема заключалась в том, что телефон не был подключен к Интернету. Я отсоединяюсь и подключаюсь к Wi-Fi, а также проверял подключение к браузеру и тестировал его снова. Работал как шарм 🙂

Я включил «Доступ к фоновым данным» для служб google. Снимите флажок «Ограничить исходные данные» в опции «Использование данных». Это работает для меня!

Для меня goolge заблокировал мой IP! Мне пришлось сбросить свой DSL-коннект, чтобы получить новый IP-адрес из пула, и все снова сработало, idk, почему они заблокировали меня, возможно, для тестирования многих приложений? В любом случае сейчас работает, надеюсь, это поможет кому-то еще 🙂

Для меня проблема SERVICE_NOT_AVAILABLE была в моем проекте приложения из-за класса приемника. Поэтому я решил после внедрения приемника, как показано ниже. <receiver android:name="receiver name" android:permission="com.google.android.c2dm.permission.SEND"> <intent-filter> <action android:name="com.google.android.c2dm.intent.RECEIVE"/> <action android:name="com.google.android.c2dm.intent.REGISTRATION"/> <category android:name="your package"/> </intent-filter> </receiver> Я надеюсь, что Вам поможет 🙂 .

После долгой борьбы мне удалось разобраться с этой проблемой. Убедитесь, что приложение Google Play Services обновлено и что его фоновая синхронизация не отключена на вашем телефоне.