最近公司需要通過公網與其它平台完成接口對接,但是基于開發時間和其它因素的考慮,本次對接無法采用https協定實作。既然不能用https協定,那就退而求其次采用http協定吧!
那麼問題來了!在對接的過程中我們需要對如下問題進行相關的考慮:
1、敏感資訊的不可見性
使用http協定傳輸資料很容易被抓包監聽傳輸内容,如果這些資料中存在敏感資訊的話,風險太大了。是以我們需要對我們的傳輸資料進行一定的加密處理,即使資料被預期接收方之外的其它不法分子攔截,也無法輕易的破譯此次請求的傳輸内容!最簡單的方案就是對傳輸資料使用Base64方法轉碼,使得資料具備一定的不可讀性。當然啦,這種方案實際上是不可取的,因為Base64方案太容易被識别然後解密了。比較常見的做法是,發送方和接收方彼此約定密鑰,發送方發送時用密鑰對資料加密,接收方用密鑰對資料解密。比如AES128加密算法?但是AES128加密也存在局限性,需要定期維護。就算你認為你這方的内部人員是可信的,你也無法無法保證對方的密鑰不會洩漏吧。當然聰明的你可能會說,那我就使用非對稱加密算法,比如RSA好了。好像是沒啥問題?但是如果資料量比較大的話,RSA加密方法對伺服器的壓力也是很大的。。是以本次結合了AES和RSA來實作我們的資料傳輸。
2、防止資料被篡改
用簽名!用簽名!用簽名!重要的事情說三遍?例如:當資料被封裝好後,我們可以用md5算法計算出待傳輸資料的摘要字元串作為簽名。當伺服器接受到資料後,同樣使用md5對資料做摘要,同請求封包中的簽名作比較,若不一緻則說明該http請求資料已被篡改。但僅僅使用md5對資料作摘要就夠了嗎?萬一攻擊方發現了資料簽名是用md5做的,攻擊方隻需要對已篡改的資料再做一次md5,同時更新請求中的簽名即可。是以如何生成可靠的簽名也需要我們仔細的斟酌。有幾點我覺得是需要注意的:1、無法輕易的根據簽名推反推出目前簽名所采用的算法;2、簽名算法的複雜性、可靠性;3、不要直接對傳輸資料作簽名,可以先對請求資料作摘要,再使用加密算法生成簽名,既可以提升效率也在一定程度上提高了安全性。
3、http請求的真實性
有很多方案可以保證http請求的真實性。比如使用token來進行身份驗證,可以借鑒微信的身份驗證方案或者jwt實作。本次我們隻做了簡單的處理,在http請求頭中設定了一個時間戳,當伺服器接收到資料後,會取出http請求中的時間戳,同時與伺服器目前時間作比較。若時間間隔過大,則認為該請求是不真實的,直接拒絕并傳回!
上面簡單的介紹了http傳輸敏感資料需要注意的地方,本方案具體實作思路如下圖所示:

發送方需要幹的事
1、生成簽名
- 構造傳輸對象,并将傳輸對象轉換成json字元串
本次接口傳輸采用rest模式作為标準,先構造待傳輸對象。構造完成後借用Google的Gson包來将對象轉換成json字元串。
- 使用md5算法生成json字元串摘要
- 使用RSA公鑰對摘要字元串作加密處理,生成簽名
2、加密請求封包
發送方建立一個http請求時,需要動态的生成一個AESKey,同時使用該AESKey對請求資料作加密處理。為什麼每次請求都需要生成一個新的AESKey呢?主要還是為了防止資料洩漏。如果固定使用相同的Key,萬一Key被發送方内部人員洩漏了,其實也對發送資料的加密也就沒有意義了。
3、加密AES密鑰
在http請求傳遞資料時,AES密鑰也會被同樣傳遞過去。為了保證AES密鑰的安全性,我們采用RSA公鑰對AES密鑰作加密處理。處理完後會放到Http請求頭的Authencation字段中。
4、構造http請求
- 将第一步生成的簽名放到http請求頭中的Authencation字段中
- 将加密後的AES密鑰放到http請求頭中的SecurityKey字段中
- 将該請求建立時間放到http請求頭中的TimesTamp字段中
- 将第二步生成的加密封包放到http body中
5、處理http請求結果
在此之前,請求方和發送方需要約定傳回結果的加密方式。發送方接收到http請求傳回結果後,通過約定的方式對傳回結果進行處理,以供後續使用。這裡我們僅簡單的約定接收方使用接收到的AES密鑰對傳回資料作加密後傳回即可。
接收方需要幹的事
1、請求的真實性校驗
擷取http請求頭中的TimesTamp字段,同時與系統時間作比較。如果請求時間與目前系統時間間隔在五分鐘之内,則認為請求是真實的,反之則認為請求是非法的。
2、擷取AES密鑰
從http請求中的SecurtiyKey擷取被加密的AES密鑰,使用RSA密鑰對其解密,擷取可供使用的AES密鑰
3、擷取請求封包
從httpbody中擷取請求封包,使用上面第二步生成的AES密鑰解密請求封包
4、驗簽
- 對第三步生成的請求封包作md5摘要生成md5Str
- 擷取http請求頭中的Authencation字元串,接着使用接收方儲存的RSA密鑰對其作解密處理擷取rsaDecryptStr
- 比較md5Str和rsaDecryptStr是否一緻,若一緻則驗簽通過
5、業務處理
使用第三步得到的請求封包進行業務處理
6、傳回處理結果
使用第二步擷取到的AES密鑰對傳回結果作加密處理并傳回
總結
本次http請求傳輸敏感資料方案的實作,上面做了詳細的介紹。另外多提一下。在接收方進行驗簽的時候,我們可以定義一個過濾器來過濾指定http請求。在過濾器中完成驗簽的工作,以避免在業務處理代碼中摻雜驗簽代碼!同時使用過濾器也可以對請求傳回結果進行加工處理,在這裡就是用AES密鑰加密傳回結果啦!
