当比较HTTP GET和HTTP POST时,从安全角度看有什么不同?其中一个选择是否天生就比另一个更安全?如果有,为什么?

我意识到POST没有公开URL上的信息,但其中有任何真正的价值吗?或者它只是通过隐匿性来实现安全?当安全性是一个问题时,我是否有理由更喜欢POST ?

编辑: 通过HTTPS, POST数据被编码,但url会被第三方嗅探吗?此外,我正在处理JSP;当使用JSP或类似的框架时,是否可以公平地说,最佳实践是避免将敏感数据完全放在POST或GET中,而是使用服务器端代码来处理敏感信息?


当前回答

没有额外的安全性。

Post数据不会显示在历史和/或日志文件中,但如果数据应该保持安全,则需要SSL。 否则,任何嗅探线路的人都可以读取数据。

其他回答

我通常的选择方法是:

GET用于稍后将通过URL检索的项 例如,搜索应该是GET,所以你可以做Search .php?s=XXX POST将被发送的项目 与GET相比,这是相对不可见的,并且更难发送,但数据仍然可以通过cURL发送。

安全如同数据传输中的安全:POST和GET之间没有区别。 安全性与计算机上的数据安全一样:POST更安全(没有URL历史)

GET请求的安全性略低于POST请求。两者本身都不能提供真正的“安全”;使用POST请求并不能神奇地使你的网站免受恶意攻击。但是,使用GET请求会使原本安全的应用程序变得不安全。

“不能使用GET请求进行更改”的咒语仍然非常有效,但这与恶意行为没有多大关系。登录表单对于使用错误的请求类型发送最为敏感。

搜索蜘蛛和网络加速器

这就是应该使用POST请求来更改数据的真正原因。搜索蜘蛛会跟踪你网站上的每个链接,但不会提交他们找到的随机表单。

Web加速器比搜索蜘蛛更糟糕,因为它们运行在客户端机器上,并且“点击”登录用户上下文中的所有链接。因此,使用GET请求删除内容的应用程序,即使它需要管理员,也会很高兴地服从(非恶意的!)web加速器的命令,删除它看到的所有内容。

混淆副攻

不管使用GET请求还是POST请求,都可能出现混淆代理攻击(代理是浏览器)。

在攻击者控制的网站上,GET和POST同样容易提交,无需用户交互。

POST不太容易受到影响的唯一情况是,许多不受攻击者控制的网站(比如第三方论坛)允许嵌入任意图像(允许攻击者注入任意GET请求),但阻止所有方式注入任意POST请求,无论是自动还是手动。

有人可能会说,网络加速器是混淆代理攻击的一个例子,但这只是一个定义的问题。如果有的话,恶意攻击者无法控制这一点,所以即使副手感到困惑,这也很难说是攻击。

代理日志

代理服务器可能会完整地记录GET url,而不剥离查询字符串。POST请求参数通常不会被记录。在这两种情况下,cookie都不太可能被记录。(例子)

这是支持POST的一个非常薄弱的论点。首先,未加密的流量可以被完整地记录;恶意代理已经拥有了它所需要的一切。其次,请求参数对攻击者的用处有限:他们真正需要的是cookie,所以如果他们唯一拥有的是代理日志,他们就不太可能攻击GET或POST URL。

登录请求有一个例外:这些请求往往包含用户的密码。将此保存在代理日志中会打开一个在POST情况下不存在的攻击向量。然而,通过纯HTTP登录本身就是不安全的。

代理缓存

缓存代理可能会保留GET响应,但不会保留POST响应。话虽如此,GET响应可以变得不可缓存,而不是将URL转换为POST处理程序。

HTTP“推荐人”

如果用户从响应GET请求的页面导航到第三方网站,该第三方网站将看到所有GET请求参数。

属于“向第三方透露请求参数”的类别,其严重性取决于这些参数中包含的内容。POST请求自然不受此影响,但是要利用GET请求,黑客需要在服务器的响应中插入到他们自己网站的链接。

浏览器历史记录

这与“代理日志”参数非常相似:GET请求连同它们的参数一起存储在浏览器历史记录中。如果攻击者有物理访问机器的权限,他们可以很容易地获得这些信息。

浏览器刷新动作

一旦用户点击“刷新”,浏览器就会重新尝试GET请求。它可能在关闭后恢复选项卡时这样做。因此,任何行为(比如付款)都会在没有任何警告的情况下重复发生。

浏览器不会在没有警告的情况下重试POST请求。

这是只使用POST请求来更改数据的一个很好的理由,但与恶意行为无关,因此与安全性无关。

那我该怎么办呢?

Use only POST requests to change data, mainly for non-security-related reasons. Use only POST requests for login forms; doing otherwise introduces attack vectors. If your site performs sensitive operations, you really need someone who knows what they’re doing, because this can’t be covered in a single answer. You need to use HTTPS, HSTS, CSP, mitigate SQL injection, script injection (XSS), CSRF, and a gazillion of other things that may be specific to your platform (like the mass assignment vulnerability in various frameworks: ASP.NET MVC, Ruby on Rails, etc.). There is no single thing that will make the difference between "secure" (not exploitable) and "not secure".


通过HTTPS, POST数据被编码,但url会被第三方嗅探吗?

不,他们不能嗅。但url将存储在浏览器历史记录中。

是否可以公平地说,最佳实践是避免将敏感数据完全放在POST或GET中,而是使用服务器端代码来处理敏感信息?

这取决于它有多敏感,或者更具体地说,以何种方式敏感。显然客户会看到它。任何可以实际访问客户端计算机的人都可以看到它。客户端可以在发送回给您时欺骗它。如果这些很重要,那么是的,把敏感数据保存在服务器上,不要让它离开。

这是一篇旧文章,但我想反对其中的一些答案。如果要传输敏感数据,则需要使用SSL。如果您使用带有GET参数的SSL(例如?userid=123),该数据将以纯文本形式发送!如果使用POST发送,则将值放在消息的加密正文中,因此大多数MITM攻击都无法读取。

最大的区别在于数据传递的位置。如果数据放在URL中,就不能加密,否则就无法路由到服务器,因为只有你可以读取URL。这就是GET的工作方式。

简而言之,您可以在POST中通过SSL安全地传输数据,但您不能使用GET,无论是否使用SSL。

修改POST请求更加困难(它需要比编辑查询字符串更多的努力)。编辑:换句话说,它只是通过模糊来保证安全,而且几乎不是这样。