如果允许人们发布RAW嵌入代码,如何保护自己免受XSS攻击?

时间:2010-03-20 02:52:19

标签: php regex

Tumblr和其他博客网站允许人们发布来自youtube和所有视频网络的嵌入式视频代码。

但他们如何只过滤flash对象代码并删除任何其他html或脚本?甚至他们都有一个自动代码,告诉你这不是一个有效的视频代码。

这是使用REGEX表达式完成的吗?是否有PHP类可以做到这一点?

由于

7 个答案:

答案 0 :(得分:25)

一般来说,使用正则表达式不是处理HTML的好方法:HTML对于正则表达式来说不够常规:标准中允许的变化太多......浏览器甚至接受HTML无效!


在PHP中,由于您的问题被标记为php,因此过滤用户输入的绝佳解决方案是HTMLPurifier工具。

有几件有趣的事情是:

  • 它允许您指定允许哪些特定标记
  • 对于每个代码,您可以定义允许哪些特定属性

基本上,我们的想法是只保留您指定的内容(白名单),而不是尝试使用黑名单删除不良内容(这将永远不会完整)


如果您只指定一个不会造成伤害的标签和属性列表,那么只会保留这些标签和属性 - 并且注入的风险会降低很多。


引用HTMLPurifier的主页:

  

HTML Purifier符合标准   用PHP编写的HTML过滤器库。   
HTML Purifier不仅会删除   所有恶意代码(更好地称为   XSS)经过全面审核,   它安全但宽容的白名单   还将确保您的文件   符合标准,只有一些东西   可以全面实现   了解W3C的规范。

是的,另一件好事是您输出的代码有效



当然,这只会让你清理/过滤/净化HTML输入;它不允许您验证用户使用的URL是:

  • 正确;即指向真实内容
  • 您网站定义的“确定”;即,例如没有裸露,......


关于第二点,关于它的问题并不多:最好的解决方案是:

  • 让主持人在内容接受之前接受/拒绝
  • 为网站的用户提供一种方式,将某些内容标记为不当内容,以便主持人采取措施。

基本上,要检查视频的内容本身,没有多少选择,但是让人说“ ok ”或“ not ok ”。


但是,关于第一点,有希望:托管内容的某些服务具有您可能想要/能够使用的API

例如,Youtube提供了API - 请参阅 Developer's Guide: PHP

在您的情况下,Retrieving a specific video entry部分看起来很有希望:如果您将HTTP请求发送到如下所示的网址:

http://gdata.youtube.com/feeds/api/videos/videoID

(当然,用视频的ID替换“videoID”)

如果视频有效,您将获得一些ATOM Feed;和“无效的身份证明”,如果它不是

这可能有助于您至少验证一些内容的网址 - 即使您必须为用户喜欢的每种可能的内容托管服务开发一些特定的代码......


现在,从HTML字符串中提取视频的标识符...如果您正在考虑使用正则表达式,那么您错了; - )

从HTML字符串中提取部分数据的最佳解决方案通常是:

使用DOM还允许您使用标准API修改HTML文档 - 这可能会有所帮助,以防您想在视频旁边添加一些消息,或任何其他类似的事情。

答案 1 :(得分:2)

看看htmlpurifier开始吧。 http://htmlpurifier.org/

答案 2 :(得分:1)

我为我工作的公司实施了一个算法。它工作得很好。但是,实施起来相当复杂。

我肯定会查看HTMLPurifier,看看它是否适合你。如果你像我一样坚持做旧学校的方式,这就是基本的步骤:

1。 第一个==>与stripos()

取得联系

2。 您必须创建一个递归函数来标识窗口小部件的开始和停止标记,其中包括<embed></embed><embed/>(自闭合)或<object></object> ...或{{1的所有组合}}

3。 在此之后,您必须解析所有属性和参数。

4。 现在,所有<object><params>...<embed/></object>标记都应包含<object>个标记作为子元素。您必须解析所有这些以获取最终生成新嵌入或对象标记所需的所有数据。特别是包含高度,数据源的参数和属性非常重要。

5。 现在,您不知道属性是用单引号还是双引号括起来的,因此您的代码必须以这种方式宽松。此外,您不知道代码是有效还是格式良好。因此,它应该能够处理嵌套的嵌入/对象标记,嵌入未正确包含的标记等等......因为它是用户generatede内容,您无法真正了解和信任输入。你会看到有很多组合。

6。 如果您设法使用其所有属性(或对象元素及其子参数)解析嵌入元素,则域的白名单很容易......

我的代码最终是大约800行代码,这是非常大的,它充满了递归方法,找到正确的停止和结束标记等。我的算法也删除了所有通常包含在内的所有SEO文本剪切和粘贴嵌入代码,就像链接回到持有小部件的网站一样。

这是一个很好的练习,但如果我在哪里...不要开始走这条路。

建议:尝试找一些现成的,开源的!

答案 3 :(得分:0)

这永远不会安全。浏览器具有那些有趣的小功能,即使HTML很乱,也能帮助人们显示页面内容。有无穷无尽的机会通过:)

检查here以查看冰山一角

您需要做的是仅使用单个输入作为宽度和高度的链接和附加输入并过滤这些输入。然后生成对象标签Yourself。

可能是安全的。

答案 4 :(得分:0)

答案 5 :(得分:0)

最简单优雅的解决方案:Allowing HTML and Preventing XSS @ shiflett.org 使用各种“HTML净化器”不仅无意义。对不起,但是当一个更简单的解决方案在手时,我不会让那些喜欢使用这些膨胀库的人。

答案 6 :(得分:0)

如果您希望从漏洞中“保护”您的网站“安全”,白名单方法是(唯一)的方法。我建议安全地转义所有用户生成的内容,白色列表只有你知道的标记是安全的并且适用于你的网站。这不仅意味着&lt; B&gt;。标签,还有flash嵌入。

例如,如果要允许嵌入任何youtube,请编写一个验证RegEx,以查找它们生成的嵌入代码。拒绝接受任何其他人(或只是将其显示为转义标记)。这是可以测试的。忘记所有这些解析废话。

如果您还想添加vimeo视频,请查看他们提供的嵌入代码并接受它。

唉?我知道这似乎是一种痛苦,但实际上它比一些尝试以某种通用方式检测“坏”内容的算法更容易编写。

在简单版本的算法运行后,您可以返回并使其更好。您可以“暂时”接受未通过白名单的URL,脚本等内容,并拥有管理进程以将已批准的正则表达式添加到输出转义例程中。通过这种方式,合法用户不会被冷落,但是你不能打开这种性质的攻击。