解讀vue項目防范XSS攻擊問題
1.對于從接口請求的數(shù)據(jù)
盡量使用{{}}加載,而不是V-HTML。
vue中的大括號會把數(shù)據(jù)解釋為普通文本。通常如果要解釋成html代碼則要用v-html。
而此指令相當于innerHTML。
雖然像innerHTML一樣不會直接輸出script標簽,但也可以輸出img,iframe等標簽。
vue文檔關(guān)于v-html的說明如下所示:
2.對用V-HTML和INNERHTML加載的客戶信息進行轉(zhuǎn)義
如果顯示內(nèi)容里面有html片段,一定需要用v-html或者innerHTML加載
例如:
<div v-html="`<span>${message}</span>`"></div>
里面的message是客戶自己輸入的信息,如果此時是惡意的dom片段肯定會引起XSS攻擊。此時我們可以對“<”,">"轉(zhuǎn)譯成“<”,“>”。然后再輸入到頁面。
可以使用lodash里面的escape方法對客戶信息進行轉(zhuǎn)譯。
如下:
import _escape from 'lodash/escape' Vue.prototype.$escape = _escape
在vue中插入一個全局方法,對需要轉(zhuǎn)譯的數(shù)據(jù)就使用這個方法:
<div v-html="`<span>${$escape(message)}</span>`"></div>
3.在入口頁面的META中使用CSP
在入口文件的head添加meta標簽
<meta http-equiv="Content-Security-Policy" content="script-src 'self';style-src 'self'">
<meta http-equiv="Content-Security-Policy" content="style-src 'self' 'unsafe-inline';script-src 'self' 'unsafe-inline' 'unsafe-eval' https://webapi.amap.com https://restapi.amap.com https://vdata.amap.com https://appx/web-view.min.js;worker-src blob:">
該指令說明:允許自身css、js和高德地圖api、地圖數(shù)據(jù)。
上面的CSP設(shè)置表示,script腳本資源和style樣式資源只能加載當前域名下的資源。這樣子可以避免外部惡意的腳本的加載和執(zhí)行。
如果頁面有例如下面的標簽,那這些CDN資源是加載不了的。
<link rel="stylesheet"> <script src='https://cdn.bootcdn.net/ajax/libs/angular.js/0.10.0/angular-ie-compat.js'></script>
題外話:個人不倡議用第三方CDN,其一是不會減少頁面加載資源的體積,其二是第三方CDN穩(wěn)定性不能保證,有時候第三方CDN的服務(wù)器會掛掉導(dǎo)致需要的資源加載不了。
一般會用下面的CSP配置:
<meta http-equiv="Content-Security-Policy" content="script-src 'self' 'unsafe-eval';style-src 'self' 'unsafe-inline'">
設(shè)置解釋:
- script-src:只加載當面域名服務(wù)器下的資源,且允許eval執(zhí)行腳本。因為webpack在development模式下大量使用eval進行腳本注入,且在development中常用的souce-map是cheap-module-eval-source-map。
- 如果script-src設(shè)置成‘self’會阻止eval的使用。
- style-src:只加載當面域名服務(wù)器下的資源,且允許使用內(nèi)聯(lián)資源。有時候無論在開發(fā)環(huán)境還是生產(chǎn)環(huán)境,可能都是通過webpack打包把CSS內(nèi)容打包到JS文件里面。加載頁面時,JS腳本會在頁面中插入一個個style標簽補充層疊樣式模型。如果style-src設(shè)置成‘self’會阻止style內(nèi)聯(lián)樣式的插入和執(zhí)行。
4.針對特殊場景,選擇性過濾XSS標簽
在項目中,XSS的安全漏洞很容易出現(xiàn),例如在聊天模塊和富文本模塊很容易出現(xiàn)。
有時候你想實現(xiàn)富文本編輯器里編輯html內(nèi)容的業(yè)務(wù)。
可是又擔心XSS惡意腳本的注入。
此時可以使用一個xss工具。
網(wǎng)址:https://github.com/leizongmin/js-xss。
更詳細的用法可以看附上的網(wǎng)址,這里簡單說一下用法。
首先下載xss
npm i xss -S
(1)在頁面中引入資源且生成XSS過濾器,對內(nèi)容進行過濾
var xss = require("xss")? const option={} //自定義設(shè)置 const myxss = new xss.FilterXSS(option); const line='<script type="text/javascript">alert(1);</script>' var html = myxss.process(line); console.log(html); //輸出:<script type="text/javascript">alert(1);</script>
(2)如果我想不過濾img標簽的onerror屬性,或者不過濾style標簽。
通過設(shè)置whiteList可選擇性的保留特定標簽及其屬性
例如:
const option={ ? ? whiteList:{ ? ? ? ? img:['src','onerror'] //img標簽保留src,onerror屬性 ? ? ? ? style:['type'] //style標簽?zāi)J是不在whileList屬性里的,現(xiàn)在添加上去 ? ? } } const myxss = new xss.FilterXSS(option); letline='<img src="./123.png" onerror="alert(1);" alt="123">' let html = myxss.process(line); console.log(html); //輸出:<img src="./123.png" onerror="alert(1);"> line='<style type="text/css">color:white;</style>' html = myxss.process(line); console.log(html); //輸出:<style type="text/css">color:white;</style>
xss默認的whiteList可以通過console.log(xss.whiteList)顯示。
(3)如果想徹底過濾掉類似script,noscript標簽,option可如下設(shè)置:
const option={ ? ? stripIgnoreTagBody: ["script","noscript"], } const myxss = new xss.FilterXSS(option) let line='<script type="text/javascript">alert(1);</script>' let html = myxss.process(line) console.log(html.length) //輸出0,即html被轉(zhuǎn)化為空字符串 line='<noscript>123</noscript>' html = myxss.process(line) console.log(html.length) //輸出0,即html被轉(zhuǎn)化為空字符串
stripIgnoreTagBody用于設(shè)置不在whiteList的標簽的過濾方法。
例如script,不在whiteList會被執(zhí)行xss內(nèi)部的escapeHtml方法。如一開頭的例子會把“<”,“>”進行轉(zhuǎn)義。
但如果stripIgnoreTagBody中添加了script。則會直接把整個script標簽過濾掉。
(4)xss默認生成的過濾器是會過濾掉任何標簽的class屬性。
如果我們不想過濾任何在whiteList的標簽的class屬性,可以這么設(shè)置:
const option={ ? ? onIgnoreTagAttr: function(tag, name, value, isWhiteAttr) { ? ? ? ? if (['style','class'].includes(name)) { ? ? ? ? ? ? return `${name}="${xss.escapeAttrValue(value)}"` ? ? ? ? } ? ? }, } const myxss = new xss.FilterXSS(option); let line='<div class="box"></div>' let html = myxss.process(line); console.log(html); //輸出:<div class="box"></div>
onIgnoreAttr方法用于設(shè)置白名單中特定屬性的過濾方法。
更多詳細教程請看一開頭附上的網(wǎng)址。
總結(jié)
以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關(guān)文章
vue3+vite+vant4手機端項目實戰(zhàn)記錄
這篇文章主要給大家介紹了關(guān)于vue3+vite+vant4手機端項目實戰(zhàn)的相關(guān)資料,Vue3是一種前端開發(fā)框架,它的目標是提供更好的性能和開發(fā)體驗,需要的朋友可以參考下2023-08-08使用Element+vue實現(xiàn)開始與結(jié)束時間限制
這篇文章主要為大家詳細介紹了使用Element+vue實現(xiàn)開始與結(jié)束時間限制,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下2021-08-08vue利用sync語法糖實現(xiàn)modal彈框的項目實踐
本文主要介紹了vue利用sync語法糖實現(xiàn)modal彈框的項目實踐,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2022-07-07Vue與.net?Core?接收List<T>泛型參數(shù)
這篇文章主要介紹了Vue與.net?Core?接收List<T>泛型參數(shù),文章圍繞主題展開詳細的內(nèi)容介紹,具有一定的參考價值,需要的小伙伴可以參考一下2022-04-04