:CDN與WAF一體化防護與性能優(yōu)化)
1. 為什么我會盯上阿里云邊緣安全加速先說背景。我自己手上有幾個網(wǎng)站和API服務(wù)有內(nèi)容類的、也有幾個給小程序提供數(shù)據(jù)的接口。前幾年一直用的是普通CDN圖個便宜省事把靜態(tài)資源一緩存帶寬成本確實壓下來了。但真正讓我覺得日子不好過的是這兩年網(wǎng)站流量慢慢上來之后各種掃描、撞庫、CC攻擊的請求也跟著漲幾臺源站服務(wù)器經(jīng)常莫名其妙被打到CPU報警。傳統(tǒng)CDN就管加速安全這塊基本是裸奔最多給個半死不活的IP黑白名單遇到真正像樣點的攻擊根本扛不住源站IP一暴露分分鐘被打穿。后來我仔細看了下阿里云的邊緣安全加速ESAEdge Security Acceleration簡單說就是把CDN加速和WAF、DDoS防護、訪問控制這些安全能力統(tǒng)一放到了邊緣節(jié)點上。也就是說用戶請求還沒到你的源站在離他最近的邊緣節(jié)點就已經(jīng)做完了安全檢測和流量清洗同時再把靜態(tài)內(nèi)容、動態(tài)請求用最優(yōu)路徑回源。這種“安全加速一體”的思路比單獨買一臺高防服務(wù)器、或者CDN和WAF分開配兩套方案省心不少也更省錢。當然光看產(chǎn)品介紹誰都會吹我自己也踩過不少“宣傳很豐滿落地很骨感”的坑。所以這篇文章主要是把近幾個月實打?qū)嵉氖褂皿w驗做一個記錄從開通配置、安全防護、性能表現(xiàn)、成本控制到各種奇奇怪怪的問題都盡量寫詳細。如果你也有類似的網(wǎng)站或接口在考慮要不要上邊緣安全加速這篇應(yīng)該能幫你省不少時間。2. 基礎(chǔ)配置階段最容易被忽略的幾個細節(jié)2.1 接入域名前先想清楚業(yè)務(wù)該走“加速”還是“安全”我第一次用ESA的時候腦子里想的就是“直接把域名CNAME解析過去就行”。但實際上阿里云邊緣安全加速的控制臺要比普通CDN復(fù)雜一些一上來就會遇到站點接入模式的選擇常見的有“CNAME接入”和“NS接入”兩種。CNAME接入比較簡單就是把你需要的子域名單獨指到ESA分配的CNAME地址不影響其他域名的DNS解析。NS接入則是把整個域名的DNS服務(wù)器都托管給阿里云這樣所有子域名默認都走ESA配置更省事控制力也更強但代價是整個域名的解析權(quán)都交出去了對于那些還有其他業(yè)務(wù)域名在跑的團隊影響面比較大。我最后選的是CNAME接入因為手上域名多有的用Cloudflare的DNS管著有的是阿里云自家的混在一起如果用NS接入很容易誤傷其他業(yè)務(wù)。這里有個很關(guān)鍵的經(jīng)驗接入之前一定要把業(yè)務(wù)分類。純靜態(tài)資源圖片、JS、CSS直接走默認的加速配置就行安全策略不用開太狠但如果你的接口API是給App或小程序用的就必須單獨建一個站點或域名分組把WAF規(guī)則、限流策略、Bot管理單獨調(diào)不然默認規(guī)則很容易誤傷正常請求。我自己一開始圖省事全部放到一個站點下結(jié)果某個API接口的請求被CC防護誤判攔了一部分排查了半天才發(fā)現(xiàn)是規(guī)則范圍太寬了。2.2 HTTPS證書配置解決“頁面不存在”這類怪問題阿里云目前對ESA提供免費證書的申請和自動續(xù)期這個確實省心。但我還是要提醒一句如果你在邊緣安全加速上配了HTTPS源站那邊最好也把HTTPS配好并且證書要有效否則會碰到一個容易讓人抓狂的現(xiàn)象——瀏覽器訪問頁面提示“抱歉您所指定的頁面不存在”。這個問題的根源通常不是真的頁面不存在而是ESA邊緣節(jié)點回源的時候如果源站返回了418、302跳轉(zhuǎn)、或者SSL握手失敗ESA會把錯誤信息緩存下來直接展示一個默認錯誤頁。尤其當你之前用了別的CDN或者源站Nginx配了強制HTTPS跳轉(zhuǎn)邊緣節(jié)點回源時和源站之間協(xié)商協(xié)議不一致就會產(chǎn)生這種奇怪現(xiàn)象。我后來是把源站的強制跳轉(zhuǎn)關(guān)掉在ESA邊緣配置里統(tǒng)一做HTTP到HTTPS的跳轉(zhuǎn)同時把回源協(xié)議設(shè)為“HTTPS源站也走443”問題就沒再出現(xiàn)過。還有一個細節(jié)證書續(xù)期之后如果ESA控制臺里的證書狀態(tài)沒有自動更新你需要手動點擊一下“更新證書”或重新部署。我遇到過幾次免費證書自動續(xù)期后控制臺顯示已生效但邊緣節(jié)點實際還是舊證書導致部分移動端App請求失敗。排查方法很簡單用OpenSSL命令看看實際證書的生效時間如果和控制臺不一致就手動觸發(fā)一次證書重新下發(fā)。openssl s_client -connect 你的域名:443 -servername 你的域名 2/dev/null | openssl x509 -noout -dates2.3 回源配置的坑別讓源頭成為瓶頸很多人以為邊緣安全加速只要配好域名就萬事大吉其實回源配置才是決定穩(wěn)定性的大頭。ESA支持“域名回源”和“IP回源”。如果你源站是阿里云ECS我建議直接用內(nèi)網(wǎng)IP回源走阿里云內(nèi)部網(wǎng)絡(luò)不占用公網(wǎng)帶寬延遲和穩(wěn)定性都要好很多。如果源站在其他云廠商或者自建機房那就只能用公網(wǎng)IP回源這時候一定要在源站的防火墻或安全組里只放行ESA的回源IP段。這里我必須強調(diào)千萬要把回源IP段配到源站白名單里。我的源站之前被掃描器直接掃到IP然后瘋狂打源站就是因為回源IP白名單沒配好。后來我在Nginx層加了一層allow/deny只允許ESA的回源IP訪問源站的80和443端口攻擊流量即使繞過ESA直連IP也進不來。# 僅放行指定回源IP段其他IP一律拒絕 allow 你的阿里云邊緣節(jié)點IP段1; allow 你的阿里云邊緣節(jié)點IP段2; deny all;如果你用的是阿里云ECS的Linux系統(tǒng)配置完記得安全組也要同步加一下規(guī)則ECS安全組和Nginx兩層都要放行ESA回源IP。這個弄完之后源站的壓力瞬間小了很多。3. 安全防護能力實測WAF和CC防護到底靈不靈3.1 WAF核心規(guī)則默認規(guī)則夠用但別裸奔阿里云ESA內(nèi)置了一套WAF托管規(guī)則可以在控制臺一鍵開啟。默認規(guī)則覆蓋了常見的SQL注入、XSS攻擊、命令注入、惡意爬蟲識別等。我開啟之后讓同事配合做了一輪“安全測試”就是模擬一些常見的攻擊Payload比如在URL參數(shù)里傳 or 11 --這種結(jié)果還是相當靠譜基本都能攔截下來并返回405或460狀態(tài)碼。但有一個容易被忽略的點WAF托管規(guī)則默認會對所有請求做檢測這會導致一些正常情況下看起來“不太正?!钡暮戏ㄕ埱蟊徽`判。比如我有個接口參數(shù)里本身允許用戶傳一段帶有特殊字符的文本像英文單引號、尖括號、SQL關(guān)鍵字之類結(jié)果被WAF當成注入攻擊給攔了。解決方案有兩條一是把對應(yīng)的接口加入WAF白名單另一個更推薦的做法是在ESA控制臺里給該站點單獨配置更精細的規(guī)則把包含這些參數(shù)的URI排除在檢測范圍之外。千萬別圖省事直接把整個站點的WAF關(guān)掉。還有一點WAF的攔截模式默認是“觀察”還是“攔截”這個是可以在控制臺調(diào)的。我第一次開啟時默認是攔截模式結(jié)果某天晚上網(wǎng)站訪問量突然掉了一半一看日志才發(fā)現(xiàn)某個老接口的POST請求一直被攔截。后來我先把WAF切到“觀察”模式跑了一個禮拜每天看誤判日志把正常業(yè)務(wù)請求加到白名單之后才重新切回“攔截”模式。所以凡是涉及到規(guī)則變更建議都先觀察后攔截不要一上來就開大招。3.2 CC防護與限流別把正常用戶也攔在外面CC攻擊Challenge Collapsar簡單說就是模擬正常用戶的高頻請求把源站和邊緣節(jié)點的資源耗光。ESA的CC防護和頻控規(guī)則我實際體驗下來對單一IP的突發(fā)高頻請求識別還是比較準的。尤其是針對登錄接口、短信發(fā)送接口這類容易被“羊毛黨”盯上的路徑可以配置“單IP每秒鐘允許請求數(shù)”和“單IP每分鐘允許請求數(shù)”兩個維度。這里有一個很實際的調(diào)優(yōu)經(jīng)驗。我最初把某個API的單IP閾值設(shè)成了“每秒10次”想著正常用戶不太可能一秒請求10次結(jié)果活動期間用戶集中搶券一個辦公室出口IP下可能有幾十個人共用瞬間就被限流攔掉了。后來我把閾值調(diào)成“每秒20次”同時加上“每個會話Cookie每秒鐘最多5次”的二級限制才兼顧了正常用戶和防刷需求。CC防護的攔截閾值沒有絕對標準得看你的業(yè)務(wù)形態(tài)。如果是面向C端的高并發(fā)API單IP閾值適當放寬如果是后臺管理系統(tǒng)或者管理接口閾值就要收得很緊甚至可以配置只允許指定IP段訪問。有條件的話把辦公網(wǎng)的出口IP加進白名單避免自己人把賬號鎖了。3.3 自定義規(guī)則和Bot管理的實戰(zhàn)經(jīng)驗ESA的自定義攔截規(guī)則部分我后來花的精力最多。除了默認的WAF規(guī)則它還支持按Header、Cookie、URI、參數(shù)等多個維度組合條件做攔截或放行。比如有段時間有個爬蟲一直用同一類User-Agent瘋狂抓數(shù)據(jù)我在控制臺配置了一條規(guī)則User-Agent包含特定關(guān)鍵字比如某些Python庫、爬蟲框架且URI匹配到數(shù)據(jù)接口路徑直接攔截。配置生效后這類請求的日志立馬安靜了效果立竿見影。Bot管理這個是針對更高級的爬蟲的能識別無頭瀏覽器、模擬瀏覽器行為的請求。我體驗下來確實有一定效果但對性能有一定損耗請求耗時會有微小的增加。如果你的網(wǎng)站是靜態(tài)頁為主CDN緩存命中率高其實不太需要開Bot管理但如果你的核心資產(chǎn)是API數(shù)據(jù)接口開了Bot管理之后精準度提升明顯。這個可以根據(jù)業(yè)務(wù)接口的重要程度按域名開啟不用全局都開。還有一點提醒大家ESA的安全日志和攔截日志都是可以在控制臺實時查看的一定要養(yǎng)成定期翻日志的習慣。我至少每周看一次攔截報表關(guān)注哪些路徑被攻擊得多、哪些規(guī)則在誤殺及時做調(diào)整。4. 加速性能實測不只是靜態(tài)緩存那么簡單4.1 動靜態(tài)混合加速對比傳統(tǒng)CDN的優(yōu)勢傳統(tǒng)CDN對靜態(tài)資源加速效果很好但是遇到帶參數(shù)的動態(tài)請求、API接口、登錄請求往往是直接回源速度提升不明顯。ESA在這方面做了一些優(yōu)化把自己的動態(tài)加速DCDN能力也整合進來了通過智能路由、TCP優(yōu)化等手段讓動態(tài)請求也能選擇最優(yōu)鏈路回源減少公網(wǎng)鏈路抖動帶來的延遲。我實際做了對比測試。同樣一個API接口直接請求源站IP的延遲在80~120毫秒左右經(jīng)過普通CDN回源之后延遲反而可能會比直連源站還高一點但經(jīng)過ESA的動態(tài)加速之后從廣州、北京、上海三個地點測試平均延遲能降到40~70毫秒。對于需要多次請求才能完成一個業(yè)務(wù)動作的App來說這個延遲差距體感非常明顯。這里也補充一下ESA的動態(tài)加速能力很多是在邊緣節(jié)點上通過應(yīng)用層協(xié)議優(yōu)化實現(xiàn)的比如HTTP/2、HTTP/3QUIC的加速。我開啟HTTP/3之后弱網(wǎng)環(huán)境下比如地鐵、電梯里的加載速度提升比較明顯。不過要注意的是如果你的網(wǎng)站不支持HTTPS那HTTP/3根本用不上所以基礎(chǔ)HTTPS配置一定要先做好。4.2 緩存命中率優(yōu)化讓邊緣節(jié)點真正“扛活”邊緣安全加速不只是安全產(chǎn)品它的本質(zhì)還是個CDN所以緩存命中率直接影響回源壓力和用戶體驗。我剛開始接入的時候緩存命中率只有50%左右源站壓力還是很大。后來我發(fā)現(xiàn)問題出在緩存策略上默認配置對帶參數(shù)的URL基本不緩存每次請求都回源。于是我專門花了半天時間梳理了網(wǎng)站的請求類型圖片、CSS、JS、字體這些靜態(tài)資源沒有Cookie的、URL不帶參數(shù)的全部設(shè)置成“忽略查詢字符串”的緩存模式緩存時間設(shè)為1天到7天不等HTML頁面設(shè)置成緩存10分鐘配合源站每次發(fā)布后主動刷新緩存API接口則按業(yè)務(wù)容忍度設(shè)置緩存30秒到5分鐘數(shù)據(jù)要求實時性高的不緩存。這么調(diào)完以后緩存命中率從50%提升到了90%以上源站后端服務(wù)器的CPU使用率直接降了大約40%。這里想提醒大家緩存配置的核心思路是“能緩存的一定要緩存不能緩存的一分鐘都別亂存”尤其對于電商類網(wǎng)站如果把購物車接口緩存了會出現(xiàn)加購后看不到商品這種嚴重事故。寧可犧牲一點速度也不能犧牲數(shù)據(jù)一致性。4.3 實時日志和監(jiān)控告警別等用戶投訴才發(fā)現(xiàn)問題最后想聊一下監(jiān)控這塊。ESA控制臺提供了詳細的訪問日志、回源日志、攔截日志和實時監(jiān)控面板。我強烈建議你開通日志服務(wù)或至少訂閱實時日志把ESA日志投遞到自己的日志平臺比如阿里云SLS或自建ELK這樣出問題的時候可以快速定位而不是登錄控制臺一頁一頁翻。我自己就吃過虧。有段時間邊緣節(jié)點命中率很低但是控制臺總覽頁看著延遲還行直到有用戶反饋App打開圖片很慢我才去翻日志發(fā)現(xiàn)大部分請求都回源了源站在高峰期被拖垮導致整體變慢。后來配置了“回源帶寬”“回源請求數(shù)”“5xx錯誤率”這幾個監(jiān)控項的告警閾值一超過就會收到短信和郵件通知。這個告警一定要配而且要配在回源側(cè)因為邊緣節(jié)點的帶寬有緩存扛著看起來再平穩(wěn)回源側(cè)可能已經(jīng)冒煙了。5. 賬算明白邊緣安全加速到底花多少錢5.1 計費項拆解別被“按量付費”嚇到很多人在意ESA的價格說實話我第一次看計費文檔也頭大因為有加速流量費、安全防護費WAF規(guī)則數(shù)、Bot管理、動態(tài)請求數(shù)費用、邊緣函數(shù)調(diào)用次數(shù)費等多個維度。不過實際用下來大部分中小網(wǎng)站的賬單大頭還是“流量費”和“請求數(shù)”。我自己的網(wǎng)站是內(nèi)容站API服務(wù)日均請求量大概40萬次其中靜態(tài)資源請求占70%API請求占30%。啟用ESA之后靜態(tài)請求基本被緩存節(jié)點直接扛掉真正回源的請求量很少所以加速流量費并沒有想象中那么高。而安全防護這塊基礎(chǔ)WAF托管規(guī)則是包含在套餐里的只要不額外買高級版的自定義規(guī)則數(shù)和Bot管理費用還是比較可控的。對比之前我用的“普通CDN另一家云WAF”的組合ESA的費用大概便宜了20%~30%而且運維成本低了不止一星半點。以前兩個控制臺來回切換出了問題還要猜是CDN的問題還是WAF的問題現(xiàn)在一個產(chǎn)品全解決出問題看ESA的日志基本就夠定位了。5.2 成本優(yōu)化的幾個實操方向如果你發(fā)現(xiàn)月底賬單超出預(yù)期不用急著換產(chǎn)品先做這幾件事第一梳理緩存策略。緩存命中率每提升10%回源流量就少一大截費用自然降下來。把圖片這類大頭靜態(tài)資源緩存時間盡量拉長版本更新時用文件名加版本號的方式來刷新而不是頻繁地手動緩存刷新。第二確認有沒有不必要的“動態(tài)請求加速”。ESA對動態(tài)請求有單獨的計費如果你的接口本身離源站很近比如源站和用戶都在同一城市那動態(tài)加速帶來的收益有限可以只對需要跨地域訪問的API開啟動態(tài)加速把省下來的錢花在其他地方。第三安全規(guī)則不是越多越好。ESA的WAF自定義規(guī)則如果超過免費額度會按條數(shù)計費。我見過有人為了圖心理安慰一口氣配了上百條規(guī)則最后發(fā)現(xiàn)有一半以上的規(guī)則命中率為0。定期檢查規(guī)則命中率把完全沒用的規(guī)則刪掉能省一部分費用。第四如果你只是個人博客或輕量站點可以先從按量付費跑起來觀察一個月的賬單規(guī)模再決定要不要買資源包。資源包適合流量比較穩(wěn)定的業(yè)務(wù)價格能便宜不少如果流量波動大按量付費反而更靈活不會因為買了包用不完造成浪費。5.3 從“救火”到“日常運營”的心態(tài)轉(zhuǎn)變最后說一個花了不少錢才想明白的道理邊緣安全加速不是裝上就一勞永逸的。它是一個需要持續(xù)運維的東西。安全規(guī)則要定期調(diào)緩存策略要跟著業(yè)務(wù)版本走監(jiān)控告警要有專人盯。我之前一直以為它是“裸奔”網(wǎng)站的救命稻草用了之后才悟了真正讓網(wǎng)站穩(wěn)的是你有沒有一套持續(xù)的運營流程。我現(xiàn)在的做法是每周固定花一小時看ESA的攔截報表和監(jiān)控數(shù)據(jù)每次發(fā)版前先檢查一下緩存策略是否需要調(diào)整特別是有沒有新增的API路徑不小心被緩存了每季度做一次規(guī)則梳理把長期零命中的規(guī)則清理掉。這套流程執(zhí)行下來網(wǎng)站的穩(wěn)定性、用戶口碑都有了實打?qū)嵉奶嵘?. 那些年我踩過的坑給你提個醒最后再分享幾個具體問題都是我實際遇到過、并且在文檔里不容易直接找到答案的。第一個是“群里問了幾百遍沒人理”的證書續(xù)期后顯示不生效問題。如果你用了阿里云免費證書到期后證書會自動續(xù)期但ESA控制臺里的“證書狀態(tài)”不一定馬上同步。遇到這種情況直接把證書重新部署一遍不用重新申請通常幾秒鐘就生效了。部署完記得用第一節(jié)里的OpenSSL命令驗證一下實際證書時間不要只看控制臺。第二個是“換SSL證書后網(wǎng)站報錯”的問題。有些同學在群暉NAS或者其他服務(wù)器上換了新證書但瀏覽器訪問還是報錯甚至提示頁面不存在或證書無效。這種現(xiàn)象多半是因為邊緣節(jié)點緩存了舊證書狀態(tài)或者瀏覽器緩存里的HSTS記錄還指向舊證書。清一下瀏覽器緩存再用無痕模式訪問試試如果還不行就在ESA控制臺重新下發(fā)一次證書。第三個是“邊緣函數(shù)配置出錯導致整個站點500”。邊緣函數(shù)確實很強大可以在邊緣直接改寫請求、做鑒權(quán)、做響應(yīng)頭注入。但它一旦崩了影響的是整個域名。我在邊緣函數(shù)測試階段就踩過一次坑函數(shù)代碼里有個明顯的語法錯誤保存后直接導致站點全部500。后來我學會了先在一個測試子域名上驗證邊緣函數(shù)確認穩(wěn)定后再把正式域名切過來。這個習慣救了我好多次。第四個小坑是“HTTPS回源端口別配錯”。默認回源端口是443還是80要看你源站實際監(jiān)聽的端口。如果你的源站Nginx只監(jiān)聽了80而你把ESA回源協(xié)議配成HTTPS回源握手就會失敗站點表現(xiàn)為間歇性打不開。檢查源站端口和ESA回源配置是否一致是排查這類問題的第一步。最后一點是別迷信“默認配置”。ESA的默認配置非常適合“快速上手”但離“好用”還有距離。你要花時間把緩存規(guī)則、WAF規(guī)則、監(jiān)控告警都按自己的業(yè)務(wù)重新調(diào)一遍才能發(fā)揮產(chǎn)品的真正價值。7. 一些真實感受和后續(xù)打算坦率說用了這段時間的阿里云邊緣安全加速整體體驗是超出預(yù)期的。它的價值不光是“網(wǎng)站變快了”“攻擊變少了”這種單點指標而是把加速和安全這兩件以前需要分開操心的事情收斂到了一個入口、一個控制臺、一套日志里。對我這種一個人要管好幾個網(wǎng)站和接口的開發(fā)者來說這種“少折騰”本身就是最大的價值。如果你問我適合什么人用我大概會這么建議個人博客或純靜態(tài)站用普通CDN或?qū)ο蟠鎯o態(tài)托管就夠了不太需要上ESA但如果你有動態(tài)API、有小程序后端、有電商或內(nèi)容交易類業(yè)務(wù)同時又被掃描和攻擊搞得頭疼ESA可以認真考慮。尤其是你已經(jīng)用了阿里云ECS、RDS、OSS這一整套生態(tài)的邊緣安全加速和這些產(chǎn)品之間天然打通配置鏈路和賬號體系都順滑很多。后面我準備把ESA的邊緣函數(shù)好好再研究一下目前只是做了一些簡單的請求改寫和緩存控制據(jù)說還可以做邊緣渲染和輕量業(yè)務(wù)邏輯如果能把我?guī)讉€小接口的邏輯直接下沉到邊緣節(jié)點源站說不定能再省幾臺低配ECS。真跑通了我再來更新一篇實戰(zhàn)記錄。