KK 的 Web 實驗室(Day7,8,9,10)

Chunhao Weng
12 min readSep 26, 2020

--

這一切都已經發生,只是我們可能還不知道。

TENET

這純粹是自己不知道為什麼想做的事情,紀錄一下 KK 的生命旅程。

Web 實驗室資源:

Youtube

Facebook

以下為 KK 課程內容的文字紀錄,我本人不是KK。(重要)

影片開始。

08 成為看起來很強的後端:Authentication v.s. Authorization

手很明顯是魔術師的手 Sleight of hand

前面的幾支影片已經介紹了網路應用、類別、從瀏覽器到伺服器的流程、以及應用層的協定。

KK 老師今天要來跟大家聊聊「權限」。

(補充: 101 是美國用來辨識初級課程用的編碼,方便學生轉學時銜接課程)

為什麼要聊權限呢?

假設你有個會員系統,你會需要規範什麼樣的人可以做什麼樣的事情。

KK 用網頁遊戲為例,你可能需要知道某個人擁有什麼樣的裝備、或是能不能使用管理員介面。

如果是做課程平台,只有付費購買的會員才能夠觀看課程內容。

權限有哪些模式?

主要兩個,Client To Server 和 Server To Server。

Client To Server 是什麼?

Client 通常指的是使用者使用的平台或軟體,如:瀏覽器 (Browser)或是App。

Client To Server 的驗證就是使用者透過 Client 端登入,獲取權限進入伺服器。

資料傳給 Server

常見的方式是,帳號(account)、密碼 (***)登入,會將資料傳給 Server (伺服器)。

伺服器會跟資料庫(Database,縮寫為 DB)做驗證,跟 Client 端確定登入成功(或沒有)。

Server 跟 DB 做驗證

另外一個常見的模式是「第三方登入」,如:網頁上提供 Facebook 登入、Google 登入、GitHub 登入…等。

此時 Facebook 會回傳一個 token 給伺服器,伺服器就會拿這個 token 去跟 Facebook 要他想要的資料,比較詳細的流程如下。

第三方登入流程

第一步,發 Scope

第一步

Client 端告訴第三方想要什麼資料(KK 說明這些請求為 Scope,找了一下這邊有補充說明

以 Facebook 為例,Client 端會先跟 Facebook 說要使用第三方登入。

此時會跳出 Facebook 介面,讓使用者輸入帳號、密碼,並且選擇同意第三方提供哪些資訊給伺服器,如:姓名、電子郵件、生日…等。

第二步,取 Token

第二步

伺服器取得權限(拿到 token)。

當第三方登入確認你是本人(帳號、密碼輸入正確),就會發一個 token 給伺服器,裡面包含了 Scope 說明使用者同意分享哪些資料。

第三步,拿資料

第三步

伺服器透過 token 取得資料。

總之,從 Client 端透過某些方法跟 Server 端驗證,我們就統稱為 Client To Server 模式。

Server To Server 是什麼?

Server To Server

如字面上意思,是伺服器端直接對伺服器端做對接,如:網站的金流、物流等第三方服務。

剛剛已經看過瀏覽器 Client 端對 Server 端,而 Server 端再對 Server 端這個就是 Server To Server 。

權限驗證上通常 Server To Server 會比 Client To Server 容易實作,因為這些操作都會在「防火牆」內,能夠建立「白名單」來限制哪些 IP 或 Port 可以使用。

Server To Server 常見的有用固定的字串或非對稱加密(公鑰、私鑰)的方式實作,相對 Client To Server 方式少很多。

為什麼呢?

KK 老師說,只要接觸人(Client)的地方都很可怕。

容易搞錯的兩個詞 Authentication 和 Authorization

Authentication 和 Authorization

Authentication(驗證):

你告訴我密碼是什麼,我告訴你對或不對。

KK 舉例:進入校園一定要學生證,只要你拿著學生證,就能進入校園。

Authorization (授權):

講的是有權限做到什麼程度。

KK 舉例:有學生證進入校園,卻不能進入某個辦公室。得到驗證進入,但沒有權限。

Authentication 講的是對或錯,Authorization 講的是 level 到哪裡。

09 成為看起來很強的後端:HTTP 狀態碼

各種 HTTP Status Code

接下來談 HTTP Status Code。

1xx 的暫且不討論,用的地方比較少。
2xx 的通常視為「成功請求」,如:200 是 OK 、 201 是 Created、204 是 No Content。
3xx 的是跟導向有關的「轉址」。
4xx 的是「Client 端的錯誤」,如:404 是 Not Found。
5xx 的是「Server 端的錯誤」。

而跟權限驗證比較有關的是 401 的 Unauthorized 和 403 的 Forbidden。

KK 舉例來說,如果今天去一個網頁,沒有登入但存取一個需要登入才能觀看的網頁。

這就像沒有帶學生證想進校園,會驗證不過並回傳 401 Unauthorized 。

如果是有登入的情形下,到達一個需要是管理員才能觀看的網頁,而你只是一個會員。

此時就會回傳 403 Forbidden 。

補充:至於為什麼 401 的 Unauthorised 是 Authentication (驗證)問題,剛找到這篇解釋滿清楚的。

簡單說 ,1999 寫 HTTP 規格書 RFC 2616 時,Authentication 和 Authorization 兩者經常通用。

之後 OAtuth 的規範才比較明確去定義 401 用在 Unauthorised 的情形,以便於讓使用者明白究竟是要再次驗證(回傳 401 時)還是要告知使用者沒有權限(回傳 403 時)。

再來就是 5xx 系列。常聽到的有:

500 是 Server Error。此時 Reverse Proxy 會回傳這樣的錯誤,讓使用者知道伺服器有問題。

502 是 Bad Gateway,代表 Reverse Proxy 跟 Web Server 斷掉了,也可能是 DNS 連不到 Reverse Proxy。

504 是 Timeout,伺服器回應太慢,通常是超過 30 秒。

10 成為看起來很強的後端:Token 類型

KK 再來解釋什麼是 Token。

中文翻譯為「權杖」、「令牌」,可以想成是學生證,用來通關用。

通常有三種型態,分別為 Event-based 、Time-based 、 Static 。

Event-based 是什麼?

代表是被一個事件觸發,通常是一次性的,我們稱之為 OTP (one-time password) 。

KK 舉例,使用網路銀行的時候,如果點選「轉帳」,此時會寄送一個驗證簡訊給使用者。

這就是一個觸發事件。

Time-based 是什麼?

一般聽到講 token 指的是一個 Time-based 的 token。

舉例來說,如果你在登入時點「忘記密碼」,你的信箱會收到一封有重置密碼連結的信件,上面註明「此連結在x小時內有效」。

Static 是什麼?

自己設定、不會變的,就是一般的 Password 這種。

常聽到的有 JWT (JSON Web Tokens) 、 Cookies 、 Session 、 OAuth 、 API Key 、Basic Authentication…等。

後面章節會把常見的權限驗證方式,根據這裡的分類做更詳細討論。

11 成為看起來很強的後端:雜湊 Hash

立刻進入主題,雜湊(Hash)、編碼(Encode)、加密(Encrypt)。

這三個觀念會影響到後面學習密碼認證、Token認證、OTP、JWT…等等。

雜湊(Hash)是什麼?

很雜的雜、湊合的湊。

把原本的一份資料(圖或字),透過某個 Hash Function (哈希表、哈希函式),變成一個新的東西(雜湊後的值)。

用 Hash Function 變魔術

一般來說,經過雜湊後的值,無法推回原始資料。

原則上是單向的轉換,還原的困難度視雜湊的方式而有差異。

常見的雜湊如: MD5 、 SHA256、SHA512。

目前 MD5 已經被視為太簡單,容易透過「查表」的方式還原。(例如使用 Rainbow table 這種表)

之後討論資安的課程,KK 老師會補充為什麼需要用其他方式去輔助雜湊。

12 成為看起來很強的後端:編碼 Encode

Encode 過去

編碼(Encode)是什麼?

這是屬於雙向的轉換,例如各種語言的轉換(中文轉英文、德文轉日文…等)。

因此編碼的特性是可以過去,也可以回來。

Decode 回來

為什麼需要做編碼這樣的東西?

瀏覽器上我們可能想要呈現一張圖,而存在資料庫的時候或存成文字的時候,需要不同的編碼方式。

例如我們可以透過 Base64 的編碼方式,把任何檔案變成用 a-z, 0–9, +, = 所組成的字串。

常用情境在大頭貼,在網頁載入的時候,用 Base64 轉為字串,加快載入速度。

KK 說,基本上只要最後面看到 = 的字串,很可能是 Base64 的編碼方式。

另外一個常見的是16進制的 Hex 編碼,使用 a-f, 0–9 所組成的字串。

常用 Base64 的原因,是因為他的壓縮率比較高,什麼意思呢?

同樣一張圖,如果使用 Hex 轉換,就會產出一個超長的字串,而 Base64 會比較短。

疑,影片結束了。

13 成為看起來很強的後端:加密 Encrypt

加密就跟腳踏車上鎖、解鎖一樣,可以加密(Encrypt)和解密(Decrypt) 資料。

跟雜湊、編碼不同,加密需要有鑰匙。

加密鑰匙又分兩種。

第一種是加密、解密都只有一把鑰匙,我們稱為「對稱式」加密。

常見的有 AES 演算法。

第二種是加密、解密有兩把鑰匙,我們稱為「非對稱式」加密。

後面的章節會談到 SSL 機制,加密都用公鑰,解密使用私鑰。

這樣的機制讓我們能把公鑰放在網路上,有任何想要發加密的訊息給我,用公鑰就能加密。

而全世界擁有我這把私鑰的人,才能解開這個訊息。

14 成為看起來很強的後端:如何儲存密碼

KK 老師這段分享密碼要如何儲存在資料庫裡面。

快速複習一下三個觀念的特性。

雜湊(Hash)的轉換是單向的。

編碼(Encode)的轉換是雙向的。

加密(Encrypt)的轉換是雙向而且需要鑰匙。

能用編碼(Encode)儲存密碼嗎?

假設我們有帳號 kk 、 密碼 kk123 (老師特別強調這不是他的真實密碼)。

這時候把 kk123 先用 Base64 做編碼,得到某個字串XXX,再把字串XXX存到資料庫裡。

這個做法相對不安全,工程師只需要進入 DB 把 XXX Decode 就能得到 kk123。

進入 DB 就能取得密碼

那能用加密(Encrypt)儲存密碼嗎?

此時我們假設用 AES 加密演算法 Encrypt,需要帶一把 Key 放到 DB 裡面。

而後端工程師一樣有你的 Key ,自然能從 DB 拿回來 Decrypt 回來。

如果能看到整個資料庫所有會員的密碼,那後端工程師就能加以利用。

因此,雙向的編碼(Encode)、加密(Encrypt),都會有這樣的問題。

看來用 AES 加密也不行

那單向的雜湊(Hash)呢?

我們用一樣的方式雜湊一個 XXX,忘記密碼的時候,工程師也會跟你說,他沒辦法幫你。

這時候你會得到一個新的連結,重新產生一組密碼。

而我們重新產生的時候,常常會被告知「密碼不能與上個密碼重複」,是不是密碼被記住了嗎?

此時是因為同樣的密碼會產出相同的 Hash 值,而系統有存之前密碼的 Hash 值。

可是雜湊(Hash)不是會被破解嗎?

Hash 加一點點 Salt

此時我們就會在密碼的前方加上一點 Salt補充),如圖中圈起的 abc。

這樣雜湊的結果用表反查也比較難知道我們的 Salt 到底是加了什麼。

但這樣還是有可能被破解,因此會在用一個 bcrypt補充)的方式,重複 Hash 幾次。

次數越多將會影響登入的速度,同時增加破解的困難度。

KK再次強調:沒有破解不了的系統,只有讓破解成本越高,降低破解方的動機。(非原文,我的個人解讀)

KK 加油!

有興趣請直接去 Web 實驗室的 Youtube 跟 Facebook 社團吧。

Web 實驗室資源:

Youtube

Facebook

Free

Distraction-free reading. No ads.

Organize your knowledge with lists and highlights.

Tell your story. Find your audience.

Membership

Read member-only stories

Support writers you read most

Earn money for your writing

Listen to audio narrations

Read offline with the Medium app

--

--

Chunhao Weng
Chunhao Weng

Written by Chunhao Weng

Random notes for personal use.

No responses yet

Write a response