利用 HTTP Security Headers 提升站點安全性

歡迎訪問陳同學博客原文

產品不斷迭代,安全卻很少關注,這在小團隊司空見慣嗎? 前兩天拿到一份站點的安全檢測報告:

例舉幾點:

  • 你是否將 Mysql、Redis、Mongo 等端口暴露在公網?
  • 你是否採用 22、3306這種極易被掃描的默認端口?
  • 你是否強制使用 HTTPS?是否將HTTP重定向到了HTTPS?
  • 你是否設置了 HTTP Security Headers?

    還有檢測不出來的,如果用了雲服務器,是否禁用了root用戶以密碼登錄?是否開啓了安全組?…

本文整理幾個 HTTP Security Header,屬於圖中的 Application Security部分。將用 nginx 來演示這些配置。通過文中材料鏈接可查看更詳細的信息。

HTTP Security Header

檢測報告提示:未遵守 X-Frame-OptionsX-XSS-ProtectionHSTSX-Content-Type-Options 的最佳實踐,這幾個都是 HTTP Response header。nginx 配置demo將在最下面給出。

X-Frame-Options

X-Frame-Options 用來告訴瀏覽器,頁面能不能以 frame、 iframe、 object 形式嵌套在其他站點中,用來避免點擊劫持(clickjacking)攻擊。例如用下面代碼將百度以 iframe 嵌入到自己的站點,然後監聽 iframe 事件做些其他事情,用戶如果不看URL估計以爲自己在用百度。

<iframe src="https://www.baidu.com/" width="100%" height="100%" frameborder="no"></iframe>

可選值:

  • DENY:頁面不允許在 frame 中展示
  • SAMEORIGIN:same origin,頁面可以在相同域名頁面的 frame 中展示
  • ALLOW-FROM uri:頁面可以在指定來源的 frame 中展示

X-XSS-Protection

用於處理跨站腳本攻擊 (XSS)。

可選值:

  • 0:禁止XSS過濾
  • 1:啓用XSS過濾。 如果檢測到跨站腳本攻擊,瀏覽器將清除頁面中不安全的部分,但頁面仍然可以訪問。
  • 1;mode=block:啓用XSS過濾。 如果檢測到攻擊,瀏覽器將直接阻止頁面加載。

HSTS

HSTS(HTTP Strict Transport Security,RFC 6797) HTTP嚴格傳輸安全 ,指告訴瀏覽器自動從HTTP切換到HTTPS(當然,站點得支持HTTPS)。

舉例說明,如下圖(nginx 將http重定向到https):

  • 左邊沒加HSTS配置,301正常重定向,耗時 80ms ;

  • 右邊配置了HSTS,瀏覽器利用cache,直接將HTTP轉成了HTTPS,耗時 2ms,免去了重定向過程。

    狀態從 301 變成了 307 Internal Redirect 即瀏覽器內部跳轉。

X-Content-Type-Options

X-Content-Type-Options 用來提示客戶端一定要遵循在 Content-Type 首部中對 MIME 類型 的設定,而不能對其進行修改,用於禁用了客戶端的 MIME 類型嗅探行爲。

當資源缺失 MIME 類型或設置了錯誤的 MIME 類型時,瀏覽器可能會通過查看資源來進行MIME嗅探。簡單來說,就是如果瀏覽器不確定資源是什麼,就會看看資源的內容,X-Content-Type-Options 就是讓瀏覽器不要幹這個事情。

可選值:

  • nosniff:sniff 即嗅探。

nginx 配置demo

HTTP Strict Transport Security (HSTS) and NGINX

通過nginx add_header 指令在 response 中添加如下header,可以根據需要調整。add_header 可以作用於nginx的 http、server、location。

server {

   listen 80;
   server_name chenyongjun.vip;

   location / {
		add_header X-Frame-Options "DENY";
		add_header X-Xss-Protection "1;mode=block";
		add_header X-Content-Type-Options "nosniff";
		add_header Strict-Transport-Security "max-age=31536000; includeSubdomains; preload";
	}
}

關於Strict-Transport-Security:

  • max-age 必要,單位s,表示HSTS Header過期時間,通常設置爲1年,即31536000秒。
  • includeSubDomains 可選,表示子域名是否開啓HSTS保護。
  • preload 可選,如果需要將域名加入到瀏覽器內置列表才需配置
  • nginx 1.7.5 or NGINX Plus R5 以上支持這麼寫, add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;,always用於確保所有的response設置了該header

Spring Security

如果你使用了 Spring Security,默認會利用 HeaderWriterFilter 將上面的安全配置全部寫入 response。

如果你想在流量入口統一做安全設置,可以禁用或調整應用中 Spring Security 配置。修改你自定義的 WebSecurityConfig

@Configuration
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // 下面的所有實例代碼都在這裏
    }
}

修改配置

禁用 Secure Header

http.headers().disable();

禁用X-Frame-Options

其他選項不一一列出

http.headers().frameOptions().disable();

nginx 中剔除配置

如果應用中啓用了 HTTP Secure Headers,但是最終返回的Response需要剔除某個配置。在不改代碼前提下,可以通過nginx來剔除,例如從response中剔除X-Frame-Options配置:

proxy_hide_header X-Frame-Options;

小結

本文主要是想增長一丟丟安全意識,這些配置倒是次要的,還有更多的安全相關配置,需要時查查資料就好。


歡迎關注陳同學的公衆號,一起學習,一起成長

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章