由最近 基於vue的知乎日報單頁應用 引發的問題 以及問題解決歷程
通過 知乎日報API 基於vue做一個知乎日報的單頁應用,在獲取圖片時存在一個圖片盜鏈問題,圖片無法加載 提示 403 錯誤,
最終解決方法 添加meta標簽
<meta name="referrer" content="never">
以下兩點為個人的解決問題的過程, 和該meta標簽的詳細介紹, 不感興趣的小伙伴可以忽略
1、解決問題的過程記錄
遇到問題不要慌,要記住充分利用網絡, 利用搜索引擎 找找前輩們遇到的同樣的坑,看他們怎么填,一來可以快捷的解決問題,二來可以快速學習前輩的解決思路
我先找到了 知乎日報API 項目下的 Issues 果然有人遇到同樣問題,一個是純前端的解決方法(通過跳板鏈接, 也是我初期采用的), 一個是基於后端的方法(該方法說明了圖片盜鏈問題的本質, 原理 “原理是request的headers里有個Referer”)
采用方法一 就要在每一個引用圖片文件的地方添加跳板鏈接,很麻煩,
采用方法二 我的項目屬於純前端的 通過API獲取信息 然后展示的一個過程,再寫一個后台麻煩,
綜上, 可不可以找一個通過前端來解決的方式呢,被我找到了,在 這里
找到解決方案是目的,但絕不是問題的終點
2、使用 Referer Meta 標簽控制 referer
以下內容為轉載內容 可以移步 原文地址
這里描述了一個關於 http 協議中 referer 的 metadata 參數的提議,使用這個 metadata 參數,html 文檔可以控制 http 請求中的 referer ,比如是否發送 referer、只發送 hostname 還是發送完整的 referer 等。雖然有一些方法可以控制 referer ,比如 flash,以及一些 js 的 tricks,但是本文中描述的是另外一番景象。
使用場景
在某些情況下,出於一些原因,網站想要控制頁面發送給 server 的 referer 信息的情況下,可以使用這一 referer metadata 參數。
隱私
社交網站一般都會有用戶個人頁面,這些頁面中用戶都有可能添加一些外網的鏈接,而社交網站有可能不希望在用戶點擊了這些鏈接的時候,泄露用戶頁面的 URL ,因為這些 URL 中可能包含一些敏感信息。當然,有些社交網站可能只想在 referer 中提供一個 hostname,而不是完整的 URL 信息。
安全
有些使用了 https 的網站,可能在 URL 中使用一個參數(sid 等)來作為用戶身份憑證,而又需要引入其他 https 網站的資源,這種情況下,網站肯定不希望泄露用戶的身份憑證信息。
Object-Capability Discipline
有些網站遵循Object-Capability Discipline,而 referer 剛好與這一策略相悖,所以,網站能夠控制 refeer 將對 Object-Capability Discipline 很有利。
技術細節
referer 的 metedata 參數可以設置為以下幾種類型的值:
never
always
origin
default
如果在文檔中插入 meta 標簽,並且 name 屬性的值為 referer,瀏覽器客戶端將按照如下步驟處理這個標簽:
1.如果 meta 標簽中沒有 content 屬性,則終止下面所有操作
2.將 content 的值復制給 referrer-policy ,並轉換為小寫
3.檢查 content 的值是否為上面 list 中的一個,如果不是,則將值置為 default
上述步驟之后,瀏覽器后續發起 http 請求的時候,會按照 content 的值,做出如下反應(下面 referer-policy 的值即 meta 標簽中 content 的值):
1.如果 referer-policy 的值為never:刪除 http head 中的 referer;
2.如果 referer-policy 的值為default:如果當前頁面使用的是 https 協議,而正要加載的資源使用的是普通的 http 協議,則將 http header 中的 referer 置為空;
3.如果 referer-policy 的值為 origin:只發送 origin 部分;
4.如果 referer-policy 的值為 always:不改變http header 中的 referer 的值,注意:這種情況下,如果當前頁面使用了 https 協議,而要加載的資源使用的是 http 協議,加載資源的請求頭中也會攜帶 referer。
例子
如果頁面中包含了如下 meta 標簽,所有從當前頁面中發起的請求將不會攜帶 referer:
<meta name="referrer" content="never">
如果頁面中包含了如下 meta 標簽,則從當前頁面中發起的 http請求將只攜帶 origin 部分(注:根據原文中的語境,我理解這里的 origin 是包含了 schema 和 hostname 的部分 url,不包含 path 等后面的其他 url 部分),而不是完整的 URL :
<meta name="referrer" content="origin">
注意:在使用本文中所述的 meta 標簽的時候,瀏覽器原有的 referer 策略將被打破,比如從 http 協議的頁面跳轉到 https 的頁面的時候,如果設置了適當的值,也會攜帶 referer。
其他問題
這與 rel=noreferer 有什么關系呢?可能 rel=noreferer 會覆蓋掉本文中的 meta 標簽所設置的值。也就是功能覆蓋。
origin 信息不是一個完整的 url,所以瀏覽器客戶端估計會在 origin 后面加一個 / 來作為 path 部分。
如果 origin 是唯一的,會發生什么情況呢?估計 referer 會被忽略。
譯者注
這篇文章最初寫於2012年,目前在原始頁面已經是廢棄狀態,並且已經提供了w3c 的referer-policy 頁面,但是,譯者注意到,目前很多網站在防御 CSRF 的時候,都采用校驗 referer 的方法,有時候允許 referer 為空,並且某些 BAT 廠商的重要業務在防御 JSON 劫持的時候,也采用校驗 referer 的方法並允許 referer 為空,也許你會覺得本文中描述的只是一種提議,但是,FireFox 在21日的一篇文章中已經聲明,從 Firefox 36 Beta 開始,將會支持 referer-policy,這無疑會讓一些廠商的業務面臨威脅。
[參考來源wiki.whatwg.org,轉載請注明來自FreeBuf黑客與極客(FreeBuf.COM)]
以上