凡是涉及到加密的時候,就涉及到安全,但是,在實際的開發過程中,涉及到安全部分的又比較少,有些甚至是框架給你做好了,不需要自己考慮。但是我們也還是需要去熟悉一下的。加密涉及到的東西不算難,有點雜,有些亂,每個人都會講一點,但是真的去說的時候又講不出個所以然。所以導致很多人對加密有些誤解。所以希望這篇文章對你有所幫助。
先說一下加密的概念吧,因為有些東西確實不是加密,又被大家冠以加密的頭銜,久而久之加密與非加密就特別容易混淆了。那加密的概念是什么呢?
在密碼學中,加密(英語:Encryption)是將明文信息改變為難以讀取的密文內容,使之不可讀的過程。只有擁有解密方法的對象,經由解密過程,才能將密文還原為正??勺x的內容?!S基百科
Base64
首先說一下 Base64 ,網上有人說,Base64 是加密,有人說不是。那他到底是不是呢?想回答這個問題,不難,了解一下 Base64 就行。
Base64 是一種使用 64 個字符來表示二進制數據的一種編碼方式。主要作用是將二進制數據重新編碼使其成為文本,便于傳輸。什么意思?舉個例子。
比如需要開發一個上傳圖片的功能,但是我們沒有一個用于獨立的上傳圖片的接口,怎么辦呢?網頁或客戶端將圖片使用 Base64 轉一下,讓它成為字符串數據,然后發送字符串即可。
下表為 Base64 碼表,圖片來自維基百科。
當然,非二進制數據即文本數據也是可以轉換的,但是本來就是文本數據(字符串)你再使用 Base64 轉換一下,干啥呢?啥,安全?高效?
簡單來說 Base64 是通過將每 6 位為一個看成一個字節,然后映射到 Base64 的碼表中得到相應的字符串。點擊這里查看更多關于Base64的詳細信息 因為其轉換過程的計算方法是公開的,所以在網上你能搜到很多在線 Base64 的轉換工具,有的叫 Base64 加密、解密,有的叫 Base64 編碼、解碼。可能這也是讓大家搞混的原因之一吧,至少在我看來不是加密。只是將二進制數據轉換成文本數據,便于傳輸。
Base64 轉換過程,參考下表:
表格來自維基百科
還有人說,使用 Base64 就不是為了安全,是因為它高效才用的。說這話的人,可能對 Base64 的編碼過程不太了解,我來解釋一下上面的圖片的意思,Base64 是首先將待轉換的數據在末尾以補 0 的方式將數據長度補全為 3 的倍數。然后以每 6 位作為一個字節,不足 6 位的最高位補 0,再將其對于到碼表中,所以,使用 Base64 只會讓數據長度變長,具體變長多少呢?1/3。既然使用 Base64 轉換后的數據都變長了,怎么高效?
再多說一點點,仔細看,其實 Base64 不是 64 個字符,是 65 個,除了 a-z、A-Z、0-9 以及兩個特殊字符外還有一個 =
作為結束標記。但是 =
不是一定會出現的。
Hash
Hash 平時可能都有用過,但是不太熟悉,甚至,還可能覺得什么把 Hash 跟加密放在一起?是因為 Hash 跟 Base64 一樣,也是容易被人混淆的。那么 Hash 到底是什么呢?Hash 在英語中有把……弄亂,切碎的意思。什么意思呢?就是把任意長度的數據映射為固定(有限)長度的數據。比如 I'm a developer
對應的 Hash 值如下:
-
SHA1
71c25c6e21f9a1571c8aab270d8a4dee3c2a07c1
-
SHA256
0f7f321e14c9dc026f95e7569dde90dcef988ff44d30ac2dc9e24168e05111b4
-
MD5
db32e7134744e20e174c9425e627dd10
可以看到,一個字符串有多個 Hash 值,這是什么情況呢?這是因為 Hash 有多種算法,SHA1、SHA256、MD5都是其中一種,還有其他的算法,比如 SHA224,同時不同的算法生成的 Hash 值的長度也不同。哎,那我同一個數據經過 Hash 之后得到的數據,變長了,或是變短了,是不是就是加密?
不好意思,還真不是,為什么呢?因為 Hash 的算法是不可逆的,說不可逆好像也不太合適,就是你只能使用 Hash 算法將 I'm a developer
變成上面幾個數據中的一個,但是,你沒辦法通過 Hash 后的數據再轉換到 I'm a developer
。哇,聽起來有點雞肋啊,那他能干啥呀。不能加密算了,還產生那么一堆看起來沒什么用的東西。別急啊。
因為一旦選定好 Hash 算法之后,Hash 值就是固定的了。所以,Hash 一般用來校驗數據。比如,你在網上下載一個文件的時候,有些下載提供商會提供幾種算法的 Hash 值,干啥呢。用來保證你下載的文件確定是沒有被有心之人篡改后的。因為同樣的數據對應的 Hash 值也是一致的,即使是略微的改動也會導致 Hash 值與之前的千差萬別。比如I'm a Developer
我只是改了其中一個字母,使用 MD5 算法得到的 Hash 值為:
1b77d24eb81c857f2f5505ca61eda70a
你看,我只是把 d
改為 D
,它與之前的 MD5 的值就完全不一樣了。
那為什么還有人說,MD5 快被破解了?是這樣的,因為 Hash 的被破解,不是真的說能將一個 Hash 后的字符串還原到源數據,而是說找到一種算法,通過這個算法能找到一個與源數據不同但經過 Hash 計算之后得出的 Hash值一致的情況。
連講了兩個都不是加密的東西,再不講,加密,說不過去了。接下來開始對稱加密、非對稱加密。
對稱加密
對稱加密的原理很簡單就是加密與解密使用同一個密鑰進行。即:使用加密算法與密鑰對原數據進行加密,使用解密算法與密鑰對密文進行解密。哎,等等,加密算法與解密算法?解釋一下,解密算法是加密算法的反向運算。
你看,由于加密與解密使用的是同一個密鑰,所以安全性在一定程度上得不到保證。必須保證通信雙方先擁有一套不被其他人知道的密鑰。不過它也是有其他有點的,比如,性能好,計算速度快,不過這個也是在犧牲密鑰長度的基礎上做的,這么一看,好像優點不是那么明顯……
常見的對稱加密算法有:DES、3DES、AES、RC5、RC6。其中,DES 因為密鑰長度太短已經逐漸被棄用。
非對稱加密
剛才說了,對稱加密是不能在不安全的網絡中直接傳輸密鑰的,那非對稱加密呢?它是可以在網絡上進行傳輸密鑰的,因為它的密鑰是兩個。一個公鑰,一個私鑰。公鑰用于在網絡上進行傳輸,私鑰留在自己手中用來解密。
非對稱加密使用進行公鑰加密、私鑰進行解密。使用公鑰對數據進行加密得到密文,使用私鑰對密文進行解密得到數據。私鑰是能解開公鑰加密的數據,公鑰也能解開私鑰加密的數據。
因為非對稱加密中公鑰與私鑰是可以互相解開的,所以,非對稱加密還可以用于數字簽名,使用 私鑰 對原數據的 Hash 值進行加密,然后,附加在原數據的后面,這樣既保證了原數據是可讀的,又可以在數據接收完成之后對數據的完整性加以驗證。
非對稱加密的優點與缺點也很清晰,優點就是能在網絡上進行傳輸自己的密鑰,就這一點來說,就已經比對稱加密厲害了,因為如果對稱加密把自己的密鑰放在網絡上 進行傳輸,很有可能被有心之人獲取,然后做一些不可描述的事情。非對稱加密就不會存在這個問題,因為它是有兩個密鑰的。這個是優點。缺點是什么呢?就是性能方面相對于對稱加密差一點。
常見的算法有:RSA、ElGamal、背包算法、橢圓曲線加密算法。
為什么經過非對稱加密后的信息在網絡傳輸中是安全的
這里引入一個場景。A、B 兩人通信,C 作為壞人,截獲、篡改 A、B 之間的通信內容。
先看看對稱加密后的信息在網絡傳輸中為什么是不安全的。
首先,因為對稱加密需要雙方共同有一套密鑰,那么密鑰是需要在網絡上進行傳輸的,在這一步,就已經不安全了,因為,一旦 A、B 在網絡上傳輸了密鑰,C 一定能獲取到,那么此后的所有經過加密的內容對于 C 來說,只是需要去把加密后的數據解開即可。
再來看看如果使用非對稱加密該怎么做。
首先通信雙方會先把自己的公鑰發送給對方,然后使用對方的公鑰對數據進行加密后傳輸。這個時候即使 C 在 A、B 交換公鑰的過程中拿到公鑰也是沒用的,因為公鑰是拿來加密的,而要解密就需要 A、B 的私鑰了。所以這個時候 C 是不能進行截獲的。這樣就絕對安全了嗎?并非如此,要知道,C 可是同時擁有 A、B 的公鑰,那只有公鑰能干什么呢?能偽造數據,C 雖然不能將 A、B 通信的內容進行獲取、篡改,但是 C 能發送一個全新的數據,然后時候公鑰進行加密呀。這樣也是能達到欺騙對方的目的。所以這還不是最終的解決方案。
所以最終的解決方案是,使用自己的私鑰對已經使用對方公鑰的密文再加密一次。之前使用對方的公鑰來進行加密,C 還能做到自己偽造一個假的數據,但是現在通信需要使用私鑰再次加密了,C 連偽裝都做不到了,為什么?因為 C 沒有任何一方的私鑰。
舉個例子,C 使用 B 的公鑰對偽裝數據進行加密然后發送給 B,這時候 B 拿到數據會先用 A 的公鑰來解開(因為在規定中,是先用 B 的公鑰加密,然后再使用 A 的私鑰進行加密,在解密的時候,就需要先使用 A 的公鑰來解密,然后使用 B 的私鑰再次解密),但這時候 B 會發現,經過 A 的公鑰解密再次經過 B 的私鑰解密后數據就完全沒法看了。因為在加密的時候少了一個使用 A 的私鑰進行加密的環節。
非對稱加密有點繞,還是得自己多想想。到這里,已經非常像 HTTPS 了,但還不是,HTTPS 比這個非對稱加密還稍微麻煩一點,敬請期待。