1吁津、網(wǎng)絡(luò)七層協(xié)議
2稍算、Http 和 Https 的區(qū)別糊探?Https為什么更加安全?
3髓考、Https的連接建立過程
4儡炼、三次握手 和 四次揮手
5、TCP 和 UDP的優(yōu)缺點
6、Cookie和Session的區(qū)別
7秆麸、Socket的原理和連接過程
8坷随、iOS Socket封包缸匪、粘包闯冷、拆包處理
網(wǎng)絡(luò)七層協(xié)議
- 應(yīng)用層:對應(yīng)應(yīng)用程序的通信服務(wù)的辩诞。例如HTTP,FTP。
- 表示層:主要功能是定義數(shù)據(jù)格式及加密纺涤。
- 會話層:它定義了如何開始译暂、控制和結(jié)束一個會話。
- 傳輸層:這層的功能包括是否選擇差錯恢復(fù)協(xié)議還是無差錯恢復(fù)協(xié)議洒琢,及在同一主機數(shù)據(jù)流的輸入進(jìn)行復(fù)用,還包括對收到的順序不對的數(shù)據(jù)包的重新排序功能褐桌。例如:TCP,UDP衰抑。
- 網(wǎng)絡(luò)層:這層對端到端的包傳輸進(jìn)行定義,它定義了能夠標(biāo)識所有結(jié)點的邏輯地址荧嵌,還定義了路由實現(xiàn)的方式和學(xué)習(xí)的方式呛踊。例如:IP,IPX砾淌。
- 數(shù)據(jù)鏈路層:它定義了在單個鏈路上如何傳輸數(shù)據(jù)。這些協(xié)議與被討論的各種介質(zhì)有關(guān)谭网。
- 物理層:跟傳輸介質(zhì)有關(guān)汪厨。
Http 和 Https 的區(qū)別?Https為什么更加安全愉择?
1劫乱、HTTPS 需要向機構(gòu)申請 CA 證書
2、HTTP 屬于明文傳輸锥涕,HTTPS基于 SSL(安全套接層) 進(jìn)行加密傳輸
3衷戈、HTTP 端口號為 80,HTTPS 端口號為 443 层坠。
4殖妇、HTTPS 是加密傳輸,有身份驗證的環(huán)節(jié)破花,更加安全谦趣。
HTTPS的連接建立過程
HTTPS的連接過程通過對稱和非對稱秘鑰進(jìn)行加密和解密的過程,服務(wù)器通過公鑰和私鑰進(jìn)行非對稱加密座每,客戶端生成隨機數(shù)進(jìn)行對稱加密前鹅。
1、客戶端將隨機數(shù)尺栖、安全協(xié)議版本號嫡纠、加密算法表發(fā)送給服務(wù)器
2、服務(wù)器與自己的加密算法表對比延赌,不匹配除盏。如果匹配,服務(wù)器發(fā)送挫以,對稱算法者蠕,公鑰算法,MAC算法同時還會把數(shù)字證書和生成隨機數(shù)發(fā)送給客戶端掐松。
3踱侣、客戶端驗證服務(wù)器公鑰合法性,如果合法則將服務(wù)器的公鑰來生成一個前主秘鑰大磺,將前主秘鑰抡句,和兩個隨機數(shù)生成會話秘鑰。并通過服務(wù)端的公鑰來對前主秘鑰進(jìn)行非對稱加密杠愧,發(fā)送給服務(wù)端
4待榔、服務(wù)端接收到加密信息后,用私鑰解密得到主秘鑰。并通過前主秘鑰和兩個隨機數(shù)來組裝會話秘鑰锐锣。
5腌闯、得到兩個秘鑰后,開始進(jìn)行數(shù)據(jù)傳輸雕憔∽丝ィ客戶端收到服務(wù)器發(fā)送來的密文,用客戶端密鑰對其進(jìn)行對稱解密斤彼,得到服務(wù)器發(fā)送的數(shù)據(jù)分瘦。同理,服務(wù)端收到客戶端發(fā)送來的密文畅卓,用服務(wù)端密鑰對其進(jìn)行對稱解密擅腰,得到客戶端發(fā)送的數(shù)據(jù)。
三次握手 和 四次揮手
-
三次握手
1.由客戶端向服務(wù)端發(fā)送 SYN 同步報文翁潘。
2.當(dāng)服務(wù)端收到 SYN 同步報文之后趁冈,會返回給客戶端 SYN 同步報文和 ACK 確認(rèn)報文。
3.客戶端會向服務(wù)端發(fā)送 ACK 確認(rèn)報文拜马,此時客戶端和服務(wù)端的連接正式建立渗勘。 -
建立連接
1.這個時候客戶端就可以通過 Http 請求報文,向服務(wù)端發(fā)送請求
2.服務(wù)端接收到客戶端的請求之后俩莽,向客戶端回復(fù) Http 響應(yīng)報文旺坠。 -
四次揮手
當(dāng)客戶端和服務(wù)端的連接想要斷開的時候,要經(jīng)歷四次揮手的過程扮超,步驟如下:
1.先由客戶端向服務(wù)端發(fā)送 FIN 結(jié)束報文取刃。
2.服務(wù)端會返回給客戶端 ACK 確認(rèn)報文 。此時出刷,由客戶端發(fā)起的斷開連接已經(jīng)完成璧疗。
3.服務(wù)端會發(fā)送給客戶端 FIN 結(jié)束報文 和 ACK 確認(rèn)報文。
4.客戶端會返回 ACK 確認(rèn)報文到服務(wù)端馁龟,至此崩侠,由服務(wù)端方向的斷開連接已經(jīng)完成。
TCP 和 UDP的優(yōu)缺點
- TCP:面向連接坷檩、傳輸可靠(保證數(shù)據(jù)正確性,保證數(shù)據(jù)順序)却音、用于傳輸大量數(shù)據(jù)(流模式)、速度慢矢炼,建立連接需要開銷較多(時間系瓢,系統(tǒng)資源)。
- UDP:面向非連接句灌、傳輸不可靠夷陋、用于傳輸少量數(shù)據(jù)(數(shù)據(jù)包模式)、速度快。
Cookie和Session的區(qū)別
- cookie數(shù)據(jù)存放在客戶的瀏覽器上肌稻,session數(shù)據(jù)放在服務(wù)器上。
- cookie相比session不是很安全匕荸,別人可以分析存放在本地的cookie并進(jìn)行cookie欺騙,考慮到安全應(yīng)當(dāng)使用session爹谭。
- session會在一定時間內(nèi)保存在服務(wù)器上。當(dāng)訪問增多榛搔,會比較占用你服務(wù)器的性能,考慮到減輕服務(wù)器性能方面诺凡,應(yīng)當(dāng)使用cookie。
- 單個cookie保存的數(shù)據(jù)不能超過4K践惑,很多瀏覽器都限制一個站點最多保存20個cookie腹泌。而session存儲在服務(wù)端,可以無限量存儲
- 將登錄信息等重要信息存放為session;其他信息如果需要保留尔觉,可以放在cookie中
Socket的原理和連接過程
Socket(套接字)網(wǎng)絡(luò)上兩個程序通過一個雙向通信連接實現(xiàn)數(shù)據(jù)交互凉袱,這種雙向通信的連接。Socket可以支持不同的傳輸協(xié)議(TCP或UDP)侦铜。
是支持TCP/IP協(xié)議的網(wǎng)絡(luò)通信的基本操作單元专甩,包含進(jìn)行網(wǎng)絡(luò)通信的必須的五種信息:連接使用的協(xié)議、本地主機的IP地址钉稍、本地進(jìn)程的協(xié)議端口涤躲、遠(yuǎn)程主機的IP地址、遠(yuǎn)程進(jìn)程的協(xié)議端口贡未。
Socket連接過程:
1种樱、客戶端調(diào)用socket,綁定服務(wù)器的ip和端口號俊卤,發(fā)送一個SYN報文嫩挤,進(jìn)入阻塞等待。
2瘾蛋、服務(wù)器使用socket俐镐,監(jiān)聽狀態(tài),等待客戶端的連接請求并阻塞當(dāng)前進(jìn)程哺哼。
3佩抹、服務(wù)器收到報文,發(fā)送ACK確認(rèn)取董。
4棍苹、客戶端收到確認(rèn)雙方開始進(jìn)行數(shù)據(jù)傳輸。(TCP,UDP)
5茵汰、通訊結(jié)束后關(guān)閉socket枢里,關(guān)閉連接狀態(tài)
iOS Socket封包、粘包、拆包處理
我們在使用Socket時栏豺,理論上可以正常通信彬碱,但是因為防火墻,傳輸速度奥洼,網(wǎng)絡(luò)等原因巷疼,數(shù)據(jù)傳輸過程中會可能出現(xiàn),socket連接中斷灵奖,丟包嚼沿,粘包等情況的方式。因此瓷患,發(fā)送socket的過程就是封包骡尽,拆包,處理粘包問題擅编。
- 封包
socket的報文格式:服務(wù)號(4bytes)+長度(4bytes)+數(shù)據(jù)
我們在轉(zhuǎn)化為二進(jìn)制數(shù)據(jù)傳輸?shù)膮f(xié)議需要依照這樣的格式進(jìn)行傳輸攀细。報頭4個字節(jié)長度的空間,用來存儲服務(wù)號轉(zhuǎn)換成的二進(jìn)制數(shù)據(jù)爱态;然后4個字節(jié)則是表示數(shù)據(jù)的總長度的二進(jìn)制辨图;最后是要傳輸?shù)臄?shù)據(jù)二進(jìn)制格式。
在IOS中肢藐,同樣的發(fā)送數(shù)據(jù)需要將同樣的數(shù)據(jù)轉(zhuǎn)化為二進(jìn)制故河,發(fā)送出去。例如使用CocoaAsyncSocket
進(jìn)行發(fā)送socket時:
NSString * strJson = [[NSString alloc] initWithData :data encoding :NSUTF8StringEncoding];
Cs_Connect *connect = [Cs_Connect new];
connect.serverID = 1;
connect.message = strJson;
connect.length = (int)connect.message.length;
//將數(shù)據(jù)傳換成二進(jìn)制數(shù)據(jù)吆豹,怎么轉(zhuǎn)化網(wǎng)上有
NSMutableData *dataModel = [socket RequestSpliceAttribute:connect];
// 通過Socket發(fā)出去
[socket sendMessage:dataModel];
- 粘包
當(dāng)使用TCP進(jìn)行傳輸時鱼的,基于TCP的socket是以字節(jié)流的方式進(jìn)行傳輸。代表這報文塊和塊之間沒有報文邊界痘煤。
當(dāng)我們在進(jìn)行兩個或以上的數(shù)據(jù)一起進(jìn)行TCP傳輸時凑阶,理想上是一塊一塊的接收。但是現(xiàn)實往往有偏差衷快,導(dǎo)致數(shù)據(jù)會出現(xiàn)多種情況:
1宙橱、數(shù)據(jù)D1,D2分開獨立到達(dá);
2蘸拔、數(shù)據(jù)D1,D2合成一個整體一起到達(dá)师郑;
3、數(shù)據(jù)D1一部分先達(dá)到调窍,還有一部分和D2一起到達(dá)宝冕;
4、數(shù)據(jù)D1和部分D2先到達(dá)邓萨,剩下一部分D2單獨到達(dá)地梨;
除了第一種理想的情況菊卷,其他情況會出現(xiàn)數(shù)據(jù)不完整問題。
- 拆包
為了解決粘包問題宝剖,我們需要在拆包的時候進(jìn)行粘包問題處理洁闰。
1、獲取報頭的長度字段万细,得到數(shù)據(jù)的長度和報文D1的總長度渴庆。
2、將數(shù)據(jù)添加并保存在緩存中雅镊。
3、根據(jù)返回來并保存在數(shù)據(jù)中的長度和長度截取完整包并返回刃滓。
4仁烹、刪除保存在緩存并已經(jīng)正常返回的數(shù)據(jù)包,再讀取下一個咧虎。
//將數(shù)據(jù)存入緩存區(qū)
[self.readBuf appendData:data];
//數(shù)據(jù)中前面有4個字節(jié)的頭信息卓缰,其中前兩位是固定的頭長度(用處不大),后兩位才是數(shù)據(jù)的長度。
//如果大于4個字節(jié)證明有消息砰诵,因為服務(wù)器只要發(fā)送數(shù)據(jù)征唬,必定包含頭
while (self.readBuf.length > 4) {
//將消息轉(zhuǎn)化成byte,計算總長度 = 數(shù)據(jù)的內(nèi)容長度 + 前面4個字節(jié)的頭長度
Byte *bytes = (Byte *)[self.readBuf bytes];
NSUInteger allLength = (bytes[2]<<8) + bytes[3] +4;
//緩存區(qū)的長度大于總長度茁彭,證明有完整的數(shù)據(jù)包在緩存區(qū)总寒,然后進(jìn)行處理
if (self.readBuf.length >= allLength) {
NSMutableData *msgData = [[self.readBuf subdataWithRange:NSMakeRange(0, allLength)] mutableCopy];
//提取出前面4個字節(jié)的頭內(nèi)容,之所以提取出來理肺,是因為在處理數(shù)據(jù)問題的時候摄闸,比如data轉(zhuǎn)json的時候,頭內(nèi)容里面包含非法字符妹萨,會導(dǎo)致轉(zhuǎn)化出來的json內(nèi)容為空年枕,所以要先去掉再處理數(shù)據(jù)問題
[msgData replaceBytesInRange:NSMakeRange(0, 4) withBytes:NULL length:0];
NSLog(@"開始處理數(shù)據(jù)問題");
//處理完數(shù)據(jù)后將處理過的數(shù)據(jù)移出緩存區(qū)
_readBuf = [NSMutableData dataWithData:[_readBuf subdataWithRange:NSMakeRange(allLength, _readBuf.length - allLength)]];
}else{
//緩存區(qū)內(nèi)數(shù)據(jù)包不是完整的,再次從服務(wù)器獲取數(shù)據(jù)乎完,中斷while循環(huán)
[self.clientSocket readDataWithTimeout:-1 tag:0];
break;
}
}
//讀取到服務(wù)端數(shù)據(jù)值后,能再次讀取
[self.clientSocket readDataWithTimeout:-1 tag:0];