我在反应教程上看到的,这是什么意思?
反应是安全的。我们不生成 HTML 字符串,所以 XSS 保护是默认的。
如果 React 是安全的,XSS 攻击是如何工作的? 这种安全是如何实现的?
React 会自动转义变量... 它防止通过带有恶意 Javascript 的字符串 HTML 注入 XSS。.当然,输入也会与此一起进行消毒。
例如,假设你有这个字符串
var htmlString = '<img src="javascript:alert('XSS!')" />';
如果您尝试呈现此字符串以进行响应
render() { return ( <div>{htmlString}</div> ); }
您将在页面上看到整个字符串,包括 <span>元素标记。在浏览器中你会看到 <img src="javascript:alert('XSS!')" />
<span>
<img src="javascript:alert('XSS!')" />
如果你查看源代码 html 你会看到
<span>"<img src="javascript:alert('XSS!')" />"</span>
下面是关于什么是 XSS 攻击的更多细节
React 基本上使得你不能插入标记,除非你自己创建渲染函数中的元素... 也就是说,他们确实有一个允许这样渲染的函数,称为 dangerouslySetInnerHTML... 这里有更多关于它的细节
dangerouslySetInnerHTML
几乎没有什么值得注意的,有办法可以避开 React 逃脱的东西。一种更常见的方法是当用户为您的组件定义道具时。不要扩展任何数据从用户输入作为道具!
ReactJS 在设计上是相当安全的,因为
所以这种典型的攻击不会起作用
const username = "<img onerror='alert(\"Hacked!\")' src='invalid-image' />"; class UserProfilePage extends React.Component { render() { return ( <h1> Hello {username}!</h1> ); } } ReactDOM.render(<UserProfilePage />, document.querySelector("#app"));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script> <div id="app"></div>
但是..。
当您使用 dangerouslySetInnerHTML时,您需要确保内容不包含任何 javascript。反应不能为你做任何事情。
const aboutUserText = "<img onerror='alert(\"Hacked!\");' src='invalid-image' />"; class AboutUserComponent extends React.Component { render() { return ( <div dangerouslySetInnerHTML=\{\{"__html": aboutUserText}} /> ); } } ReactDOM.render(<AboutUserComponent />, document.querySelector("#app"))
示例1: 使用 javascript: code
点击“运行代码片段”-> “我的网站”查看结果
const userWebsite = "javascript:alert('Hacked!');"; class UserProfilePage extends React.Component { render() { return ( <a href={userWebsite}>My Website</a> ) } } ReactDOM.render(<UserProfilePage />, document.querySelector("#app"));
示例2: 使用 base64编码的数据:
const userWebsite = "data:text/html;base64,PHNjcmlwdD5hbGVydCgiSGFja2VkISIpOzwvc2NyaXB0Pg=="; class UserProfilePage extends React.Component { render() { const url = userWebsite.replace(/^(javascript\:)/, ""); return ( <a href={url}>My Website</a> ) } } ReactDOM.render(<UserProfilePage />, document.querySelector("#app"));
const customPropsControledByAttacker = { dangerouslySetInnerHTML: { "__html": "<img onerror='alert(\"Hacked!\");' src='invalid-image' />" } }; class Divider extends React.Component { render() { return ( <div {...customPropsControledByAttacker} /> ); } } ReactDOM.render(<Divider />, document.querySelector("#app"));
这里有更多的资源
利用 ReactJS 应用中的脚本注入缺陷
React.js 应用程序中最常见的 XSS 漏洞
应对多少 XSS 漏洞保护负责?
在反应中避免 XSS 仍然很困难
在 React 中通过 Markdown 避免 XSS