服务不可用时如何在 Google 云消息传递 Api 中实施退避

How to implement Back Off in Google Cloud Messaging Api when Service Not Available

我已经使用 Google 云消息传递 Api 来实现 GCM 功能,但我需要修复服务不可用错误。为此,我正在使用回退,但在让线程休眠后我不知道。我怎样才能再次设置注册设备。

 private void registerInBackground() {
        new AsyncTask<Void, Void, String>() {
            @Override
            protected String doInBackground(Void... params) {
                String msg = "";
                try {
                    if (gcm == null) {
                        gcm = GoogleCloudMessaging.getInstance(SettingsActivity.this);
                    }
                    regid="";
                    regid = gcm.register(SENDER_ID);
                    msg = "Device registered, registration ID=" + regid;

                    // You should send the registration ID to your server over HTTP, so it
                    // can use GCM/HTTP or CCS to send messages to your app

                    sendRegistrationIdToBackend();

                    // For this demo: we don't need to send it because the device will send
                    // upstream messages to a server that echo back the message using the
                    // 'from' address in the message.

                    // Persist the regID - no need to register again.
                    storeRegistrationId(SettingsActivity.this, regid);
                } catch (IOException ex) {
                    Log.e("Error on register",""+ex);
                    msg = "Error :" + ex.getMessage();
                    ex.printStackTrace();
                    // If there is an error, don't just keep trying to register.
                    // Require the user to click a button again, or perform
                    // exponential back-off.


                    if(ex.getMessage().equals(ERROR_SERVICE_NOT_AVAILABLE))
                    {
                        try
                        {
                            for(int n=0;n<5;n++)
                            {
                                Log.e("service_error","retrying:"+(n+1)+"time");
                                Thread.sleep((1 << n) * 1000 + randomGenerator.nextInt(1001));
                               /* gcm=GoogleCloudMessaging.getInstance(SettingsActivity.this);
                                regid=gcm.register(SENDER_ID);
                                Log.e("back off reg id:",""+regid);*/

                            }
                        }
                        catch (Exception e)
                        {
                            e.printStackTrace();
                            Log.e("back off error",""+e);
                        }
                    }


                }
                catch (Exception e)
                {
                    Log.e("Erron on register main exp",""+e);
                    e.printStackTrace();
                }
                Log.i("reg resp",msg);
                return msg;
            }

您可以在外部 try-catch 上放置一个 for 循环,以便它在 register() 调用失败时进行迭代。一旦 regid 有一个值来打破循环,你将不得不 return msg

实现指数退避的另一种方法是通过 do-while 循环。示例参见 this method。您仍然需要将 register() 调用包含在 try-catch 语句中。