HTTPS總結(jié)

HTTPS定義

  1. 全稱(chēng):Hypertext Transfer Protocol over Secure Socket Layer
  2. HTTP的安全版瞧毙,即HTTP之下TCP之上加入SSL層喷好,與HTTP不同的是不同的默認(rèn)端口(http通常是80湿诊,https通常是443)一個(gè)加密/身份驗(yàn)證層
  3. HTTPS協(xié)議需要到CA申請(qǐng)證書(shū)妖混,免費(fèi)證書(shū)很少萍恕,需要交費(fèi)
  4. HTTP的連接是無(wú)狀態(tài)的境氢;HTTPS協(xié)議包含一種類(lèi)似握手協(xié)議的身份認(rèn)證過(guò)程(認(rèn)證是單向的/雙向的)

有兩種基本的加解密算法類(lèi)型

  1. 對(duì)稱(chēng)加密:密鑰只有一個(gè)蟀拷,加密解密為同一個(gè)密碼碰纬,且加解密速度快,典型的對(duì)稱(chēng)加密算法有DES问芬、AES等悦析;

    • 類(lèi)似傳統(tǒng)的賬號(hào)密碼概念,內(nèi)容是賬號(hào)密碼是密鑰
  1. 非對(duì)稱(chēng)加密:密鑰成對(duì)出現(xiàn)此衅,且根據(jù)公鑰無(wú)法推知私鑰强戴,根據(jù)私鑰也無(wú)法推知公鑰;加密解密使用不同密鑰挡鞍,公鑰加密需要私鑰解密骑歹,私鑰加密需要公鑰解密,如RSA墨微。

    • 密文 S = A×B道媚,S是加密后的內(nèi)容,A與B分別是兩個(gè)大素?cái)?shù)(僅可被自己與1整除欢嘿,如13)衰琐,這樣使用A加密后的結(jié)果S只能被B除盡(解開(kāi)),反之同理炼蹦。

有兩種認(rèn)證方法(單向/雙向)

  1. 單向認(rèn)證:一般意義的https羡宙,如瀏覽器訪(fǎng)問(wèn)https網(wǎng)站

    • 主要保證服務(wù)器是它自己所聲明的正確地址
    • 客戶(hù)端和服務(wù)端的內(nèi)容都是通過(guò)對(duì)稱(chēng)密鑰加密的
    • 對(duì)稱(chēng)密鑰是由客戶(hù)端產(chǎn)生,通過(guò)服務(wù)器派發(fā)出的公鑰加密后發(fā)送給服務(wù)器
  2. 雙向認(rèn)證:客戶(hù)端也具有一個(gè)自己的證書(shū)掐隐,如銀行的U盾

    • 客戶(hù)端本身具備證書(shū)狗热,保密的是傳輸過(guò)程本身而不一定能保證服務(wù)器本身是安全的
    • 如常見(jiàn)的釣魚(yú)網(wǎng)站或DNS劫持,用戶(hù)訪(fǎng)問(wèn)的域名并沒(méi)有指向正確的地址虑省,所以客戶(hù)端證書(shū)本身并無(wú)法確保服務(wù)器是真實(shí)的
    • 雙向認(rèn)證是指客戶(hù)端不僅要向CA驗(yàn)證服務(wù)器本身的真實(shí)性匿刮,服務(wù)器在響應(yīng)數(shù)據(jù)時(shí)也要驗(yàn)證接收方的真實(shí)性
    • 詳細(xì)鏈接 Https detail

證書(shū)格式以及轉(zhuǎn)化

證書(shū)的標(biāo)準(zhǔn)

PKCS 全稱(chēng)是 Public-Key Cryptography Standards 
是由 RSA 實(shí)驗(yàn)室與其它安全系統(tǒng)開(kāi)發(fā)商為促進(jìn)公鑰密碼的發(fā)展而制訂的一系列標(biāo)準(zhǔn)
PKCS 目前共發(fā)布過(guò) 15 個(gè)標(biāo)準(zhǔn)。 

常見(jiàn)的標(biāo)準(zhǔn):

  1. PKCS#7 Cryptographic Message Syntax Standard
  2. PKCS#10 Certification Request Standard
  3. PKCS#12 Personal Information Exchange Syntax Standard
  4. X.509是常見(jiàn)通用的證書(shū)格式探颈。所有的證書(shū)都符合為Public Key Infrastructure (PKI) 制定的 ITU-T X509 國(guó)際標(biāo)準(zhǔn)熟丸。

PKCS#7 常用的后綴是: .P7B .P7C .SPC

PKCS#12 常用的后綴有: .P12 .PFX

X.509 DER 編碼(ASCII)的后綴是: .DER .CER .CRT

X.509 PAM 編碼(Base64)的后綴是: .PEM .CER .CRT

編碼與擴(kuò)展名

X.509證書(shū)是一個(gè)數(shù)字文檔,具有擴(kuò)展名和編碼兩個(gè)屬性
  • .DER = DER是一種編碼伪节,擴(kuò)展名有三種光羞。以二進(jìn)制存放,常見(jiàn)于Windows系統(tǒng)
  • .PEM = PEM是一種編碼怀大,擴(kuò)展名也是三種纱兑,文件開(kāi)始由一行"—– BEGIN …“開(kāi)始。
  • .CRT = CRT常見(jiàn)于Linux/Unix證書(shū)化借。證書(shū)可以是DER編碼潜慎,也可以是PEM編碼。
  • .CER = CRT證書(shū)的微軟型式。也可以用兩種編碼铐炫。
  • .KEY = 擴(kuò)展名KEY用于PCSK#8的公鑰和私鑰垒手。可以是兩種編碼驳遵。
  • 擴(kuò)展名CER和CRT幾乎是同義詞淫奔,CRT文件和CER文件只有在使用相同編碼的時(shí)候才可以通過(guò)改后綴名代替。

證書(shū)之間的轉(zhuǎn)換

只有編碼相同可以通過(guò)改后綴名代替堤结,正常情況下應(yīng)該通過(guò)專(zhuān)業(yè)的編碼工具來(lái)互相轉(zhuǎn)換,如OpenSSL

    "openssl x509 -in 你的證書(shū).crt -out 你的證書(shū).cer -outform der"

CA簽名證書(shū)與自簽名證書(shū)

CA簽名證書(shū)如何驗(yàn)證

HTTPS連接建立過(guò)程大致是:

  1. 客戶(hù)端和服務(wù)端建立一個(gè)連接
  2. 服務(wù)端返回一個(gè)證書(shū)
  3. 客戶(hù)端里存有各個(gè)受信任的證書(shū)機(jī)構(gòu)根證書(shū)(IOS8 預(yù)裝的根證書(shū)Apple Support
    )
  4. 用這些根證書(shū)對(duì)服務(wù)端返回的證書(shū)進(jìn)行驗(yàn)證鸭丛,經(jīng)驗(yàn)證如果證書(shū)是可信任的竞穷,就生成一個(gè)pre-master secret
  5. 用這個(gè)證書(shū)的公鑰加密后發(fā)送給服務(wù)端,服務(wù)端用私鑰解密后得到pre-master secret
  6. 再根據(jù)某種算法生成master secret
  7. 客戶(hù)端也同樣根據(jù)這種算法從pre-master secret生成master secret
  8. 隨后雙方的通信都用這個(gè)master secret對(duì)傳輸數(shù)據(jù)進(jìn)行加密解密鳞溉。

自簽名的證書(shū)通過(guò)SSL Pinning使用

  1. 為什么要用SSL Pinning瘾带?

如果服務(wù)端的證書(shū)是從受信任的的CA機(jī)構(gòu)頒發(fā)的,驗(yàn)證是沒(méi)問(wèn)題的熟菲,但CA機(jī)構(gòu)頒發(fā)證書(shū)比較昂貴看政,小企業(yè)或個(gè)人用戶(hù) 可能會(huì)選擇自己頒發(fā)證書(shū),這樣就無(wú)法通過(guò)系統(tǒng)受信任的CA機(jī)構(gòu)列表驗(yàn)證這個(gè)證書(shū)的真?zhèn)瘟顺保孕枰猄SL Pinning這樣的方式去驗(yàn)證允蚣。

  1. 什么是SSL Pinning?

可以理解為證書(shū)綁定呆贿,是指客戶(hù)端直接保存服務(wù)端的證書(shū)(存入Xcode工程)嚷兔,建立https連接時(shí)直接對(duì)比服務(wù)端返回的和客戶(hù)端保存的兩個(gè)證書(shū)是否一樣,一樣就表明證書(shū)是真的做入,不再去系統(tǒng)的信任證書(shū)機(jī)構(gòu)里尋找驗(yàn)證冒晰。

這適用于非瀏覽器應(yīng)用,因?yàn)闉g覽器跟很多未知服務(wù)端打交道竟块,無(wú)法把每個(gè)服務(wù)端的證書(shū)都保存到本地壶运,但CS架構(gòu)的手機(jī)APP事先已經(jīng)知道要進(jìn)行通信的服務(wù)端,可以直接在客戶(hù)端保存這個(gè)服務(wù)端的證書(shū)用于校驗(yàn)浪秘。

  1. 為什么直接對(duì)比就能保證證書(shū)沒(méi)問(wèn)題蒋情?

如果中間人從客戶(hù)端取出證書(shū),再偽裝成服務(wù)端跟其他客戶(hù)端通信秫逝,它發(fā)送給客戶(hù)端的這個(gè)證書(shū)不就能通過(guò)驗(yàn)證嗎恕出?
確實(shí)可以通過(guò)驗(yàn)證,但后續(xù)的流程走不下去违帆,因?yàn)橄乱徊娇蛻?hù)端會(huì)用證書(shū)里的公鑰加密浙巫,中間人沒(méi)有這個(gè)證書(shū)的私鑰就解不出內(nèi)容,也就截獲不到數(shù)據(jù),這個(gè)證書(shū)的私鑰只有真正的服務(wù)端有的畴,中間人偽造證書(shū)主要偽造的是公鑰渊抄。

如何使用AFNetworking發(fā)送HTTPS請(qǐng)求

建立自己的安全策略(Security Policy)

AFSecurityPolicy分三種驗(yàn)證模式:

  • AFSSLPinningModeNone

這個(gè)模式表示不做SSL pinning,只跟瀏覽器一樣在系統(tǒng)的信任機(jī)構(gòu)列表里驗(yàn)證服務(wù)端返回的證書(shū)丧裁。若證書(shū)是信任機(jī)構(gòu)簽發(fā)的就會(huì)通過(guò)护桦,若是自己服務(wù)器生成的證書(shū),這里是不會(huì)通過(guò)的煎娇。

  • AFSSLPinningModeCertificate

這個(gè)模式表示用證書(shū)綁定方式驗(yàn)證證書(shū)二庵,需要客戶(hù)端保存有服務(wù)端的證書(shū)拷貝,這里驗(yàn)證分兩步缓呛,第一步驗(yàn)證證書(shū)的域名/有效期等信息催享,第二步是對(duì)比服務(wù)端返回的證書(shū)跟客戶(hù)端返回的是否一致。

這里還沒(méi)弄明白第一步的驗(yàn)證是怎么進(jìn)行的哟绊,代碼上跟去系統(tǒng)信任機(jī)構(gòu)列表里驗(yàn)證一樣調(diào)用了SecTrustEvaluate因妙,只是這里的列表?yè)Q成了客戶(hù)端保存的那些證書(shū)列表。若要驗(yàn)證這個(gè)票髓,是否應(yīng)該把服務(wù)端證書(shū)的頒發(fā)機(jī)構(gòu)根證書(shū)也放到客戶(hù)端里攀涵?

  • AFSSLPinningModePublicKey

這個(gè)模式同樣是用證書(shū)綁定方式驗(yàn)證,客戶(hù)端要有服務(wù)端的證書(shū)拷貝洽沟,只是驗(yàn)證時(shí)只驗(yàn)證證書(shū)里的公鑰以故,不驗(yàn)證證書(shū)的有效期等信息。只要公鑰是正確的玲躯,就能保證通信不會(huì)被竊聽(tīng)据德,因?yàn)橹虚g人沒(méi)有私鑰,無(wú)法解開(kāi)通過(guò)公鑰加密的數(shù)據(jù)跷车。

整個(gè)AFSecurityPolicy就是實(shí)現(xiàn)這這幾種驗(yàn)證方式棘利,剩下的就是實(shí)現(xiàn)細(xì)節(jié)了,詳見(jiàn)源碼朽缴。

示例代碼

- (void)testClientCertificate {
NSString *url = @"https://218.244.131.231/ManicureShop/api/order/pay/%@";
NSDictionary *dic = @{@"request" : @{
                        @"orderNo" : @"1409282102222110030643",
                        @"type" : @(2)
                        }
                    };

NSData *postData = [NSJSONSerialization dataWithJSONObject:dic options:NSJSONWritingPrettyPrinted error:nil];
//stringWithFormat 自定義文字混淆函數(shù)
NSString *sign = [self signWithSignKey:@"test" params:dic];
NSMutableData *body = [postData mutableCopy];
NSLog(@"%@", [[NSString alloc] initWithData:body encoding:NSUTF8StringEncoding]);
 url = [NSString stringWithFormat:url, sign];

//設(shè)置可以解析的文本
//code =1016錯(cuò)誤因?yàn)檫@里
AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
manager.requestSerializer = [AFJSONRequestSerializer serializer];
manager.responseSerializer = [AFJSONResponseSerializer serializer];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Accept"];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
manager.responseSerializer.acceptableContentTypes = [NSSet setWithArray:@[@"application/json", @"text/plain",@"text/html"]];
//自定義安全策略
manager.securityPolicy = [self customSecurityPolicy];

[manager POST:url parameters:dic success:^(AFHTTPRequestOperation *operation, id responseObject) {
NSLog(@"JSON: %@", responseObject);
} failure:^(AFHTTPRequestOperation *operation, NSError *error) {

NSLog(@"Error: %@", error);
}];
}

//某種和服務(wù)器約定的混淆方式 默認(rèn)使用不混淆
-(id) signWithSingleKey:(NSString *)inString params:    (NSDictionary *)inDictionnary {

return inString;
}

//AFNetworking的自定義安全措施
-(AFSecurityPolicy *) customSecurityPolicy {
NSString *cerPath = [[NSBundle mainBundle] pathForResource:@"工程根目錄中證書(shū)的名字" ofType:@"cer"];
NSData *certData = [NSData dataWithContentsOfFile:cerPath];
//初始化時(shí)使用證書(shū)綁定加密  也可以使用公鑰綁定加密 可選有3種模式
AFSecurityPolicy *securityPolicy = [AFSecurityPolicy policyWithPinningMode:AFSSLPinningModeCertificate];
//允許使用非CA簽名的證書(shū)
//這里有個(gè)問(wèn)題善玫,如果使用的是IP測(cè)試模式 不通過(guò)DNS 需要去AFNet的安全.m文件里注銷(xiāo)掉驗(yàn)證域名的代碼 code=1012因?yàn)檫@里
[securityPolicy setAllowInvalidCertificates:YES];
[securityPolicy setPinnedCertificates:@[certData]];


return securityPolicy;
}

注銷(xiāo)域名驗(yàn)證

前面說(shuō)過(guò),驗(yàn)證站點(diǎn)證書(shū)密强,是通過(guò)域名的茅郎,如果服務(wù)器端站點(diǎn)沒(méi)有綁定域名(萬(wàn)惡的備案),僅靠IP地址上面的方法是絕對(duì)不行的或渤。
需要修改AFNetworking2的源代碼系冗!打開(kāi)AFSecurityPolicy.m文件,找到方法:

- (BOOL)evaluateServerTrust:(SecTrustRef)serverTrust forDomain:(NSString *)domain

將下面這部分注釋掉

//            SecTrustSetAnchorCertificates(serverTrust, (__bridge CFArrayRef)pinnedCertificates);
//
//            if (!AFServerTrustIsValid(serverTrust)) {
//                return NO;
//            }
//
//            if (!self.validatesCertificateChain) {
//                return YES;
//            }

這樣薪鹦,AFSecurityPolicy就只會(huì)比對(duì)服務(wù)器證書(shū)和內(nèi)嵌證書(shū)是否一致掌敬,不會(huì)再驗(yàn)證證書(shū)是否和站點(diǎn)域名一致了惯豆。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市奔害,隨后出現(xiàn)的幾起案子楷兽,更是在濱河造成了極大的恐慌,老刑警劉巖华临,帶你破解...
    沈念sama閱讀 210,978評(píng)論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件芯杀,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡雅潭,警方通過(guò)查閱死者的電腦和手機(jī)揭厚,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 89,954評(píng)論 2 384
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)寻馏,“玉大人棋弥,你說(shuō)我怎么就攤上這事〕锨罚” “怎么了?”我有些...
    開(kāi)封第一講書(shū)人閱讀 156,623評(píng)論 0 345
  • 文/不壞的土叔 我叫張陵漾岳,是天一觀(guān)的道長(zhǎng)轰绵。 經(jīng)常有香客問(wèn)我,道長(zhǎng)尼荆,這世上最難降的妖魔是什么左腔? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 56,324評(píng)論 1 282
  • 正文 為了忘掉前任,我火速辦了婚禮捅儒,結(jié)果婚禮上液样,老公的妹妹穿的比我還像新娘。我一直安慰自己巧还,他們只是感情好鞭莽,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,390評(píng)論 5 384
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著麸祷,像睡著了一般澎怒。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上阶牍,一...
    開(kāi)封第一講書(shū)人閱讀 49,741評(píng)論 1 289
  • 那天喷面,我揣著相機(jī)與錄音,去河邊找鬼走孽。 笑死惧辈,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的磕瓷。 我是一名探鬼主播盒齿,決...
    沈念sama閱讀 38,892評(píng)論 3 405
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了县昂?” 一聲冷哼從身側(cè)響起肮柜,我...
    開(kāi)封第一講書(shū)人閱讀 37,655評(píng)論 0 266
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎倒彰,沒(méi)想到半個(gè)月后审洞,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 44,104評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡待讳,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,451評(píng)論 2 325
  • 正文 我和宋清朗相戀三年芒澜,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片创淡。...
    茶點(diǎn)故事閱讀 38,569評(píng)論 1 340
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡痴晦,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出琳彩,到底是詐尸還是另有隱情誊酌,我是刑警寧澤,帶...
    沈念sama閱讀 34,254評(píng)論 4 328
  • 正文 年R本政府宣布露乏,位于F島的核電站碧浊,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏瘟仿。R本人自食惡果不足惜箱锐,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,834評(píng)論 3 312
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望劳较。 院中可真熱鬧驹止,春花似錦、人聲如沸观蜗。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,725評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)嫂便。三九已至捞镰,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間毙替,已是汗流浹背岸售。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 31,950評(píng)論 1 264
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留厂画,地道東北人凸丸。 一個(gè)月前我還...
    沈念sama閱讀 46,260評(píng)論 2 360
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像袱院,于是被迫代替她去往敵國(guó)和親屎慢。 傳聞我的和親對(duì)象是個(gè)殘疾皇子瞭稼,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,446評(píng)論 2 348

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