最佳实践取决于确切的用法。
我从您的问题中收集到的是,您有一个向您发送 GPS 数据和时间的应用程序,例如“足迹”应用程序。您要确保您没有收到虚假数据,因此您要确保数据来自您的真实客户而不是虚假数据。
好吧,不幸的是,正如其他答案所述,这是不可能的。鉴于您的应用程序的 APK 文件,有人可以将其反编译成 Java 源代码,这可能不如您自己的源代码那么优雅,但绝对可行。然后,他们可以使用您的代码构建自己的应用程序,以您期望的方式与您的应用程序进行通信,并使用它来为您提供虚假数据。
因此,您用于数据传输的任何方案都不应信任客户端。相反,它应该信任用户。
考虑这个解决方案;您的应用程序服务器使用受信任的公钥证书进行签名(在这种情况下,它可能是受信任的,唯一原因是您的应用程序知道应该提供的确切证书;这称为“证书固定”,无论您是否获得了由全球 CA 签署的证书)。根据要求,它会将该证书提供给任何要求它的人;这是公共信息,你可以在互联网上的每个黑客论坛上贴上这个东西,它的安全性也不会降低。您的客户端使用此证书来协商安全通信隧道;这是非常标准的东西。
现在,你有保密了。你需要真实性;如果您不确定对方是谁,那么没有人可以听到你们两个之间的对话也没关系。因此,一旦通道打开,您期望的下一件事就是包含用户凭据的身份验证请求。如果会话未通过身份验证,您应该拒绝任何发送 GPS 数据的请求。用户在此类请求中提供的凭据可能是他们的用户名和密码、他们手机的 IMEI 或 MAC 地址、来自加密密钥卡的 10 位代码,任何您认为正确确保只有特定用户才能使用的必要信息提供这些凭据。
一旦您拥有这些凭据并验证它们是否符合预期,无论您想要这样做,您都可以将它们发回一个“身份验证令牌”。这与用于任何其他打开会话的随机数一样简单。V4 GUID 也是一个不错的选择。此标识符将作为在此会话期间在此通道上发送或接收数据的任何请求的一部分,它将仅在此特定通道上被接受,并且仅在此唯一会话打开时才被接受。
一旦所有这些都设置好,通过该会话的安全通道进行的任何服务调用(包括正确的身份验证令牌)通常都可以被信任。您可能应该再包括一件事,这是一种防止重放攻击的措施。攻击者不必通过简单地重复已经说过的话来确切地知道来回发送的内容来搞砸你。因此,为了确保您的系统无论发送多少次都只处理一次唯一消息,每条消息都应该包含一个随机数,一次使用的唯一值。一个简单的序列计数器值,构成请求结构的一部分并由安全通道加密,就足够了;然后,您所要做的就是忽略序列号不是您希望从客户端接收到的下一个消息的任何消息(这可能存在一些固有的容错性,但永远不要接受来自同一服务器的相同类型的服务请求具有相同序列号的客户端两次)。