前端——影子殺手篇

前言

對於一個影子殺手而言,總能殺人於無形。前端也有影子殺手,它老是防不勝防地危害着你的網站javascript

本篇打算介紹一些前端的影子殺手們——XSS和CSRF。或許,你對它恨之入骨;又或者,你運用的駕輕就熟。恨之入骨,多是由於你的網站被它搞得苦不堪言;駕輕就熟,多是由於你從事這項工做,天天都在和此類問題打交道。那咱們今天就來了解它,防護它。若是你喜歡個人文章,歡迎評論,歡迎Star~。歡迎關注個人github博客php

正文

注:在開始正文以前,先聲明一下,全部的實驗環境均爲本地搭建——DVWA。css

影子殺手們,由來已久,幾乎伴隨着整個互聯網的發展。歷史的潮流,老是值得去考究,去深思的。可能在十年以前,這些問題層出不窮;隨着開發者安全意識的提升,老是多多少少能夠避免的。那麼,咱們就先來看看,今天的第一位主角——XSS。html

第一位主角——XSS

記得在學校的時候,玩過CTF,應對相似於XSS等網絡漏洞,老是會有固定的套路。今天咱們也來了解了解這些套路。前端

概述

XSS的全名叫作Cross-site Scripting。不知你能否會有個疑問,老外都喜歡將英文縮寫,可是爲何這個縮寫倒是XSS呢?由於只能怪它來的晚咯,被css搶先一步^_^。不過不要緊,並不阻礙咱們記憶它。java

XSS是一種代碼注入類攻擊,它容許攻擊者在其餘人的電腦上面執行惡意的腳本代碼。每每XSS並不須要攻擊者去直接攻擊受害者的瀏覽器。攻擊者能夠利用網站的漏洞,將這一段惡意代碼提交。而後,經過網站去傳遞給受害者,同時竊取受害者的信息等。git

咱們能夠先看一個簡單的例子:程序員

或許,你會好奇,我應該怎麼去運用網站的漏洞,那咱們先來看一張圖:github

comment
comment

這是一個評論框,而後咱們能夠在其中輸入:正則表達式

comment
comment

而後,你提交這條信息,若是該網站沒有作防禦(例如:過濾),那麼,你所在的頁面會跳出以下畫面:

xss
xss

看了這個信息,或許你已經意識到了它的危害。由於若是能夠這樣子隨意的運行js腳本,對於你客戶端的信息(例如:cookie)將通通被竊取。

回到咱們的話題,在看到xss的基本效果以後,你會認爲JavaScript是危險的嗎?

其實否則,真正的JavaScript是運行在比較嚴格的環境下面,並不會對操做系統或者其餘應用形成傷害。不信的話,你能夠打開控制檯,在裏面隨意嘗試,你會發現你並無形成任何危害。那麼,咱們所謂的XSS的嚴重性,是吹的嗎?

那就更加不是了。首先,咱們要申明的是——何爲惡意代碼?惡意代碼的叫法,並非由於它自己是有危害的,而是它的意圖是對使用者有害的。咱們能夠來看看,何爲對使用者有害?例子:

  1. JavaScript對於用戶的私密信息進行讀取(例如:cookies)。
  2. JavaScript能夠經過XMLHttpRequest發送任意的信息到任意的服務器上
  3. JavaScript能夠修改當前頁面中的任意DOM元素

這些行爲,若是是不善的人所爲,那麼,將對使用者形成不可估量的損失。

XSS中的角色扮演

XSS整個流程中,會出現不一樣的角色。演員表可分爲:網站、受害者、攻擊者。

網站,一般是指那些會被受害者訪問的HTML頁面。

受害者,指的是那些訪問網站的普通用戶

攻擊者,則是那些躲在陰暗角落,敲擊着鍵盤的惡意用戶。一般,攻擊者還會具有一臺本身的服務器,用來接收發送過來的用戶信息。

整個流程圖,以下:

xss-process
xss-process

整個流程中,演員都是必須的環節,否則整個攻擊都沒法完成。可從圖中看出4個步驟:

  1. 攻擊者選取一個具有漏洞的網站,在其數據庫插入惡意代碼
  2. 用戶向網站服務器請求這個被注入的網站
  3. 網站服務器響應用戶請求,併發送給用戶已被修改的網站
  4. 用戶完成訪問,同時注入的惡意代碼執行,將用戶的cookie發送給攻擊者服務器

但願你對這幅流程圖多看幾眼,由於它也將會是咱們後續防護XSS的先決條件。以後,咱們來看看XSS的分類狀況

分類

XSS的目標是在受害者的瀏覽器中執行惡意代碼。而實現這一目標,每每只有不一樣的途徑,主要能夠分爲三種:反射型XSS存儲型XSS基於DOM的XSS

  • 反射型XSS:用戶的惡意代碼字符串來源於受害者的請求,例如,郵件中參雜的惡意連接。
  • 存儲型XSS:用戶的惡意代碼字符串來自於網站的數據庫。一般是咱們圖中舉的例子——在評論中注入惡意代碼,讓受害者進行訪問
  • 基於DOM型XSS:這種攻擊的漏洞主要在客戶端,而非服務端。通常比較少見。

因爲存儲型的XSS的流程圖,咱們已經在上面看到過了。以後,咱們須要來看一看反射型的XSS流程圖,如圖:

xss-reflect
xss-reflect

能夠看到流程中,並未向網站的數據庫中插入惡意代碼,而是由如下4步驟組成:

  1. 攻擊者向受害者傳遞一個網站URL地址
  2. 而後,受害者點擊了這個地址,同時會向網站發出請求
  3. 網站響應原先已經存在惡意代碼的網頁給用戶
  4. 當用戶加載完網頁以後,會向攻擊者的服務器發送私密信息。

這種形式每每是須要用戶進行點擊的。

還有一種基於DOM的XSS,平時運用較少,並且攻擊條件較爲苛刻。在此不作討論。

咱們看完分類以後,對於攻擊的大致流程已經掌握。

接下來的操做平臺,我比較推薦——DVWA。由於目前網上XSS漏洞比較少,主要也是由於開發者的重視,並且網上操做會致使必定的危害,因此在本地搭建開發環境是最好的選擇。

實際操做:

最初,咱們須要安裝DVWA,這個教程網上有不少,因此,能夠自行百度。

第一步,咱們須要將DVWA的安全級別調低,由於不一樣的安全級別採起的防護措施不一樣。

DVWA
DVWA

第二步,咱們開始在XSS reflected中進行xss試驗。

第三步,在輸入框中輸入"",如圖:

XSS
XSS

第四步:提交以後,咱們便可看到彈窗(這裏提醒一下儘可能不要使用chrome,那個瀏覽器會屏蔽這些,最好使用老版本的IE),如圖:

xss
xss

若是你具有後臺服務器的話,那麼就能夠將這個cookie經過請求的形式發送到服務器後臺上面,此處就不作演示了。

防護

既然有人企圖使用這些玩意來危害使用者,那麼,咱們這些開發者在開發應用的過程當中,天然會有應對之策。不知你還記得上面的攻擊流程圖沒有?若是忘記了,不妨回去看一眼。由於,最好的防護措施就是截斷攻擊環節中的任意一個環節。

首先,做爲一個開發者,必須達成的一點共識是全部的用戶輸入都是不安全的。尤爲是相似於XSS這類的注入型漏洞。咱們能夠經過兩個方式對其進行防護——編碼驗證

編碼:對於用戶的輸入而言,所輸入的內容只會做爲數據,而不是代碼。

驗證:經過正則表達式等方式,去檢查用戶的輸入中是否帶有敏感字符等。

因此,咱們的解決方案能夠圍繞上述兩點進行展開:

  1. 輸入檢測
    對用戶輸入的數據進行檢測。對於這些代碼注入類的漏洞原則上是不相信用戶輸入的數據的。因此,咱們要對用戶輸入的數據進行必定程度上的過濾,將輸入數據中的特殊字符與關鍵詞都過濾掉,而且對輸入的長度進行必定的限制。只要開發的人員嚴格檢查每一個輸入點,對每一個輸入點的數據進行檢測和xss過濾,是能夠阻止xss攻擊的。

  2. 輸出編碼
    經過前面xss的原理分析,咱們知道形成xss的還有一個緣由是應用程序直接將用戶輸入的數據嵌入HTML頁面中了。若是咱們對用戶輸入的數據進行編碼,以後在嵌入頁面中,那麼html頁面會將輸入的數據看成是普通的數據進行處理。

  3. Cookie安全
    利用xss攻擊,咱們能夠輕易的獲取到用戶的cookie信息。那麼咱們須要對用戶的cookie進行必定的處理。首先,咱們儘量減小cookie中敏感信息的存儲,而且儘可能對cookie使用hash算法屢次散列存放。合理的使用cookie的httponly的屬性值。這樣能夠防止惡意的js代碼對cookie的調用。

  4. 禁用腳本
    能夠在瀏覽器中進行js的安全設置。相似與chrome等瀏覽器都會攔截一些危險的xss操做,例如:想要讀取cookie時,瀏覽器會阻止這個操做,徵求用戶指示,同時提醒用戶此類操做的危害性。

對於XSS而言,咱們能夠了解的內容就到此爲止。若是你想要深究,能夠看一些網絡安全的書籍,或者查閱其餘的文章,都可獲得詳細的解答。下面咱們須要介紹咱們的第二位主角——CSRF

第二位主角——CSRF

還記得第一位主角的名字叫什麼嗎?是叫——跨站腳本攻擊。那麼第二位主角也有一個相似的名字——跨站請求僞造(Cross-site request forgery)。

概述

CSRF 顧名思義,是僞造請求,冒充用戶在站內的正常操做。咱們知道,絕大多數網站是經過 cookie 等方式辨識用戶身份(包括使用服務器端 Session 的網站,由於 Session ID 也是大多保存在 cookie 裏面的),再予以受權的。因此要僞造用戶的正常操做,最好的方法是經過 XSS 或連接欺騙等途徑,讓用戶在本機(即擁有身份 cookie 的瀏覽器端)發起用戶所不知道的請求。

CSRF這種攻擊方式在2000年已經被國外的安全人員提出,但在國內,直到06年纔開始被關注,08年,國內外的多個大型社區和交互網站分別爆出CSRF漏洞,如:NYTimes.com(紐約時報)、Metafilter(一個大型的BLOG網站),YouTube和百度HI......

或許,咱們如今對它瞭解的少了,可是網絡中的確還留有它的足跡。咱們具體的操做就不實際操做了。咱們能夠來看一下CSRF的原理,如圖(該圖來自一篇知名的博客,在此註明):

CSRF
CSRF

能夠從圖中看到如下步驟:

  1. 首先用戶會登陸網站A,以後在經過驗證以後,會由cookie來進行信息的傳遞
  2. 這時,用戶又訪問了網站B(例如:郵件連接等形式),用戶會在不知情的狀況下,利用用戶在網站A的cookie,對網站A發送第三方請求。
  3. A站點一般不會關注這個訪問是來自用戶或者網站B

分類

CSRF也可會分紅兩種形式的攻擊:站內攻擊站外攻擊

CSRF站內類型的漏洞在必定程度上是因爲程序員濫用$_REQUEST類變量形成的,一些敏感的操做原本是要求用戶從表單提交發起POST請求傳參給程序,可是因爲使用了$_REQUEST等變量,程序也接收GET請求傳參,這樣就給攻擊者使用CSRF攻擊創造了條件,通常攻擊者只要把預測好的請求參數放在站內一個貼子或者留言的圖片連接裏,受害者瀏覽了這樣的頁面就會被強迫發起請求。

CSRF站外類型的漏洞其實就是傳統意義上的外部提交數據問題,通常程序員會考慮給一些留言評論等的表單加上水印以防止SPAM問題,可是爲了用戶的體驗性,一些操做可能沒有作任何限制,因此攻擊者能夠先預測好請求的參數,在站外的Web頁面裏編寫javascript腳本僞造文件請求或和自動提交的表單來實現GET、POST請求,用戶在會話狀態下點擊連接訪問站外的Web頁面,客戶端就被強迫發起請求。

防禦

CSRF,對於目前而言攻擊較少,也是由於對於這方面的防護手段愈來愈成熟所致使的。下面,咱們來看一下如何去防禦CSRF的攻擊。

預防CSRF攻擊能夠從兩方面入手:

  • 正確使用GET、POST和cookie
  • 在非GET請求的時候添加僞隨機碼

何爲正確使用GET和POST呢?拿RESTful API舉例來講,GET是獲取資源,而POST是提交修改資源。那麼咱們在定義一個url時,遵循這個規則,就能夠保證GET的非用戶請求,沒法對服務器資源進行修改,這樣就能夠防止GET的CSRF攻擊。

那麼,你可能會疑惑,要是POST的請求攻擊怎麼辦呢?這就須要從第二方面下手。

增長僞隨機碼的方式,通常能夠分爲三種:

  • 爲每一個用戶生成一個cookie token,這樣能夠保證在每次表單驗證時附帶上同一個僞隨機碼。這種方式是最簡單的,可是同時也須要保證cookie的安全。每每cookie中的信息是很是容易被盜取的,因此這種方案在保證沒有XSS的前提下是比較安全的。

  • 每次請求生成驗證碼。這種方法是安全的,可是相對於用戶體驗來講,並不友好

  • 不一樣表單包含一個不一樣的token。有興趣能夠去了解一下,這種是比較安全的POST請求方式。

小結

因爲,如今對於CSRF的攻擊預防比較完全,通常在沒有XSS的前提下,已經很難進行此類攻擊了。因此真實的實際操做環境並無多少。以往主要的攻擊手段仍是,經過XSS對於cookie進行盜取,而後經過CSRF用戶數據進行修改。咱們能夠一個例子來講明最經典的銀行的例子:

若是銀行A容許以GET請求的形式來轉帳,咱們這裏大多指的不是實際生活中的,由於實際生活中銀行不可能只用get請求轉帳這麼簡單操做:www.mybank.com/Transfer.ph…

這是危險網站B的代碼段中有這麼一句:

<img src= http://www.mybank.com/Transfer.php?toBankId=11&money=1000」>複製代碼

那麼當你再回A銀行時,就會發現你的帳戶上已經少了1000元。

固然,這是假的。

總結

前端安全,一直以來都是被關注的重點對象。咱們在瞭解他們的同時,應該注重他們的防禦,這就是對用戶的包含。能夠是XSS的漏洞,時有發生,BAT等大廠的產品也不例外。今天總結了XSS和CSRF的攻擊與防禦,是警醒本身,在之後的開發中多加註意,同時,也但願和大家一塊兒分享。

若是你對我寫的有疑問,能夠評論,如我寫的有錯誤,歡迎指正。你喜歡個人博客,請給我關注Star~呦github博客

相關文章
相關標籤/搜索