授權(quán)協(xié)議OAuth2.0——基礎(chǔ)入門

1.前言

前段時間公司取消了Android崗龄坪,在面臨失業(yè)沒有飯碗天天吃土的壓迫下叙身,我轉(zhuǎn)崗變成JAVA工程師。雖然JAVA并不陌生志鹃,但在陌生技術(shù)的面前夭问,還是向大佬們低下了頭。

也有人會問為啥不換份工作曹铃。自己也問過自己為什么缰趋?這份工作掙得少,變化多陕见,不穩(wěn)定秘血。但是卻能每次讓我面臨新的挑戰(zhàn),不論是轉(zhuǎn)崗JAVA還是前端评甜,就是這種挑戰(zhàn)的感覺讓我無法停止灰粮,如果有一天公司不會再讓我吸收到養(yǎng)分,那應(yīng)該就是我離開的一天忍坷。

不多廢話了粘舟,因為最近要對接另一個公司的接口,面臨權(quán)限的問題佩研,領(lǐng)導(dǎo)讓我調(diào)研了下柑肴,跟大家也分享下。


2.概念

2.1 OAuth2.0是什么旬薯?

OAuth是一個關(guān)于授權(quán)(authorization)的開放網(wǎng)絡(luò)標(biāo)準(zhǔn)晰骑,在全世界得到廣泛應(yīng)用,目前的版本是2.0版绊序。

OAuth2.0是OAuth協(xié)議的下一版本些侍,但不向后兼容OAuth 1.0即完全廢止了OAuth1.0。 OAuth 2.0關(guān)注客戶端開發(fā)者的簡易性政模。

那我們該怎么使用協(xié)議岗宣?協(xié)議給我們定義了流程和參數(shù),只要我們雙方都遵循這個協(xié)議淋样,那就算使用實現(xiàn)了該協(xié)議耗式。

2.2 OAuth2.0做什么?

目前很多開放平臺如新浪微博開放平臺都在使用提供開放API接口供開發(fā)者使用,隨之帶來了第三方應(yīng)用要到開放平臺進行授權(quán)的問題刊咳,OAuth就是干這個的彪见。

舉個栗子,咱們?yōu)g覽百度的時候需要登陸娱挨,可以用微信賬號登錄余指,那這時候微信給百度的賬號信息就可以通過授權(quán)(OAuth2.0)來實現(xiàn)了。


登錄百度跷坝,有多種方式

使用微信賬號授權(quán)

2.3 關(guān)鍵字

這部分大家需要記牢酵镜,在后面的流程中多次涉及。

  • client:第三方應(yīng)用程序柴钻,客戶端(百度)
  • HTTP service:HTTP服務(wù)提供商淮韭,資源信息提供方(微信)
  • Resource Owner:資源所有者,用戶(有微信賬號的百度使用者)
  • User Agent:用戶代理贴届,瀏覽器
  • Authorization server:認證服務(wù)器靠粪,即服務(wù)提供商(微信)專門用來處理認證的服務(wù)器。
  • Resource server:資源服務(wù)器毫蚓,即服務(wù)提供商(微信)存放用戶生成的資源的服務(wù)器占键。它與認證服務(wù)器,可以是同一臺服務(wù)器元潘,也可以是不同的服務(wù)器畔乙。

2.4 運行流程


(A)用戶打開客戶端以后,客戶端要求用戶給予授權(quán)柬批。
(B)用戶同意給予客戶端授權(quán)。
(C)客戶端使用上一步獲得的授權(quán)袖订,向認證服務(wù)器申請令牌氮帐。
(D)認證服務(wù)器對客戶端進行認證以后,確認無誤洛姑,同意發(fā)放令牌上沐。
(E)客戶端使用令牌,向資源服務(wù)器申請獲取資源楞艾。
(F)資源服務(wù)器確認令牌無誤参咙,同意向客戶端開放資源。

以上是OAuth2.0的運行流程硫眯,其中ABCD如何授權(quán)是咱們關(guān)注的主要流程蕴侧。

3.客戶端的授權(quán)模式

在上節(jié)我們明白了OAuth2.0的運行流程,那咱們這節(jié)主要看一下如何獲取授權(quán)的方法两入。
客戶端必須得到用戶的授權(quán)(authorization grant)净宵,才能獲得令牌(access token)。OAuth 2.0定義了四種授權(quán)方式。

  • 授權(quán)碼模式(authorization code)
  • 簡化模式(implicit)
  • 密碼模式(resource owner password credentials)
  • 客戶端模式(client credentials)

上面的四種方法只有授權(quán)碼模式應(yīng)用廣泛择葡,所以本文只講授權(quán)碼模式紧武,其余三個會在下面給大家鏈接,有興趣的可以查看敏储。

3.1 授權(quán)碼模式運行流程


以下我們還是采用用微信賬號登錄百度的栗子講解阻星。(括號中均為舉例)

(A)用戶訪問客戶端,后者將前者導(dǎo)向認證服務(wù)器已添。(當(dāng)我們在百度客戶端點擊微信登錄妥箕,會在百度客戶端中跳轉(zhuǎn)到微信授權(quán)頁面,詢問用戶是否同意授權(quán)酝碳。顯示的授權(quán)URI是微信提供的矾踱,其中帶有部分參數(shù),包括授權(quán)成功后的重定向URI疏哗,該重定向URI是百度提供的呛讲。)

(B)用戶選擇是否給予客戶端授權(quán)。

(C)假設(shè)用戶給予授權(quán)返奉,認證服務(wù)器將用戶導(dǎo)向客戶端事先指定的"重定向URI"(redirection URI)贝搁,同時附上一個授權(quán)碼。(在A步驟中芽偏,我們傳遞了重定向URI雷逆,那么微信授權(quán)頁面就知道授權(quán)成功后,應(yīng)該跳轉(zhuǎn)到該重定向URI污尉,并向百度傳遞授權(quán)碼膀哲。該步驟在瀏覽器中可見。)

(D)客戶端收到授權(quán)碼被碗,附上早先的"重定向URI"某宪,向認證服務(wù)器申請令牌。這一步是在客戶端的后臺的服務(wù)器上完成的锐朴,對用戶不可見兴喂。(百度拿著授權(quán)碼和一些參數(shù),去微信申請訪問令牌焚志。)

(E)認證服務(wù)器核對了授權(quán)碼和重定向URI衣迷,確認無誤后,向客戶端發(fā)送訪問令牌(access token)和更新令牌(refresh token)酱酬。(微信返回給百度訪問令牌和更新令牌壶谒,百度就能拿著訪問令牌去訪問微信的信息了。)

3.2 授權(quán)碼模式所需參數(shù)

該步驟對應(yīng)3.1的步驟

(A)訪問授權(quán)頁面URI

  • response_type:表示授權(quán)類型膳沽,此處的值固定為"code"佃迄,必選項
  • client_id:表示客戶端的ID泼差,在授權(quán)方的開放平臺申請的appid,是雙方的一個身份證明呵俏,必選項
  • redirect_uri:表示重定向URI堆缘。當(dāng)用戶同意授權(quán),服務(wù)商回應(yīng)客戶端的uri普碎,可選項建議寫吼肥。
  • scope:表示申請的權(quán)限范圍,可選項
  • state:表示客戶端的當(dāng)前狀態(tài)麻车,可以指定任意值缀皱,認證服務(wù)器會原封不動地返回這個值。

例子:
/authorize ? response_type=code & client_id=s6BhdRkqt3 & state=xyz & redirect_uri=https%3A%2F%2Fclient%2Eexample%2Ecom%2Fcb

(C)服務(wù)商給重定向URI傳回Code

C步驟中动猬,假設(shè)用戶同意授權(quán)啤斗,服務(wù)商會訪問重定向URI,并包含以下參數(shù):(用戶同意用微信賬號登錄百度赁咙,微信訪問百度給的重定向URI钮莲,并拼上參數(shù))

  • code表示授權(quán)碼,必選項彼水。該碼的有效期應(yīng)該很短崔拥,通常設(shè)為10分鐘,客戶端只能使用該碼一次凤覆,否則會被授權(quán)服務(wù)器拒絕链瓦。該碼與客戶端ID和重定向URI,是一一對應(yīng)關(guān)系盯桦。(微信給百度的授權(quán)碼)
  • state:如果客戶端的請求中包含這個參數(shù)慈俯,認證服務(wù)器的回應(yīng)也必須一模一樣包含這個參數(shù)。

例子:
https://client.example.com/cb ? code=SplxlOBeZQQYbYS6WxSbIA & state=xyz

(D)用Code換Token

在C步驟中拿到Code之后拥峦,客戶端(百度)向認證服務(wù)器(微信)申請令牌的HTTP請求贴膘,包含以下參數(shù):

  • grant_type:表示使用的授權(quán)模式,必選項事镣,此處的值固定為"authorization_code"步鉴。
  • code:表示上一步獲得的授權(quán)碼揪胃,必選項璃哟。
  • redirect_uri:表示重定向URI,必選項喊递,且必須與A步驟中的該參數(shù)值保持一致随闪。(這個參數(shù)會做一個驗證)
  • client_id:表示客戶端ID,在授權(quán)方開放平臺申請的appid骚勘,必選項铐伴。(百度在微信開放平臺申請的appid)
  • client_secret:表示客戶端Secret撮奏,在授權(quán)方開放平臺申請的secret,必選項当宴。(百度在微信開放平臺申請的secret)

注意: 該步中的信息一定要保證正確畜吊,且只有該步驟可以暴露secret,因為不會暴露給外網(wǎng)户矢。

(E)返回Token格式

E步驟中玲献,認證服務(wù)器發(fā)送的HTTP回復(fù),包含以下參數(shù):

  • access_token:表示訪問令牌梯浪,必選項捌年。
  • token_type:表示令牌類型,該值大小寫不敏感挂洛,必選項礼预,可以是bearer類型或mac類型。
  • expires_in:表示過期時間虏劲,單位為秒托酸。如果省略該參數(shù),必須其他方式設(shè)置過期時間伙单。
  • refresh_token:表示更新令牌获高,用來獲取下一次的訪問令牌,可選項吻育。
  • scope:表示權(quán)限范圍念秧,如果與客戶端申請的范圍一致,此項可省略布疼。

例子:返回值采用JSON格式
{
"access_token":"2YotnFZFEjr1zCsicMWpAA",
"token_type":"example",
"expires_in":3600,
"refresh_token":"tGzv3JOkF0XG5Qx2TlKWIA",
"example_parameter":"example_value"
}

3.3 appid和secret的存在意義

這兩個參數(shù)都是從授權(quán)方的開放平臺申請獲取的摊趾。
如果 appid 是為了告訴身份認證服務(wù)器,『我是 百度』游两;那么 secret 是為了告訴身份認證服務(wù)器砾层,『我真的是 百度』。A步驟中贱案,為了告訴身份認證服務(wù)你是哪家第三方服務(wù)肛炮,你總是需要暴露一些信息(appid)給身份認證服務(wù)器的(暴露是指用戶能獲取到,比如會在地址欄里出現(xiàn))宝踪。

獲取 code 的時候侨糟,那能暴露的只能是 appid,但如果數(shù)據(jù)交互可以不暴露給用戶瘩燥,比如獲取 access token 那一步秕重,D步驟,由第三方服務(wù)器內(nèi)部直接發(fā)起厉膀,用戶并不可見溶耘,那會帶上 secret二拐。secret 為什么叫 secret,就因為他絕對不能暴露給外網(wǎng)凳兵。secret其實就是第三方網(wǎng)站與 OAuth 服務(wù)網(wǎng)站之間的信物百新。此信物是一定一定不能被第三者知道的。如果知道了一定要第一時間重新生成庐扫。

3.4 Code的存在意義

可能看到這吟孙,大家會問,Code有必要存在嗎聚蝶?我為什么不能直接申請token呢杰妓?
OAuth 2.0 當(dāng)初設(shè)計的一個目標(biāo)之一是,讓不支持 https 的網(wǎng)站也能安全使用碘勉。既然提到了 https巷挥,必然跟中間人攻擊有關(guān)系。

我們先舉個栗子

我們先假設(shè) OAuth 不需要整什么 code验靡,就直接獲取 access token倍宾,那么流程就是(還是拿 baidu.com 和微信舉例):

用戶瀏覽器訪問 baidu.com,baidu.com 服務(wù)器發(fā)現(xiàn)用戶處于未登錄狀態(tài)胜嗓,返回 302高职,讓瀏覽器跳轉(zhuǎn)到微信 OAuth 服務(wù)獲取 access token,(假設(shè)為 https://wx.qq.com/token?appid=xxx&redirect_uri=http://chrisyue.com&scope=...)
用戶在微信的網(wǎng)頁上完成了賬號密碼的輸入并登錄成功(或者已經(jīng)登錄授權(quán)成功)辞州,微信服務(wù)器也返回 302怔锌,讓瀏覽器跳轉(zhuǎn)到 redirect_uri 指定的地址并且?guī)?access token 參數(shù)。
用戶瀏覽器訪問帶 access token 的鏈接变过,完成整個登錄埃元。
此流程沒大毛病,就是最后一步媚狰,如果 chrisyue.com 是不支持 https 訪問的岛杀,那么 access token 就等于是暴露在瀏覽器和 chrisyue.com 服務(wù)器之間的線路中。

當(dāng)然崭孤,從另外一方面來說类嗤,如果第三方網(wǎng)站強行要求必須支持 https,理論上來說辨宠,code 這一步也是可以省的遗锣。

可能也有人會問,那多一步獲取 code 有什么用呢彭羹?如果 baidu.com 不支持 https黄伊,code 不也是會被暴露嗎泪酱?攻擊者拿到 code派殷,類似與之前討論 redirect_uri 是否可以不檢查域名時所做的一樣还最,直接用獲取到的 code,訪問 baidu.com 獲取 access token 的地址來登錄受害人的賬號毡惜。針對這個問題拓轻,OAuth2.0 協(xié)議其實對此是有處理方式的:

  • code 只能被使用一次。
  • 若是攻擊者比正常用戶先用了 code 也沒事经伙,因為如果同一個 code 被用了兩次扶叉,之前通過此 code 獲取的 access token 將被撤回,而因為普通用戶本來就是要訪問拿 code 換 access token 的地址帕膜,code 是一定會被用的

也就是說枣氧,攻擊者最多讓正常用戶有點困擾,可能會出現(xiàn)登錄意外失敗垮刹,或者明明看起來登錄成功但還是獲取不到用戶信息的情況(access token 已經(jīng)失效)达吞,但攻擊者依舊拿不到數(shù)據(jù)。

4.資料

4.1 大佬的教學(xué)文章

以下文章沒有先后荒典,會讓大家更深入了解OAuth2.0酪劫,如果大家不喜歡我這篇,以下幾篇足夠用了:

理解OAuth 2.0
OAuth2集成——《跟我學(xué)Shiro》
關(guān)于 OAuth2.0 安全性你應(yīng)該要知道的一些事

4.2 微博開放平臺API

現(xiàn)在微博寺董,微信覆糟,支付寶等用的都是OAuth2.0協(xié)議,給大家拿微博的API看下遮咖,可以確認自己學(xué)的不是假的滩字。(/ω\)

5.總結(jié)

本篇文章我們圍繞著:

  1. OAuth2.0是什么?做什么御吞?
  2. 關(guān)鍵字與運行流程
  3. 四種授權(quán)模式(授權(quán)碼模式)
  4. Code的作用

以上四個方面對OAuth2.0進行了學(xué)習(xí)踢械,希望大家讀完這篇文章,會對OAuth2.0有一個更深入的了解魄藕。如果我的文章能給大家?guī)硪稽c點的福利内列,那在下就足夠開心了。
下次再見背率!

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末话瞧,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子寝姿,更是在濱河造成了極大的恐慌交排,老刑警劉巖,帶你破解...
    沈念sama閱讀 219,490評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件饵筑,死亡現(xiàn)場離奇詭異埃篓,居然都是意外死亡,警方通過查閱死者的電腦和手機根资,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,581評論 3 395
  • 文/潘曉璐 我一進店門架专,熙熙樓的掌柜王于貴愁眉苦臉地迎上來同窘,“玉大人,你說我怎么就攤上這事部脚∠氚睿” “怎么了?”我有些...
    開封第一講書人閱讀 165,830評論 0 356
  • 文/不壞的土叔 我叫張陵委刘,是天一觀的道長丧没。 經(jīng)常有香客問我,道長锡移,這世上最難降的妖魔是什么呕童? 我笑而不...
    開封第一講書人閱讀 58,957評論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮淆珊,結(jié)果婚禮上拉庵,老公的妹妹穿的比我還像新娘。我一直安慰自己套蒂,他們只是感情好钞支,可當(dāng)我...
    茶點故事閱讀 67,974評論 6 393
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著操刀,像睡著了一般烁挟。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上骨坑,一...
    開封第一講書人閱讀 51,754評論 1 307
  • 那天撼嗓,我揣著相機與錄音,去河邊找鬼欢唾。 笑死且警,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的礁遣。 我是一名探鬼主播斑芜,決...
    沈念sama閱讀 40,464評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼祟霍!你這毒婦竟也來了杏头?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,357評論 0 276
  • 序言:老撾萬榮一對情侶失蹤沸呐,失蹤者是張志新(化名)和其女友劉穎醇王,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體崭添,經(jīng)...
    沈念sama閱讀 45,847評論 1 317
  • 正文 獨居荒郊野嶺守林人離奇死亡寓娩,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,995評論 3 338
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片棘伴。...
    茶點故事閱讀 40,137評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡寞埠,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出排嫌,到底是詐尸還是另有隱情,我是刑警寧澤缰犁,帶...
    沈念sama閱讀 35,819評論 5 346
  • 正文 年R本政府宣布淳地,位于F島的核電站,受9級特大地震影響帅容,放射性物質(zhì)發(fā)生泄漏颇象。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,482評論 3 331
  • 文/蒙蒙 一并徘、第九天 我趴在偏房一處隱蔽的房頂上張望遣钳。 院中可真熱鬧,春花似錦麦乞、人聲如沸蕴茴。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,023評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽倦淀。三九已至,卻和暖如春声畏,著一層夾襖步出監(jiān)牢的瞬間撞叽,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,149評論 1 272
  • 我被黑心中介騙來泰國打工插龄, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留愿棋,地道東北人。 一個月前我還...
    沈念sama閱讀 48,409評論 3 373
  • 正文 我出身青樓均牢,卻偏偏與公主長得像糠雨,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子徘跪,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,086評論 2 355

推薦閱讀更多精彩內(nèi)容