使用 AJAX 并设置 innerHTML 的安全性?

Posted

技术标签:

【中文标题】使用 AJAX 并设置 innerHTML 的安全性?【英文标题】:Security using AJAX and set innerHTML? 【发布时间】:2017-02-04 05:49:06 【问题描述】:

考虑以下情况:

我向 php 发送了一个 AJAX 请求(无用户输入),它启动了一个函数。 该函数返回一个原始 html 字符串。可以是任何东西 - 一个链接列表、一堆空的 div、要内联插入的 SVG、页面的大部分内容......在其创建过程中不使用任何用户输入数据。 我收到字符串作为响应并将其插入到 div。 我(目前并希望继续)使用纯 JS - 无库

接受 JS 中固有的某种程度的不安全性,我刚刚所做的事情有多不安全?

OWASP XSS Cheat Sheet 表示要转义所有“不受信任的数据”。鉴于上述情况,我的 AJAX 请求的结果是否不受信任?任何 AJAX 请求的结果是否被视为“不受信任”?

以这种方式插入 HTML 是不好的做法吗?如果是这样,我应该怎么做?

编辑以澄清几件事:

AJAX 请求中的 URL 变量仅用于在服务器上启动 PHP 函数。根本没有将变量传递给该函数(具体来说,我使用的是 Joomla 的 com_ajax 组件)。 所有返回的代码都是静态的,是我写的。

【问题讨论】:

假设服务器返回的 HTML 完全由您生成,并且不涉及任何用户输入,这对我来说听起来很安全。 如果您信任编写服务器脚本的程序员,那么您应该信任响应。 把换成"",改用bbcode 在发送 AJAX 请求之前,您需要使用 javascript 验证它是否有值。 @SathvikCheela 为什么在发送之前而不是在服务器端接收之后?我可以看到两者都做,但客户端部分不会让任何事情更安全,它只是为了更快的客户反馈。 【参考方案1】:

只要响应是真正静态的并且不涉及任何类型的用户输入,就可以了。 AJAX 本身(正如您所暗示的)不会使其容易受到 XSS 的攻击(只要传输是安全的,这实际上意味着 https)。

一个警告(不一定在您的情况下,但一般而言)可能是您认为用户输入的内容和不考虑的内容。您的应用程序总是接收来自用户的输入,或者它可能使用以前接收到的参数,甚至是另一个应用程序接收到的参数。即使您不传递参数,也可以从数据库中读取请求标头、cookie(如果有)和用户输入。即使它看起来像数据库中的静态数据,在某些时候它也可能来自某种类型的用户,可能是合法(但流氓)用户,或者外部攻击者,或者它可能来自另一个应用程序写入同一个数据库(无论如何都不是一个好习惯)。

因此,简而言之,如果您发回的数据实际上只是静态数据(如硬编码),那么它并不容易受到攻击,但它可以通过多种方式变成动态数据,然后由您(理想情况下基于风险)决定,您可以防止什么以及您信任什么。

最佳做法是默认对所有内容进行编码以避免错误。如果您确定您信任要作为 HTML 插入 DOM 的数据源,那很好。威胁建模可能有助于发现您应该信任和不应该信任的内容,但在某些情况下也可能很明显。

【讨论】:

完美答案,谢谢。我已经知道你的警告中的所有内容 - 页面不是严格静态的,但所有动态变量都是从服务器上使用的 Joomla 菜单模块中正确转义的条目,所以它们也可能是。我基本上一直担心在 AJAX 中使用 innerHTML 是一个坏主意,如果我不小心的话,XSS 可能会像某种 MITM 攻击一样。我现在可以看到我一直在无谓地烦恼。

以上是关于使用 AJAX 并设置 innerHTML 的安全性?的主要内容,如果未能解决你的问题,请参考以下文章

通过 AJAX/innerHTML 显示部分 Unicode 编码的数据

从 Firefox 扩展中清除 innerHTML 的最佳方法

一个带有 2 个输出的 ajax 循环错误 innerHTML

javascript没有设置innerHTML

未捕获的类型错误:无法将属性“innerHTML”设置为 null

iOS Safari 内存泄漏导致应用程序无法使用