如何将秘密 API 密钥存储在应用程序的二进制文件中?

Posted

技术标签:

【中文标题】如何将秘密 API 密钥存储在应用程序的二进制文件中?【英文标题】:How to store a secret API key in an application's binary? 【发布时间】:2011-07-28 08:57:43 【问题描述】:

我正在为 Mac OS X 创建一个 Twitter 客户端,并且我有一个消费者密码。据我了解,我不应该分享这个 secret 密钥。问题是当我将它作为字符串文字放入我的应用程序并使用它时,如下所示:

#define QQTwitterConsumerSecret @"MYSECRETYOUMAYNOTKNOW"

[[QQTwitterEngine alloc] initWithConsumerKey:QQTwitterConsumerKey consumerSecret:QQTwitterConsumerSecret];

它位于我的应用程序二进制文件的数据部分。黑客可以阅读此内容、反汇编应用程序等。

是否有任何安全的方式来存储消费者机密?我应该加密吗?

【问题讨论】:

如果你加密它,你仍然需要隐藏加密密钥。 @Null 设置黑客不知道加密算法怎么办? 除非密钥是指某种特权帐户,否则没有理由对其保密甚至存在,而 Twitter 只是愚蠢的。如果它确实引用了特权帐户,则它不属于您共享的应用程序。 @Radek Pro-Grammer:你为什么用C标记这个?那个代码 sn-p 是objective-c @Radek 在加密中总是最好假设对手完全了解所使用的加密技术,并解决这个问题。 【参考方案1】:

没有真正完美的解决方案。无论你做什么,都有专门的人可以窃取它。

甚至是 iPhone/iPad/android/mac/等的 Twitter。里面有一个密钥,他们可能只是以某种方式掩盖了它。

例如,您可以将其分解为不同的文件或字符串等。

注意:使用十六进制编辑器可以读取二进制格式的 ascii 字符串,这是最简单的方法。通过将其分解为不同的部分或使用函数调用来创建密钥通常会使该过程更加困难。

【讨论】:

值得注意的是,这就是可以撤销 API 访问密钥的原因。如果它确实被盗(这是一个问题),只需撤销密钥并将带有新密钥的更新应用推送给您的用户。 @DanielDickison 还值得注意的是,推出新版本的移动应用程序需要时间,尤其是对于 Apple。【参考方案2】:

您可以对它进行 base64 编码来混淆它。或者,更好的主意,生成密钥而不是仅仅存储它 - 编写如下内容:

char key[100];
++key[0]; ... ; ++key[0]; // increment as many times as necessary to get the ascii code of the first character
// ... and so on, you get the idea.

然而,一个真正优秀的黑客无论如何都会找到它;真正保护它不被别人看到的唯一方法是使用安全的哈希函数,但是你也无法检索它:)

【讨论】:

在这种情况下,最安全的哈希函数是:int hash(char *s) return 0; 这也是最糟糕的,因为它总是会产生碰撞 我的观点是,有损/不可逆哈希对于存储您需要作为身份验证令牌传输的密钥是无用的(而不是仅使用它来验证知道秘密的其他人)。【参考方案3】:

您不应在并非仅在您的服务器上运行的应用程序中使用秘密 api 密钥。

即使它完全隐藏.. 您也可以随时窥探通过网络传输的数据。而且由于它是您的设备,您甚至可以篡改 SSL(中间人使用由自定义 CA 创建的证书,该证书已添加到设备的受信任 CA 列表中)。或者,您可以挂接 SSL 库以在实际加密之前拦截数据。

【讨论】:

那么就不可能创建桌面推特客户端了:O @Radek 如果您有桌面客户端连接到您的服务器,则不会。 @Null 集:好点。现在我想起来了,这几乎肯定是 Twitter 想要你做的。当然,它会让你的应用侵犯用户的隐私(通过你的服务器传输他们的数据)并在你的服务器离线时停止工作,因此这是一个可怕的设计...... 在最一般的情况下,您的服务器将希望提供原始服务器 (Twitter) 提供的所有服务。现在您必须使用您的服务器对客户端应用程序进行身份验证。这导致了与我们开始时完全相同的问题。 其实你只需要做你“不应该做的”。【参考方案4】:

一个很晚的答案......

如果您设置自己的服务器,则可以使用它来帮助您的桌面应用程序在 twitter 上获得用户的授权,而无需共享(即:嵌入)您的密钥。

您可以使用这种方法:

当用户安装您的桌面应用程序时,她必须在 twitter 和您的服务器上注册它 *) *) 应用程序要求服务器生成令牌请求 URL *) 服务器将生成的 URL 发送到应用程序 *) 应用程序将用户定向到授权 URL *) 用户在 Twitter 上授权您的应用并将生成的 PIN 粘贴到其中 *) 使用您的应用程序的 PIN 码获取令牌 *) 所有进一步的通信都使用令牌,不涉及您的服务器

注意:应用程序使用您服务器的用户凭据(例如:ID 和密码)登录到您的服务器。

【讨论】:

以上是关于如何将秘密 API 密钥存储在应用程序的二进制文件中?的主要内容,如果未能解决你的问题,请参考以下文章

当我推送到 GitHub 时如何处理秘密 API 密钥,以便在克隆存储库时我的项目仍然有效?

什么是最安全的存储和使用API 密钥和秘密的方法?

API 密钥和秘密密钥如何工作?如果我必须将我的 API 和密钥传递给另一个应用程序,它会安全吗?

在Swift上存储API密钥的位置?

服务如何生成和使用公共和秘密 API 密钥?

JavaCard 存储(秘密)数据