1. 程式人生 > >Nginx服務器抵禦CC攻擊的相關配置講解

Nginx服務器抵禦CC攻擊的相關配置講解

完全 超過 原因 是否 cookie n) 配置文件 nginx服務 uri

CC攻擊利用代理服務器向網站發送大量需要較長計算時間的URL請求,如數據庫查詢等,導致服務器進行大量計算而很快達到自身的處理能力而形成DOS。而攻擊者一旦發送請求給代理後就主動斷開連接,因??代理並不因??客戶端這邊連接的斷開就不去連接目標服務器。

0x00 CC攻擊的基本原理

CC攻擊利用代理服務器向網站發送大量需要較長計算時間的URL請求,如數據庫查詢等,導致服務器進行大量計算而很快達到自身的處理能力而形成DOS。而攻擊者一旦發送請求給代理後就主動斷開連接,因??代理並不因??客戶端這邊連接的斷開就不去連接目標服務器。因此攻擊機的資源消耗相對很小,而從目標服務器看來,來自代理的請求都是合法的。

以前防CC攻擊的方法

為了防範CC,以前的方法一個是限制每個IP的連接數,這在地址範圍很廣闊的情況下比較難實現;二是限制代理的訪問,因為一般的代理都會在HTTP頭中帶 X_FORWARDED_FOR字段,但也有局限,有的代理的請求中是不帶該字段的,另外有的客戶端確實需要代理才能連接目標服務器,這種限制就會拒絕一些正常用戶訪問。

CC攻擊用硬防難防住

CC攻擊比DDOS攻擊更可怕的就是,CC攻擊一般是硬防很難防止住的。

個人分析原因有三:

一、因為CC攻擊來的IP都是真實的,分散的;

二、CC攻擊的數據包都是正常的數據包;

三、CC攻擊的請求,全都是有效的請求,無法拒絕的請求。

防CC攻擊思路

防CC有效性在於攻擊方不接受服務器回應的數據,發送完請求後就主動斷開連接,因此要確認連接是否是CC,服務器端不立即執行URL請求命令,而是簡單的返回一個頁面轉向的回應,回應中包含新的URL請求地址。如果是正常訪問,客戶端會主動再次連接到轉向頁面,對用戶來說是透明的;而對於CC攻擊者,由於不接收回應數據,因此就不會重新連接,服務器也就不需要繼續進行操作。

完美版

http{ 
   ... 
   limit_req_zone $cookie_token zone=session_limit:3m rate=1r/s; 
   limit_req_zone $binary_remote_addr $uri zone=auth_limit:3m rate=1r/m; 
} 
location /{ 
   limit_req zone=session_limit burst=5; 
   rewrite_by_lua  
   local random = ngx.var.cookie_random   if (random == nil) then     return
ngx.redirect("/auth?url=" .. ngx.var.request_uri) end local token = ngx.md5("opencdn" .. ngx.var.remote_addr .. random) if (ngx.var.cookie_token ~= token) then return ngx.redirect("/auth?url=".. ngx.var.request_uri) end ; } location /auth { limit_req zone=auth_limit burst=1; if ($arg_url = "") { return403; } access_by_lua local random = math.random(9999) local token = ngx.md5("opencdn" .. ngx.var.remote_addr .. random) if (ngx.var.cookie_token ~= token) then ngx.header["Set-Cookie"] = {"token=" .. token, "random=" .. random} return ngx.redirect(ngx.var.arg_url) end ; }

我想大家也應該已經猜到,這段配置文件的原理就是:把本來的發token的功能分離到一個auth頁面,然後用limit對這個auth頁面進行頻率限制即可。這邊的頻率是1個IP每分鐘授權1個token。當然,這個數量可以根據業務需要進行調整。

需要註意的是,這個auth部分我lua采用的是access_by_lua,原因在於limit模塊是在rewrite階段後執行的,如果在rewrite階段302的話,limit將會失效。因此,這段lua配置我不能保證可以用原生的配置文件實現,因為不知道如何用配置文件在rewrite階段後進行302跳轉,也求大牛能夠指點一下啊。

當然,你如果還不滿足於這種限制的話,想要做到某個IP如果一天到達上限超過幾次之後就直接封IP的話,也是可以的,你可以用類似的思路再做個錯誤頁面,然後到達上限之後不返回503而是跳轉到那個錯誤頁面,然後錯誤頁面也做個請求次數限制,比如每天只能訪問100次,那麽當超過報錯超過100次(請求錯誤頁面100次)之後,那天這個IP就不能再訪問這個網站了。

於是,通過這些配置我們便實現了一個網站訪問頻率限制。不過,這樣的配置也不是說可以完全防止了攻擊,只能說讓攻擊者的成本變高,讓網站的扛攻擊能力變強,當然,前提是nginx能夠扛得住這些流量,然後帶寬不被堵死。如果你家門被堵了,你還想開門營業,那真心沒有辦法了。

然後,做完流量上的防護,讓我們來看看對於掃描器之類的攻擊的防禦。

0x01 防掃描

ngx_lua_waf模塊

這個是一個不錯的waf模塊,這塊我們也就不再重復造輪子了。可以直接用這個模塊來做防護,當然也完全可以再配合limit模塊,用上文的思路來做到一個封IP或者封session的效果。

0x02總結

本文旨在達到拋磚引玉的作用,我們並不希望你直接單純的復制我們的這些例子中的配置,而是希望根據你的自身業務需要,寫出適合自身站點的配置文件。

Nginx服務器抵禦CC攻擊的相關配置講解