如何将我的服务器设置为仅接受来自我自己的客户端应用程序的请求?(类似于 SSL 客户端证书)

信息安全 tls 证书 证书固定
2021-08-27 10:54:58

我想让我的服务器 API 只接受来自我自己的应用程序的请求,以防止我的服务的其他“流氓”客户端。

据我了解,执行此操作的方法是使用应用程序发送的“客户端证书”,并且 Web 服务器配置为进行验证。

但是,我在 Heroku 中托管我的应用程序,并且我相信这样做是不可能的,所以我正在寻找能够让我实现这一目标的尽可能好的东西。

我想也许我可以有一个密钥对,其中客户端使用私钥签署某个商定的令牌(加上一些随机盐,这样加密的字符串总是不同的),服务器使用公钥来验证令牌(并拒绝重复的盐以防止重播)。或者客户端可能使用其私钥或类似的东西签署整个请求。

这个想法是,即使有人设法绕过我们的 SSL pinning(可能使用 iOS 终止开关之类的东西)并检查我们的流量并弄清楚我们的 API 是如何工作的,除非他们对二进制文件进行逆向工程,否则他们仍然无法调用我们提取该证书/私钥。我知道这样做是可能的,我只是想设置尽可能多的障碍。

有什么好的方法可以做到这一点?

4个回答

此类问题适用于Cargo-Cult Security类型的“解决方案”。

在现实世界中,没有可能的机制可以阻止恶意客户端连接到您的服务。VPN 是一种经过验证的安全系统,允许受信任的客户端访问受信任的网络,但互联网本质上是不可信的。攻击者将有权访问嵌入在您的应用程序中或存储在应用程序内存中的任何秘密,TLS 客户端证书依赖于秘密。

在设计 Web 服务时,永远不要忘记:“客户端是攻击者,永远不能被信任。 ”如果你犯了这个错误,那么你需要回到绘图板上。

笔记

该答案仅适用于所述假设。我是根据问题的明确措辞制作它们的,这明确允许不减轻已知的攻击向量。

安全性是资产受损时的损失价值与对手为实现此类妥协而愿意付出的努力(包括成本等)之间的相对平衡。决定这种平衡是作者的特权,因为他们对利益相关者有全面的了解。

假设

您试图减轻的威胁是可以读取/篡改自己的通信、冒充客户端但不能对二进制文件内容进行逆向工程的对手之一(由于缺乏技术能力或缺乏意愿)。

TL;博士

HMAC(message | nonce, key)连同客户端消息/随机数“明文”(通过 TLS,但没有任何进一步的加密)。

详细解答

您的问题是authentication之一,但您似乎正试图通过加密来解决它(是的,在某些情况下存在一些交叉,但将两者分开会使答案更容易)。

如果密钥(不是非对称私钥;只是一个足够大的、加密安全的随机数)存储在二进制文件中(正如您使用公钥/私钥对提出的那样),那么它不会通过对HMAC /明文对。

您的服务器也知道密钥,计算接收到的消息的 HMAC,并丢弃任何无效的客户端通信。nonce 在发送消息之前由服务器提供给客户端,并且是唯一的。它的作用是防止被截获消息的重放。

警告

如前所述,在其他答案/评论中,仍然可以从二进制文件中获取密钥。对于那些感兴趣的人,有一种非常酷的技术可以计算二进制所有区域的熵,然后将线性位置映射到希尔伯特曲线机器代码区域将具有比“关键”区域相对较低的熵。Chris Domas 在他的一个视频中展示了这一点;可能是他的TED 演讲,虽然我不记得了(无论哪种方式都可以观看 TED 视频)。

您可以使用任何隧道机制来接受服务器端的特定 IP,或者只需将防火墙配置为接受受信任的客户端列表。

使用OAuth2.0它不仅授权用户,还授权具有client_idclient_key属性的客户端应用程序。