FE.WEB-前端安全防範初識

xss-跨站腳本攻擊

概念:用戶填寫信息是可運行的 js 代碼。 操做用戶界面javascript

攻擊源頭html

  • 反射型 – 從url讀取內容展現
<!--1.xss.html-->
<script>
//打開 1.xss.html#<img src="404.html" onerror="alert('xss')" />
    var $test = document.querySelector('#test');
    $test.innerHTML = decodeURIComponent(window.location.hash);
</script>
  • 存儲型 - 從後臺讀取內容展現
<!--2.xss.html-->
<script>
    //這是一個從後臺讀取的數據
    var renderText = '<img src="404.html" onerror="alert(\'xss\')" />'
    var $test = document.querySelector('#test');
    $test.innerHTML = renderText;
</script>

防範手段前端

  • 純文本– html encode , js encode。因爲內容可能在多端展現,因此不在提交的時候轉義,只在展現的時候轉義。
<!--3.xss.html-->
<title>防範:html-encode</title>
<div id="test"></div>
<script>
    var htmlEscape = function(str) {
        return String(str)
            .replace(/&/g, '&amp;')
            .replace(/"/g, '&quot;')
            .replace(/'/g, '&#39;')
            .replace(/</g, '&lt;')
            .replace(/>/g, '&gt;');
    };
    var htmlUnescape = function(value) {
        return String(value)
            .replace(/&quot;/g, '"')
            .replace(/&#39;/g, "'")
            .replace(/&lt;/g, '<')
            .replace(/&gt;/g, '>')
            .replace(/&amp;/g, '&');
    };
    //這是一個從後臺讀取的數據
    var renderText = '<img src="404.html" onerror="alert(\'xss\')" />'
    var $test = document.querySelector('#test');
    $test.innerHTML = htmlEscape(renderText);
</script>
//4.svr.js
const http = require('http');
const fs = require('fs');
var spCharCodes = '[\\u0000-\\u001F]|\\u00F1|\\u000B|\\u000C|\\u00A0|\\uFEFF|\\u1680|\\u180E|[\\u2000-\\u200F]|\\u2028|\\u2029|\\u202F|\\u205F|\\u3000';
var norCharStr = '\'|"|>|<';
var JavaScriptEncode = (function(str){

    var norChar = '\\n|\\r|\\\\|'+norCharStr;
    var reg = new RegExp(norChar+'|'+spCharCodes, 'g');

    var escapeMap = {};
    norChar.split('|').forEach(function(str){
        if (str == '<')
            // 防</script> xss
            escapeMap[str] = '\\u003c';
        else if (str.length == 1)
            escapeMap[str] = '\\'+str;
        else if (str.length == 2 && str[0] == '\\')
            escapeMap[eval('"'+str+'"')] = str;
    });

    function rp(str) {
        return escapeMap[str] || '\\u'+zeroize(str.charCodeAt(0).toString(16), 4, 0);
    }
    return function(str) {
        if (str === null || str === undefined || typeof str == 'function') return '';
        return (''+str).replace(reg, rp);
    };
}())

const proxy = http.createServer((req, res) => {
    res.writeHead(200, { 'Content-Type': 'text/html' });
    res.end(fs.readFileSync('./4.xss.html').toString().replace('{{replaceJs}}}' , "bbb'" + ";alert('xss')+'" ));
    // res.end(fs.readFileSync('./4.xss.html').toString().replace('{{replaceJs}}}' , JavaScriptEncode("bbb'" + ";alert('xss')+'" )));
}).listen(3000);
  • 富文本– 白名單過濾

npm xssjava

  • URL 編碼

將不可信數據做爲 URL 參數值時須要對參數進行 URL 編碼git

encodeURIComponent(str)

JavaScript 編碼github

function encodeForJavascript(str, kwargs) {
    let encoded = '';
    for(let i = 0; i < str.length; i++) {
      let cc = hex = str[i];
      if (!/[A-Za-z0-9]/.test(str[i]) && str.charCodeAt(i) < 256) {
        hex = '\\x' + cc.charCodeAt().toString(16);
      }
      encoded += hex;
    }
    return encoded;
  };

csrf-跨站僞造請求

概念:利用你所在網站的登陸的狀態,悄悄提交各類信息(post ,get 請求)web

<!--1.scrf.html-->
<iframe id="" name="csrf-form"></iframe>
<form target="csrf-form" method="post" action="http://127.0.0.1:3001/csrf">
    <input name="name" value="1111">
    <input type="submit" value="提交">
</form>
//1.svr.js
const http = require('http');
const fs = require('fs');
const proxy = http.createServer((req, res) => {
    if(req.method == 'POST'){
        req.on('data' , (data)=>{
            console.log('referer :' ,   req.headers.referer);
            console.log('data :' ,   data.toString() , ' cookies:' , req.headers.cookie);
        });
        req.on('end' , (data)=>{
            res.writeHead(200, { 'Content-Type': 'text/html' });

            res.end('');
        })
    } else {
        res.setHeader('Set-Cookie', ['login=1']);
        res.end('');
    }
}).listen(3001);

防範手段npm

  • 提交 method=Post 判斷referer
  • Token(特殊登錄態)

SSRF-服務器僞造請求

概念:利用某些業務服務端會發出請求,請求內網地址segmentfault

<!--提交一個圖片地址,服務器幫轉爲png格式。
1. 服務器拉取圖片
2. 假如提交的圖片是 http://127.0.0.1
-->
<form target="csrf-form" method="post" action="http://127.0.0.1:3001/csrf">
    <input name="name" value="1111">
    <input type="submit" value="提交">
</form>

防範手段安全

  • 域名限制 - 不予提交內網域名
  • 內網IP 限制 - 不予提交內網IP
    -內網請求地址作token(特殊登錄態)- 信任請求

hijack 頁面劫持

概念:頁面劫持;iframe 嵌套某的頁面,騙取用戶輸入信息

<!--1.hijack.html-->
<iframe src="./2.hikjack.html" frameborder="0"></iframe>
<!--2.hijack.html-->
<script>
    if (window.parent != window)
        alert('hikjack')
</script>

防範手段

  • 頁面劫持:Window.parent 判斷
  • Json 劫持: 返回{} ,而不是返回數據
  • X-FRAME-OPTIONS: [DENY|SAMEORIGIN|ALLOW-FROM]

其餘

Jsonp & cors 安全校驗

防範手段
Token (特殊登陸態)
referer 校驗

受權經過後的須要重定向的URL,被串改了

防範手段
黑名單

參考資料:
https://github.com/caihuiji/w...
http://blog.gojaven.com/post/...
前端安全系列(一):如何防止XSS攻擊?
前端安全系列之二:如何防止CSRF攻擊?

相關文章
相關標籤/搜索