保护ajax请求完整性的最佳方法

时间:2012-02-01 21:49:34

标签: php javascript ajax security drupal

我正在构建一个Drupal网站,其中包含许多用户特定信息,这些信息将使用jQuery / ajax发布。它本身的信息不是很敏感,重要的是验证表单数据没有被Firebug等工具篡改,以及确保指定用户真正请求信息。换句话说,我试图找出用ajax发布时保护数据完整性和真实性的最佳方法。

理想情况下,我想使用一些众所周知的消息认证系统,如HMAC算法。但由于这包含一个对称密钥,我不知道如何在不暴露我的javascript文件中的密钥的情况下加密POST数据(显然任何人都可以看到)。

如果我对如何运作有错误的想法,请纠正我。

例如,我需要发送的信息

field1=x&field2=y&uid=10

...然后计算数据的哈希值和密钥。这可以不在我的javascript代码中公开哈希函数吗?

CHECKSUM: hash(postdata, "secret_key")

...最后将校验和附加到原始的postdata。

field1=x&field2=y&uid=1&c=CHECKSUM

替代

另一种方法是使用登录用户的会话ID。然而,这不会检查消息的完整性......

使用PHP生成表单时,我可以使用以下

生成隐藏的输入
CHECKSUM: hash(session id for the current user, "secretkey")

然后我将使用ajax发布的是

field1=x&field2=y&uid=10&c=CHECKSUM

通过这种方式,对相应用户(再次伪代码)进行身份验证是相当安全的

ssid = SELECT ssid FROM sessions WHERE uid = $_POST[uid]
if(ssid && hash(ssid, "secretkey") == $_POST[c]) {
     //User OK
} else {
     //Invalid user
}

5 个答案:

答案 0 :(得分:6)

你无法做你想做的事。基本上,您正在尝试验证不受信任和不受控制的客户端上的一个组件(您的表单)是否未被同一客户端上的另一个组件篡改。你无法控制客户。您可以提出各种方法,让某些人更难让某人在他们的客户端上执行此操作,但最终您必须揭示您如何对客户端执行这些完整性检查。无论你在表单中做什么,脚本都可以被客户端上的人阅读和理解(它必须在客户端上运行,因此与客户交互的任何人都可以对你正在做的任何事情进行逆向工程以恢复所使用的技术和你必须启用你的方案的任何键/等。)

Web应用程序安全性的基本规则是您无法控制客户端上发生的事情,因此您无法信任此类客户端验证/安全方案。

最后,这种方案提供的保护不太可能值得花时间和投资来实施。决心打破它的人将能够。

答案 1 :(得分:1)

正如其他人已经提到的,您无法控制客户端。这意味着你无法控制,因此无法信任客户端发送的内容以及任何可能被篡改的内容。

但是现在考虑一下:您向客户端公开的参数越少,它们就越不能篡改。因此,尽可能多地控制参数(即在服务器端)。这就是会话的用途。

因此,您可以在会话中存储不需要更改的参数,而不是将它们发送到不受控制的客户端。您只需将表单实例与服务器端表单参数相关联即可。您可以使用在会话数据数组中用作键的随机标识符来执行此操作:

$data = array('uid'=>10);
$id = generateRandomIdentifier();
$_SESSION['formdata'][$id] = $data;

然后,当您处理表单请求时,您只需使用表单数据标识符在$_SESSION['formdata']中查找表单数据,以获取进一步处理的数据。

答案 2 :(得分:0)

绝对没有办法阻止某人发出“假”请求。你只需要这样思考:

  

如果我的网络浏览器可以发出此请求,则任何人(手动或非手动)都可以进行此操作。

如果您在用户端进行某种加密,那么任何人都可以轻松获得加密方式,然后手动执行相同操作。例如,当你谈论哈希时:

hash(session id for the current user, "secretkey")

您的secretkey并非秘密,因为它位于javascript文件中。

你唯一能做的就是在“黑客”的作品中投入扳手。例如,您可以从AJAX请求中获取此密钥。此密钥将是唯一的,并在每个成功请求时删除。以更一般的方式,您必须将应用程序的逻辑移动到靠近服务器端。

答案 3 :(得分:0)

您需要保留uid存储在服务器端。这通常通过将其存储在session变量中来实现。

session_start();
$_SESSION['uid']

由于您的服务器存储会话数据,因此客户端无法修改其会话数据。恶意用户可能希望的最好的方法是劫持其他人的活动会话密钥,这不是对正确安全系统的实际攻击。

See also this detailed write-up about why we use sessions.

答案 4 :(得分:0)

可能此页面有用:http://www.jcryption.org

按照提及的问题检查我的答案

Securing and/or encrypting (hiding) POST variables in a jQuery ajax request