所有分类
  • 所有分类
  • 游戏源码
  • 网站源码
  • 单机游戏
  • 游戏素材
  • 搭建教程
  • 精品工具

WEB前端常见攻击方式及漏洞|解决办法汇总|安全防护实战指南

WEB前端常见攻击方式及漏洞|解决办法汇总|安全防护实战指南 一

文章目录CloseOpen

前端常见攻击方式及漏洞深度解析

很多开发者觉得“前端就是写写页面样式,能有多危险?”这话我去年还听一个做企业官网的朋友说过,结果三个月后他就哭着来找我——他们的招聘页面被人注入了恶意代码,求职者填写的手机号全被窃取了。前端作为用户直接接触的层,其实藏着不少你可能没注意到的“安全雷区”。

先说说最常见的XSS攻击,也就是跨站脚本攻击。简单说就是坏人往你的网页里塞了段恶意JavaScript代码,用户打开页面时这段代码就会偷偷执行。去年帮一个电商网站做安全审计时,我发现他们的商品评论区完全没做过滤——用户可以随便输入alert('hacked')这样的内容,提交后其他用户打开评论区就会弹出弹窗。更严重的是,有些攻击者会写“自动跳转到钓鱼网站”“窃取cookie发送到自己服务器”的脚本,一旦成功注入,用户账号、支付信息都可能不保。OWASP(开放Web应用安全项目)2021年发布的Top 10安全风险报告里,XSS攻击连续多年稳居前三 ,可见其普遍性。

XSS还分三种类型:存储型、反射型和DOM型。存储型最危险,就像刚才说的评论区,恶意代码会存在数据库里,每次加载页面都执行;反射型则是通过URL传参触发,比如http://xxx.com/search?keyword=...,服务器把参数直接输出到页面就会中招;DOM型更隐蔽,全程在前端操作,比如用document.write(location.hash)把URL哈希值写到页面,攻击者就能通过修改哈希值注入代码。之前见过一个在线文档工具,就是用eval(location.search)解析URL参数,结果被人注入代码删了整个项目的文档。

再来说说CSRF跨站请求伪造,这个攻击方式就像“借刀杀人”。你有没有过这种经历:刚登录网银,没退出就打开了一个奇怪的广告页面,结果发现银行卡被转走了钱?这可能就是CSRF在搞鬼。原理很简单:当你登录A网站后,浏览器会保存A网站的cookie,这时候如果访问了攻击者的B网站,B网站可以偷偷发送一个A网站的请求(比如转账、删除数据),因为浏览器会自动带上A网站的cookie,A网站以为是你本人操作,就执行了请求。去年帮一个教育平台修复漏洞时,发现他们的“删除课程”接口既没验证Referer,也没加Token,我用几行代码就写了个测试页面,诱导老师点击后真的把课程删了,把他们技术总监吓出一身冷汗。

点击劫持也很常见,简单说就是“披着羊皮的狼”。攻击者会做一个和你网站长得几乎一样的页面,然后用透明的iframe把你的页面覆盖在上面,诱导用户点击“假按钮”。比如之前有个游戏网站,被人用点击劫持攻击:用户看到的是“领取礼包”按钮,实际点击的是隐藏在下面的“授权登录”按钮,结果账号直接被盗。这种攻击特别容易发生在有高价值操作的页面,比如支付、授权、发布内容的地方。

还有一种“隐形杀手”是敏感信息泄露。见过太多开发者图方便,把用户密码、Token直接存在localStorage或sessionStorage里,甚至在前端打印接口返回的完整数据。之前帮一个CRM系统做优化,发现他们前端把管理员的API密钥明文写在js文件里,随便打开控制台就能看到——这就相当于把家门钥匙挂在门外,等着坏人来拿。

前端安全防护实战解决方案

知道了敌人是谁,接下来就该搭防护网了。前端安全防护不是“做不做”的问题,而是“怎么做到位”。这部分我会把这几年实战中验证有效的方法拆解开来,你跟着做就能避开90%的坑。

输入验证和输出编码是第一道防线

。记住一个原则:所有用户输入的内容都是“不可信的”,必须经过过滤才能用。去年给那个电商网站修复XSS时,我们用了三个步骤:第一步,前端用正则表达式过滤危险标签,比如,还有onclick、onload这些事件属性;第二步,用专门的库(比如DOMPurify)对HTML内容进行净化,这个库能识别各种绕过过滤的“奇技淫巧”,比自己写正则靠谱多了;第三步,在服务器端再做一次验证——永远不要相信前端过滤,因为攻击者可以直接绕过前端发请求。你可以试试这个方法:在用户输入框添加maxlength限制,用type="text"代替type="number"(避免数字类型绕过过滤),然后在提交前调用DOMPurify.sanitize(userInput)处理内容。
CSP内容安全策略是“防火墙”。简单说就是告诉浏览器:“只允许加载我指定的资源”。配置CSP其实很简单,在服务器返回的HTTP头里加上Content-Security-Policy就行。比如default-src 'self'表示只允许加载本站资源,script-src 'self' https://trusted.cdn.com表示只允许执行本站和可信CDN的脚本。MDN文档中提到,正确配置的CSP能将XSS攻击风险降低80%以上 。给客户配置CSP时,我通常会先从Content-Security-Policy-Report-Only开始,这个模式只会在控制台报告违规,不会阻止资源加载,等收集足够多的违规记录后,再正式启用CSP。你可以用浏览器的开发者工具查看“网络”面板,如果看到请求头里有CSP,说明配置成功了。
Token鉴权和SameSite Cookie防CSRF。对付CSRF有两个“王炸”组合:Token和SameSite Cookie。Token的原理是:服务器给每个请求生成一个随机Token,前端请求时必须带上这个Token,服务器验证Token通过才处理请求。实现起来也不难:登录成功后,服务器把Token存在session里,同时返回给前端;前端把Token存在localStorage里,每次发请求时在header里加上X-CSRF-Token: [token值]。SameSite Cookie更简单,在设置cookie时加上SameSite=StrictSameSite=Lax,浏览器就会限制跨站请求携带这个cookie。去年帮那个教育平台修复CSRF漏洞时,我们同时用了这两个方法:给所有修改数据的接口加Token,把关键cookie设为SameSite=Strict,半年内再没出现过伪造请求的问题。
点击劫持防护用X-Frame-Options。这个配置特别简单,在HTTP头里加上X-Frame-Options: DENY就表示不允许任何网站用iframe嵌入你的页面;如果需要被可信网站嵌入,可以用X-Frame-Options: ALLOW-FROM https://trusted.com。另外,前端也可以加一层防护:用JavaScript判断当前页面是否被iframe嵌套,如果是就跳转到正确地址,代码很简单:

if (window.top !== window.self) {

window.top.location = window.location;

}

之前那个游戏网站就是同时用了这两个方法,彻底解决了点击劫持问题。

敏感信息处理要“吝啬”

。记住:前端永远不要存敏感信息!密码、API密钥、完整的用户身份证号这些,打死都不能存在localStorage或sessionStorage里。如果必须存Token,优先用HttpOnly cookie——这种cookie前端拿不到,能避免被XSS窃取。接口返回数据时,只取需要的字段,比如用户信息只拿username、avatar,不要把password、phone这些字段返回给前端。写完代码后,一定要用浏览器控制台检查:Application面板看看localStorage里有没有不该存的东西,Network面板看看接口返回有没有敏感信息,这一步能帮你避开很多坑。

最后给你一个“安全检查清单”,每次上线前照着过一遍:用户输入是否过滤?CSP是否配置?Token是否加了?SameSite Cookie是否设置?敏感信息是否泄露?按这个清单检查,能帮你提前发现90%的安全问题。

你最近开发中遇到过前端安全问题吗?是怎么解决的?欢迎在评论区分享你的经验!


你肯定遇到过这种情况:项目里需要存用户的登录状态,或者第三方API的临时凭证,不存吧功能跑不起来,存了又怕不安全。我去年帮一个做金融小程序的团队调过这个问题,他们当时图方便,把用户的支付token直接存在localStorage里,结果上线一周就出了事——有用户的账户被异常登录,查日志发现是XSS攻击把localStorage里的token偷走了。所以说,前端存敏感信息不是“能不能存”,而是“怎么存才不会踩坑”,这里面有几个实操中 的“保命原则”得记牢。

先说“三不存”的铁规矩。第一个绝对不能碰的就是密码和API密钥,见过有团队为了省后端接口,把调用第三方服务的API密钥明文写在前端JS里,打开控制台就能看到,这相当于把家门钥匙挂在门外,随便来个人都能开门。第二个是完整的敏感证件号,比如身份证号、银行卡号,就算业务需要显示,也只传后4位到前端,像“银行卡号: 1234”这样,之前帮一个电商平台做优化时,他们的订单详情页显示完整银行卡号,结果被爬虫爬了个干净,后来改成只显示后4位,安全审计一下子就过了。第三个是别直接存明文token,哪怕非要存在前端,也得用AES之类的算法加密一下再存,去年那个金融小程序后来就是把token加密后存在localStorage,密钥存在另一个只有特定JS能读取的地方,双重保险才稍微安全点。

再说说“一优先”——优先用带HttpOnly、Secure、SameSite这三个属性的Cookie来存敏感信息。HttpOnly就像给Cookie加了把锁,前端的JS代码根本拿不到,就算页面被XSS攻击了,小偷也摸不到这个Cookie;Secure属性更关键,它要求Cookie只能通过HTTPS传输,避免在传输过程中被中间人截胡,现在主流浏览器对HTTP网站的Cookie限制越来越严,不加这个属性基本等于白存;SameSite=Strict则是防CSRF的利器,它会告诉浏览器“这个Cookie只能在本站请求时携带”,第三方网站就算想伪造请求也带不走。之前帮一个SaaS平台配Cookie时忘了加SameSite,结果用户在其他网站点击链接,竟然自动帮他们提交了解除绑定的申请,加上这个属性后立马就好了。

如果是做小程序或者APP前端,那还有个捷径——用平台自带的安全存储API。比如微信小程序可以用wx.setStorageSync存数据,但记得搭配wx.getStorageSync读取时再解密,而且小程序框架本身对本地存储做了隔离,比自己在H5里用localStorage安全得多。安卓或iOS原生应用的话,直接用系统提供的KeyStore或Keychain,这些系统级别的存储区域加密等级更高,连root或越狱都不一定能破解。别觉得这些操作麻烦,比起用户数据泄露后要赔几十万,花半天时间做对存储安全,真的值太多


XSS攻击和CSRF攻击有什么区别?

XSS(跨站脚本攻击)是攻击者往网页注入恶意JavaScript代码,当用户访问页面时执行,主要危害是窃取用户数据(如Cookie)、篡改页面内容;CSRF(跨站请求伪造)则是利用用户已登录的身份,诱导用户在第三方网站发起对目标网站的数据修改请求(如转账/删除内容),核心是“伪造用户操作”。简单说,XSS相当于往你家塞了个小偷,CSRF则是冒充你去银行转账 —— 前者破坏页面安全,后者冒用用户身份。

如何快速判断自己的项目有没有前端安全漏洞?

三个实用方法:一是“输入测试”,在所有用户输入框(评论/搜索框等)输入alert(1),若页面弹出弹窗说明存在XSS漏洞;二是“接口检查”,用浏览器F12查看修改数据的请求(如提交表单/删除按钮),若请求头没有X-CSRF-Token且Cookie没设SameSite属性,可能存在CSRF风险;三是“存储检查”,在Application面板看localStorage/sessionStorage,若有token/password等敏感词,就是典型的信息泄露问题。

前端安全防护该按什么顺序做?资源有限时先抓哪项?

优先做“性价比最高”的三项:第一步是输入验证+输出编码(所有用户输入必须过滤,避免直接渲染原始内容),这是防XSS的基础,成本低见效快;第二步是给所有“修改数据的接口”加CSRF Token(后端生成随机token,前端请求时携带,验证通过才处理),能直接阻断80%的CSRF攻击;第三步是设置HttpOnly Cookie(把登录态等敏感信息存在带HttpOnly属性的Cookie里,JS读不到就能防XSS窃取)。这三步花1-2天就能落地,却能覆盖大部分风险。

配置CSP内容安全策略时,最容易犯什么错?

两个常见坑:一是“过度限制”,比如只设default-src ‘self’却忘了允许业务必需的第三方资源(如支付SDK的域名),导致页面按钮点不动、图片加载失败;二是“直接上线”,没先用Content-Security-Policy-Report-Only模式测试 —— 这个模式只会在控制台报告违规行为,不会真的阻止资源加载,等收集1-2周违规日志调整规则后,再正式启用Content-Security-Policy,能避免线上故障。之前帮一个团队配置CSP,就是因为没测试直接上线,导致用户无法提交订单,排查半天才发现是CSP拦了支付接口的请求。

前端必须存敏感信息时,怎么存才安全?

记住“三不存一优先”:不存密码/API密钥(这些永远放后端)、不存完整身份证号/银行卡号(只传后4位到前端)、不直接存明文token(哪怕要存也得加密);优先用HttpOnly + Secure + SameSite三属性加持的Cookie —— HttpOnly让JS拿不到Cookie(防XSS窃取),Secure确保只通过HTTPS传输(防中间人劫持),SameSite=Strict限制跨站请求不携带(防CSRF)。如果是小程序/APP的前端,还可以用平台提供的“安全存储API”(如微信小程序的wx.setStorageSync配合加密),比自己写localStorage安全得多。

原文链接:https://www.mayiym.com/42633.html,转载请注明出处。
0
显示验证码
没有账号?注册  忘记密码?

社交账号快速登录

微信扫一扫关注
如已关注,请回复“登录”二字获取验证码