node.js的crypto在0.8版本,這個模塊的主要功能是加密解密。
node利用 OpenSSL庫(https://www.openssl.org/source/)來實現它的加密技術,
這是因為OpenSSL已經是一個廣泛被采用的加密算法。它包括了類似MD5 or SHA-1 算法,這些算法你可以利用在你的應用中。
作為工程師,對於openssl一個開源的軟件庫,你沒有用過,你應該聽過這個名字。openssl是使用C/C++實現算法的。
Nodejs用C/C++實現這些算法后,通過cypto這個模塊暴露為JavaScript接口,這樣用起來方便,運行速度也快。
同步文章:http://www.mwcxs.top/page/421.html,歡迎訪問交流學習社區,社區源碼在github上:https://github.com/saucxs/nodeJSBlog,歡迎fork和start。
以下你可以看到內容:
一、首先看一下hash算法
二、HMAC算法
三、加密算法知識
四、SSL協議
一、首先看一下hash算法
1.1創建hash實例
通過crypto.createHash()函數,,創建一個hash實例,但是需要調用md5,sha1,sha256,sha512算法來實現實例的創建。
const hash = crypto.createHash('md5');
這樣帶有md5加密算法的hash實例創建成功。可以把md5換成sha1護着其他的。
MD5是最常用的,但是他有一定的碰撞的問題,你可以使用更新的sha1算法。
1.2加密數據
通過hash.update('需要機密的字符串')函數,實現加密。
hash.update('需要加密的字符串');
這樣數據就加密好了,但是我怎么看到我加密的數據。
注意:hash.update()方法是有記憶功能的,實際就是將字符串相加
1.3獲取hash對象
可以通過hash.digest()函數實現字符串加密返回。
hash.digest()
直接運行 hash.digest(); 出現了亂碼,因為它默認返回的是2進制的數據;
所以使用的是
hash.digest('hex');
這樣就可以以16進制的形式顯示出來
md5.digest();這個方法被調用了,hash 對象就被清空了是不能被重用的。
2、md5加密的栗子
const crypto = require('crypto'); const hash = crypto.createHash('md5'); hash.update('HEllo World'); hash.update('hhhhhhh'); console.log(hash.digest('hex'));
使用node index.js方式運行,因為crypto需要用到nodeJS的核心模塊。(注:crypto.js是我們自己編寫的js文件)
輸出結果:
28210daaea2a2a4dcc6d29f775671854
3、md5的update()函數由記憶功能
以下是crypto.js代碼:
const crypto = require('crypto'); const hash = crypto.createHash('md5'); hash.update('HEllo Worldhhhhhhh'); console.log(hash.digest('hex'));
運行,結果一樣:
4、sha1的加密算法
const crypto = require('crypto'); const hash = crypto.createHash('sha1'); hash.update('HEllo Worldhhhhhhh'); console.log(hash.digest('hex'));
輸出結果:
f67592206f0fe61cb3123cabf8d9dbe160a7f54a
5、sha256的加密算法
const crypto = require('crypto'); const hash = crypto.createHash('sha256'); hash.update('HEllo Worldhhhhhhh'); console.log(hash.digest('hex'));
輸出結果
300bfc4b9f19bcfc6a8fac7ea54e4e8d31b0cea544c23f9e4cea21dc94c3ea22
6、sha512的加密算法
const crypto = require('crypto'); const hash = crypto.createHash('sha512'); hash.update('HEllo Worldhhhhhhh'); console.log(hash.digest('hex'));
輸出結果
062e805ad0c342151275dec7c25f4bc15fca747f70395cda6b41d6fce7c5954628e0f42587f5d6d3d6312ae353f72208c9ca6bfdd7b953dbb51317db79abfc34
二、HMAC算法
翻譯之后的就是"哈希運算消息認證碼"
利用哈希算法,以一個密鑰和一個消息為輸入,生成一個加密串作為輸出。
HMAC可以有效防止一些類似md5的彩虹表等攻擊,比如一些常見的密碼直接MD5存入數據庫的,可能被反向破解。
crypto.createHmac(algorithm, key)
這個方法返回和createHash一樣,返回一個HMAC的實例,有update和digest方法。
但是這個key怎么獲取呢?這個要說一下SSL,利用opensll命令來創建一個key.pem,這個key.pem就是key,就是這個秘鑰。
這樣我們就生成了一個秘鑰key.pem
var crypto = require('crypto'); var fs = require('fs'); var pem = fs.readFileSync('key.pem'); var key = pem.toString('ascii'); var hmac = crypto.createHmac('sha1', key); hmac.update('foo'); hmac.digest('hex'); '7b058f2f33ca28da3ff3c6506c978825718c7d42'
先通過 fs.readFileSync 方法讀取了key.pem密鑰,
然后將它轉為ascii碼,
最后通過 createHmac(‘sha1’, key) 方法獲得HMAC實例,
然后執行update和digest,
生成一串密鑰字符串。
注意:由於key的不同,所以同樣的字符串’foo’經過hmac加密后生成的16進制字符串也是不同的,從而更加保障了數據的安全性。
三、加密算法知識
1、什么是加密算法?
加密算法很容易理解,就是把明文變成人家看不懂的東西,然后送給自己想要的送到的地方,接收方用配套的解密算法又把密文解開成明文,這樣就不怕密文給人家截獲而泄密。
2、加密算法的種類 ?
大致分為2類,一種是基於key的,一種不是基於key的。 不基於key的算法就是消息雙方都通過一定的加密和解密算法來進行通信,這種算法缺點很明顯如果加密算法被破解了就泄露了。
3、基於key的加密算法?
key是一個什么東西呢?隨便你,可以是一個隨機產生的數字,或者一個單詞,啥都行,只要你用的算法認為你選來做key的東西合法就行。所以基於key的加密算法又分為2類:對稱加密和不對稱加密。對稱加密算法的原理很容易理解,通信一方用KEK加密明文,另一方收到之后用同樣的KEY來解密就可以得到明文。
4、不對稱加密算法?
不對稱加密指雙方用不同的KEY加密和解密明文,通信雙方都要有自己的公共密鑰和私有密鑰。舉個例子比較容易理解,我們們假設通信雙方分別是A,B. A,擁有KEY_A1,KEY_A2,其中KEY_A1是A的私有密鑰,KEY_A2是A的公共密鑰。 B,擁有KEY_B1,KEY_B2,其中KEY_B1是B的私有密鑰,KEY_B2是B的公共密鑰。公共密鑰和私有密鑰的特點是,經過其中任何一把加密過的明文,只能用另外一把才能夠解開。也就是說經過KEY_A1加密過的明文,只有KEY_A2才能夠解密,反之亦然。
4.1不對稱加密算法通信過程:
4.1.1公共秘鑰交換
A-------->;KEY_A2------------>B
A<--------KEY_B2<------------A
這個過程叫做公共密鑰交換,老外管這叫keyexchange。
4.1.2公共秘鑰解密
之后A和B就分別用對方的公共密鑰解密,用自己的私有密鑰加密。 一般公共密鑰是要發布出去的,這就是SSL使用的驗證機制(注意不是數據傳輸機制)。
常用的不對稱加密一般有RSA,DSA,DH等。我們一般使用RSA。
四、SSL協議
4.1 SSL簡介
openssl的命令很多,整理一下:
SSL(SecureSocketLayer)是netscape公司提出的主要用於web的安全通信標准,.
TLS(TransportLayerSecurity)是IETF的TLS工作組在SSL3.0基礎之上提出的安全通信標准,
SSL/TLS提供的安全機制可以保證應用層數據在互聯網絡傳輸不被監聽,偽造和竄改。
1、一般情況下的網絡協議應用中,數據在機器中經過簡單的由上到下的幾次包裝,就進入網絡,如果這些包被截獲的話,那么可以很容易的根據網絡協議得到里面的數據.由網絡監聽工具可以很容易的做到這一點。
2、SSL就是為了加密這些數據而產生的協議,可以這么理解,它是位與應用層和 TCP/IP之間的一層,數據經過它流出的時候被加密,再往TCP/IP送,而數據從TCP/IP流入之后先進入它這一層被解密,同時它也能夠驗證網絡連接兩端的身份(根據我們之前學習的不對稱加密算法只是可知)。
3、SSL協議包含2個子協議,一個是包協議,一個是握手協議。包協議位於握手協議更下一層,我們暫時對包協議的內容沒有興趣。SSL握手過程說簡單點就是:通信雙方通過不對稱加密算法來協商好一個對稱加密算法以及使用的key,然后用這個算法加密以后所有的數據完成應用層協議的數據交換。
4.2 SSL通信流程:
握手一般都是由client發起的,SSL也不例外。
1、client送給server它自己本身使用的ssl的version(ssl一共有三個version),加密算法的一些配置,和一些隨機產生的數據,以及其他在SSL協議中需要用到的信息。
2、server送給client它自己的SSL的version,加密算法的配置,隨機產生的數據,還會用自己的私有密鑰加密SERVER-HELLO信息。Server還同時把自己的證書文件給送
過去。同時有個可選的項目,就是server可以要求需要客戶的certificate。
3、client就用server送過來的certificate來驗證server的身份。如果server身份驗證沒通過,本次通信結束。通過證書驗證之后,得到server的公共密鑰,解開server送來的
被其用私有密鑰加密過的SERVER-HELLO信息,看看對頭與否。如果不對,說明對方只有該server的公共密鑰而沒有私有密鑰,必是假的。通信告吹。
4、client使用到目前為止所有產生了的隨機數據(sharedsecret),client產生本次握手中的premastersecret(這個步驟是有可能有server的參與的,由他們使用的加密算法決
定),並且把這個用server的公共密鑰加密,送回給server.如果server要求需要驗證client,那么client也需要自己把自己的證書送過去,同時送一些自己簽過名的數據過去。
RSA就是我們上一章說過的一種不對稱加密算法。首先server把自己的RSA公共密鑰送給client,client於是用這個key加密一個隨機產生的值(這個隨機產生的值就是
sharedsecret),再把結果送給server.
5、Server驗證完client的身份之后,然后用自己的私有密鑰解密得到premastersecret然后雙方利用這個premastersecret來共同協商,得到mastersecret. 6、雙方用master
一起產生真正的sessionkey,着就是他們在剩下的過程中的對稱加密的key了。這個key還可以用來驗證數據完整性。雙方再交換結束信息。握手結束。
同步文章:http://www.mwcxs.top/page/421.html,歡迎訪問交流學習社區,社區源碼在github上:https://github.com/saucxs/nodeJSBlog,歡迎fork和start。