> InstanceId服务提供API以生成gcm注册令牌您发送&将此生成的令牌存储在您的应用服务器中
>这些令牌可以偶尔从客户端和instanceId服务端更改一次,如here所述.要处理此问题,您必须实现InstanceIDListenerService,InstanceID提供程序将调用onTokenRefresh,您只需编写逻辑即可获取新令牌并将其发送到服务器(Google’s sample app )
>如果您的应用服务器发送较旧的注册ID,那么GCM服务器会发送您的设备,这就是canonical_id(as mentioned here)(这是设备发送的最后一次registration_id).您必须使用此canonical_id替换服务器中的现有令牌.
现在,以下是我的问题:
>如果未卸载应用程序,InstanceId.getToken似乎返回相同的令牌,如果令牌未更改,则返回非常快.那么,每次启动应用程序时都可以调用RegistrationIntentService吗?这样我就可以保证一直使用最新的令牌.
>如果您的应用未连接到Play商店(没有互联网或其他东西),onTokenRefresh如何刷新? InstanceId提供商是否重试?这是在某处记录的吗?如果同时发送推送通知会发生什么?
> canonical_id究竟是什么?它是为设备生成的最新令牌(由客户端或InstanceId提供者端的InstanceID.getToken启动)?如果canonical_id确实是最新的gcm令牌,那么onTokenRefresh实现的需求是什么,因为如果找到canonical_id,你可以分析推送通知数据并更新你的app服务器?
解决方法
can I call the RegistrationIntentService every time I start the app?
更好的解决方案是优先保存您已设法注册令牌.仅在您尚未注册时才启动RegistrationIntentService.
String token = InstanceID.getToken(...); //send to server getSharedPreferences(context).edit().putBoolean(PREFIX_PREF_GCM_KEY,true).apply();
然后当你启动你的应用程序时,只需检查PREFIX_PREF_GCM_KEY是否为真
How does the onTokenRefresh if refresh happens while your app is not connected to the play store (no internet or something)
Called when the system determines that the tokens need to be refreshed. The application should call getToken() and send the tokens to all application servers.
This will not be called very frequently,it is needed for key rotation and to handle special cases.
The system will throttle the refresh event across all devices to avoid overloading application servers with token updates.
它可以在您的应用程序处于睡眠状态时调用(与收到通知时相同),但您应该对其进行测试,并确保它按预期工作.
我也认为你可以假设,虽然没有互联网连接,系统不会调用onRefreshToken,原因很简单,因为它无法接收更新通知……但是你应该一如既往地自己测试一下更新过程的工作原理和条件.
What exactly is a canonical_id?
可能是因为您错误地为服务器中的同一设备注册了多个注册ID – 例如 – onRefreshToken – 注册了一个令牌而没有删除旧令牌.如果您使用旧的registartaion_id发送邮件,Google会通知您应将其更改为新邮件 – canonical_id