Android 对GCM令牌更新过程感到困惑

Android 对GCM令牌更新过程感到困惑,android,google-cloud-messaging,Android,Google Cloud Messaging,试图实现谷歌最新的GCM服务。我读过。我还下载并分析了。综上所述,我明白了以下几点: InstanceId服务提供API来生成gcm注册令牌您可以将生成的令牌发送并存储在应用服务器中 如前所述,这些令牌可以偶尔从客户端和instanceId服务端进行更改。要处理此问题,您必须实现InstanceIDListenerService,InstanceID提供程序将调用onTokenRefresh,您只需编写逻辑以获取新令牌并将其发送到服务器() 如果您的应用程序服务器发送较旧的注册id,则GCM服务

试图实现谷歌最新的
GCM
服务。我读过。我还下载并分析了。综上所述,我明白了以下几点:

  • InstanceId
    服务提供API来生成
    gcm注册令牌
    您可以将生成的令牌发送并存储在应用服务器中
  • 如前所述,这些令牌可以偶尔从客户端和instanceId服务端进行更改。要处理此问题,您必须实现
    InstanceIDListenerService
    ,InstanceID提供程序将调用
    onTokenRefresh
    ,您只需编写逻辑以获取新令牌并将其发送到服务器()
  • 如果您的应用程序服务器发送较旧的注册id,则GCM服务器会向您的设备发送一个名为
    canonical_id
    ()(这是从设备发送的最后一个注册id)。您必须用此规范id替换服务器中的现有令牌
  • 下面是我的问题:

  • InstanceId.getToken
    如果应用程序未卸载,则返回相同的令牌;如果令牌未更改,则返回速度相当快。那么,我可以在每次启动应用程序时调用
    注册服务吗?这样我就可以保证一直使用最新的代币
  • 如果在应用程序未连接到play store(没有互联网或其他东西)的情况下进行刷新,则如何进行
    onTokenRefresh
    InstanceId
    提供程序是否重试?这有文件记录吗?如果同时发送推送通知,会发生什么情况
  • 什么是
    规范id
    ?它是为设备生成的最新令牌(由客户端或提供者端的
    InstanceID.getToken
    启动)?如果
    canonical\u id
    确实是最新的gcm令牌,那么当您发现提供了
    canonical\u id
    时,您仍然可以分析推送通知数据并更新您的应用程序服务器,那么
    onTokenRefresh
    实现需要什么
  • 我可以在每次启动应用程序时呼叫注册服务吗

    更好的解决方案是优先保存您已经成功注册了令牌的内容。只有在您尚未注册的情况下,才启动注册服务

    String token = InstanceID.getToken(...);
    //send to server
    getSharedPreferences(context).edit().putBoolean(PREFIX_PREF_GCM_KEY, true).apply();
    
    然后启动应用程序时,只需检查
    PREFIX\u PREF\u GCM\u KEY
    是否为真

    如果在应用程序未连接到play store(没有互联网或其他)时发生刷新,onTokenRefresh将如何进行

    我猜是由系统来调用这个
    刷新过程的。文件规定:

    当系统确定令牌需要刷新时调用。应用程序应该调用getToken()并将令牌发送到所有应用程序服务器。 这不会被频繁调用,它是键旋转和处理特殊情况所必需的。 系统将限制所有设备的刷新事件,以避免令牌更新导致应用程序服务器过载

    它可以在你的应用程序处于睡眠状态时调用(与你收到通知时相同),但你应该测试它,看看它是否按预期工作

    我还认为,您可以假设,虽然没有internet连接,
    系统
    不会调用
    onRefreshToken
    ,原因很简单,它将无法接收更新通知。。。但和往常一样,您应该自己测试更新过程是否有效,以及在什么条件下有效

    什么是规范的id

    可能是您在服务器中错误地为同一设备注册了多个注册id,例如,
    onRefreshToken
    ,在未删除旧的令牌的情况下注册了令牌。
    如果您将使用旧的
    注册id
    发送消息,google将告诉您应该将其更改为新的-规范id

    谢谢!我知道您可以保留
    SharedReferences
    ,因为我一直在为较旧的GCM API(
    GCM.register
    )执行此操作。然而,现在我对这个令牌更新感到困惑。我的基本问题是发送的canonical_id是否与该设备的最新令牌相同。因为如果是这样的话,可能就不需要onRefreshToken实现了。为什么不呢?这是一个使您能够在问题出现之前解决问题的过程(在使用旧令牌之前更新令牌)。如果您无法在服务器中更新新的刷新令牌,如果您插入了新的刷新令牌但没有删除旧令牌。简言之,如果出现错误,唯一可能的情况是-
    -这不是真的,请阅读我的帖子、评论和谷歌文档,这取决于你用新的注册id更新你的服务器,这样你就有很多可能同时拥有注册id和规范id“我假设一切都做得对”-哈哈(;如果你觉得答案正确,请不要忘记接受,或者投票赞成,谢谢