从移动应用程序使用AWS(特别是S3)的首选方式是什么?

直接在应用程序代码中添加AWS访问密钥和密钥绝对不是一个好方法,主要是因为应用程序驻留在用户设备上(与服务器端代码不同),并且可以进行反向devise以获取证书,然后可能会被滥用。

尽pipe我在任何地方都能find这些信息,但却无法find解决这个问题的明确办法。 我有什么select? 我读了关于临时证书的令牌自动售货机架构,但我不相信它是更好的。 如果我可以反向devise密钥,那么我可以对请求临时凭证的代码进行反向工程。 而且一旦我拥有一组临时的证书来访问S3,我就像拥有密钥一样好。 我可以一次又一次地申请临时证书,即使它们过期很快。 总之,如果一个应用程序可以做一些事情,我可以像恶意用户一样做。 如果有的话,TVM可以在pipe理上更好一些(轮换凭证,在违规情况下更换密钥等)。 请注意,我们可以对密钥施加相同的访问限制,因为我们计划在TVM临时证书的情况下执行这些限制。

此外,如果亚马逊不希望人们直接在应用程序中使用密钥,为什么不在他们的SDK中阻止它,并强制使用TVM或正确的解决scheme。 如果你要走的路,人们将使用它。 我读了几篇这样的文章,不知道为什么?

我主要从网页背景,所以我的理解可能有点有缺陷。 请帮助我理解这是否更好,以及是否有一个完美的(或可能是好的)解决scheme可用于此问题。

PS:是否有TVM的轨道实施?

在应用代码中embeddedS3密钥是非常危险的。 任何人都可以轻松地从您的应用程序代码中获得该密钥(不需要反向工程或高级技能),即使encryption存储它仍然是妥协,只是有人需要努力(取决于如何encryption)。

我希望你明白使用临时凭证访问Amazon(S3等)资源(主要是安全性+其他一些像没有应用程序更新等)的优势。 我认为你对从TVM获取临时证书的过程感到困惑,以及如何将密钥embedded到代码中更安全。

每个使用TVM的客户首先需要注册您所托pipe的TVM服务器实施。 App(使用TVM客户端)和TVM服务器之间的通信是通过SSL进行的。

首先,应用程序通过提供UUID和密钥向TVM注册。 请注意,秘密密钥没有embedded在应用程序代码(我认为是你的困惑的主要原因),但在注册(和hex编码)随机生成(使用SecRandomCopyBytes生成一个密码安全的随机字节数组)。

一旦设备用TVM成功注册,客户端TVM将生成的UDID和密钥存储在iOS中的钥匙串和Android中的共享首选项中。 iOS中的钥匙串是iOS提供的安全(encryption)存储信息(主要是密钥,密码等)的共享存储。

在注册和UDID /密钥存储之后,App可以通过发送UDID,密码签名和时间戳从TVM获得令牌。 密码签名是使用密钥从时间戳生成的HMAC哈希 。 TVM可以使用UDID查找密钥并使用它来validation签名。 然后,TVM通过发送回使用秘密密钥(使用AES )encryption的临时证书进行响应。 应用程序使用密钥解密临时凭证,然后可以使用它们访问授权临时凭证的任何AWS服务。 最终,这些临时凭证的到期时间将达到,如果需要,应用程序可以获得新的临时凭证。

我不确定签名的URL与TVM有什么关系,因为我不明白这些概念是100%,但签名的URL真的解决了我的问题。 我需要一种机制来提供networking应用程序和移动应用程序数据,而不允许滥用凭证。 把密钥放在代码中确实是一个非常糟糕的主意,因为它可能会给公司带来巨额账单。

经过3天的广泛研究,我发现了一个简单的,似乎是可靠和相对安全的解决scheme: 签名的URL 。 这个想法是,一个非常轻的后端可以生成一个临时的URL,在有限的时间内授予用户对特定资源的访问权限。 所以这个想法很简单:

  • 用户要求我们的后端rest电话,他想要一个特定的资源

  • 后端已经被AWS S3授权

  • 后端为用户生成一个临时URL,并在Rest响应中发送

  • 用户使用该URL直接从AWS获取数据

一个即插即用的Python实现可以在这里find,稍作修改,我不得不使用: 在这里 。

当然还有一件事要弄清楚,在我们知道我们可以授予URL之前,我们如何授权用户,但这又是一双鞋子。

理想情况下,您应该使用Cognito Identity来实现此目的以及适当的策略。 它应该与iOS和Android SDK中的S3TransferUtilityS3TransferManager一起使用。 这将允许背景上传和下载。 Cognito用于访问AWS资源的临时凭证,并且是免费的。 另外,如果您想要安全访问,则可以使用UserPools或Google,Facebook等提供商进行联合。

谢谢,罗汉