我正在用 PHP/MySQL 开发本地内联网系统来管理我们的客户数据。看来最好的做法是在输入 MySQL 服务器上的敏感数据时对其进行加密。
不过,我不清楚在保证数据易于访问的情况下,什么才是实现这一目标的最佳方法。
这似乎是一个很难回答的问题:密钥存储在哪里?如何最好地保护密钥?如果密钥存储在每个用户的机器上,如果机器被利用,如何保护它?如果密钥被利用,如何更改密钥?
如果密钥要存储在数据库中,如何保护它?用户如何访问它?
答案1
实际上,MySQL 中没有任何内置功能可以处理复杂的加密密钥设置。您需要在自己的 PHP 和/或浏览器端(javascript?)代码中实现大部分加密逻辑。
但您所说的担忧有点奇怪:似乎您唯一真正担心的是来自远程客户端台式机/笔记本电脑工作站的 SQL 注入或暴力破解(我猜是密码猜测)攻击。这让我怀疑您已经计划了一些其他未提及的安全措施,并且您已经分析了可能的入侵途径。
首先,我假设您有防火墙规则保护 MySQL/PHP 主机免受来自未经批准的远程客户端 IP 的任何访问。如果我没记错的话,您只担心来自受感染用户工作站的攻击是有道理的。
此外,我假设您了解,如果远程客户端主机上的攻击者可以升级到 root/Admin 权限,或者直接危及真实用户自己的帐户,那么无论采用何种加密或任何其他保护措施,该客户端的数据都将得不到任何保护。(攻击者可以从磁盘上保存密钥的任何位置读取密钥,或者在真实用户登录时输入密钥时窥探密钥,然后密钥将指向数据。)
从这两个假设出发,我们可以得出结论:唯一相关的威胁是 A)暴力破解密码,以及 B)SQL 注入尝试:
- 如果攻击者没有获得真实用户的密钥,或者他想要访问的不仅仅是真实用户的数据,他可以尝试强行获取真实用户或其他帐户的登录凭据。(理论上,您可以将每个帐户锁定到特定的远程客户端 IP,这也有助于划分风险。)
- 如果攻击者确实获得了真实用户的有效密钥,他就可以绕过登录屏幕(可能足够简单,足够安全),进入可能存在漏洞的应用程序代码的软肋。从真实用户上下文中成功进行 SQL 注入也可以让他访问其他客户端数据。
现在,让我们讨论一下服务器端加密如何适用于这些情况:
- 服务器端加密无疑有助于抵御 SQL 注入威胁。如果行值在数据库表中加密,攻击者只能看到属于其他帐户的数据的乱码密文。威胁被控制、隔离。
- 然而,对于面对服务器端加密的攻击者来说,暴力破解密码实际上并没有变得更难。无论用户的密钥是存储在服务器上还是根据密码现场生成的,唯一重要的是您是否拥有正确的密码。服务器要么决定让您使用有效的存储密钥,因为它会检查您的密码是否正确,要么它会为您计算有效的密钥,因为您的密码是生成该密钥的正确输入。
另一方面,客户端加密实际上使暴力密码攻击变得无关紧要。您无法暴力破解正确构造的密钥。客户端加密对 SQL 注入的保护级别与服务器端加密基本相同。客户端可以在登录时将密钥传递给服务器,并在内存中保留一份副本直到会话结束,这会将加密 CPU 负担放在服务器上。或者,客户端可以在浏览器中自行处理加密/解密。这两种技术各有利弊:
- 将其密钥传递给服务器变得更加容易编码和管理,并且由于加密代码更加优化(可能是编译后的 C 语言),速度通常会更快。
- 纯客户端方法提供了额外的安全性,因为即使攻击者获得了服务器的权限,他仍然无法读取加密数据,并且永远无法读取它。唯一可能的攻击媒介是入侵远程客户端工作站。
最后,我要指出的是,加密数据库中的数据存在一些巨大的操作缺陷。由于加密的数据表示本质上是随机模式,因此索引、连接等基本数据库功能将无法使用。客户端承担了巨大的逻辑负担,并且可能会失去数据库功能通常带来的许多好处。
答案2
你可能想看看ezNcrypt,它使用 ecryptfs、访问控制和密钥管理为 MySQL 数据库和其他进程的 Linux 加密提供高安全性和性能。不,我不为他们工作。
答案3
您可以使用 Scytale。它是适用于现代 DBMS 和 Web 应用程序的 NoSQL 加密代理。支持多收件人和组加密。加载了强大的 RSA/AES 加密系统。它也是 100% 免费和开源的。