[转]TCP(HTTP)长连接和短连接区别和怎样维护长连接
原文鏈接
一、HTTP協議和TCP協議
HTTP的長連接和短連接本質上是TCP長連接和短連接。HTTP屬于應用層協議,在傳輸層使用TCP協議,在網絡層使用IP協議。IP協議主要解決網絡路由和尋址問題,TCP協議主要解決如何在IP層之上可靠的傳遞數據包,使在網絡上的另一端收到發端發出的所有包,并且順序與發出順序一致。TCP有可靠,面向連接的特點。
二、HTTP協議的長連接和短連接
在HTTP/1.0中,默認使用的是短連接。也就是說,瀏覽器和服務器每進行一次HTTP操作,就建立一次連接,但任務結束就中斷連接。如果客戶端瀏覽器訪問的某個HTML或其他類型的 Web頁中包含有其他的Web資源,如JavaScript文件、圖像文件、CSS文件等;當瀏覽器每遇到這樣一個Web資源,就會建立一個HTTP會話。
但從 HTTP/1.1起,默認使用長連接,用以保持連接特性。使用長連接的HTTP協議,會在響應頭有加入這行代碼:
Connection:keep-alive在使用長連接的情況下,當一個網頁打開完成后,客戶端和服務器之間用于傳輸HTTP數據的 TCP連接不會關閉,如果客戶端再次訪問這個服務器上的網頁,會繼續使用這一條已經建立的連接。Keep-Alive不會永久保持連接,它有一個保持時間,可以在不同的服務器軟件(如Apache)中設定這個時間。實現長連接要客戶端和服務端都支持長連接。
HTTP協議的長連接和短連接,實質上是TCP協議的長連接和短連接。
三、TCP長連接和短連接:
我們模擬一下TCP短連接的情況,client向server發起連接請求,server接到請求,然后雙方建立連接。client向server 發送消息,server回應client,然后一次讀寫就完成了,這時候雙方任何一個都可以發起close操作,不過一般都是client先發起 close操作。為什么呢,一般的server不會回復完client后立即關閉連接的,當然不排除有特殊的情況。從上面的描述看,短連接一般只會在 client/server間傳遞一次讀寫操作
短連接的優點是:管理起來比較簡單,存在的連接都是有用的連接,不需要額外的控制手段
接下來我們再模擬一下長連接的情況,client向server發起連接,server接受client連接,雙方建立連接。Client與server完成一次讀寫之后,它們之間的連接并不會主動關閉,后續的讀寫操作會繼續使用這個連接。
首先說一下TCP/IP詳解上講到的TCP保活功能,保活功能主要為服務器應用提供,服務器應用希望知道客戶主機是否崩潰,從而可以代表客戶使用資源。如果客戶已經消失,使得服務器上保留一個半開放的連接,而服務器又在等待來自客戶端的數據,則服務器將應遠等待客戶端的數據,保活功能就是試圖在服務 器端檢測到這種半開放的連接。
四、長連接和短連接的生命周期
短連接在建立連接后,完成一次讀寫就會自動關閉了。
正常情況下,一條TCP長連接建立后,只要雙不提出關閉請求并且不出現異常情況,這條連接是一直存在的,操作系統不會自動去關閉它,甚至經過物理網絡拓撲的改變之后仍然可以使用。所以一條連接保持幾天、幾個月、幾年或者更長時間都有可能,只要不出現異常情況或由用戶(應用層)主動關閉。
在編程中,往往需要建立一條TCP連接,并且長時間處于連接狀態。所謂的TCP長連接并沒有確切的時間限制,而是說這條連接需要的時間比較長。
五、怎樣維護長連接或者檢測中斷
1、在應用層使用heartbeat來主動檢測。
對于實時性要求較高的網絡通信程序,往往需要更加及時的獲取已經中斷的連接,從而進行及時的處理。但如果對方的連接異常中斷,往往是不能及時的得到對方連接已經中斷的信息,操作系統檢測連接是否中斷的時間間隔默認是比較長的,即便它能夠檢測到,但卻不符合我們的實時性需求,所以需要我們進行手工去不斷探測。
探測的方式有兩種:
2、改變socket的keepalive選項,以使socket檢測連接是否中斷的時間間隔更小,以滿足我們的及時性需求。有關的幾個選項使用和解析如下:
A、我們在檢測對端以一種非優雅的方式斷開連接的時候,可以設置SO_KEEPALIVE屬性使得我們在2小時以后發現對方的TCP連接是否依然存在。用法如下:
keepAlive = 1;
setsockopt(listenfd, SOL_SOCKET, SO_KEEPALIVE, (void*)&keepAlive, sizeof(keepAlive));
B、如果我們不想使用這么長的等待時間,可以修改內核關于網絡方面的配置參數,也可設置SOCKET的TCP層(SOL_TCP)選項TCP_KEEPIDLE、TCP_KEEPINTVL和TCP_KEEPCNT。
TCP_KEEPIDLE:開始首次KeepAlive探測前的TCP空閉時間
The tcp_keepidle parameter specifies the interval of inactivity that causes TCP to generate a KEEPALIVE transmission for an application that requests them. tcp_keepidle defaults to 14400 (two hours).
TCP_KEEPINTVL:兩次KeepAlive探測間的時間間隔
The tcp_keepintvl parameter specifies the interval between the nine retries that are attempted if a KEEPALIVE transmission is not acknowledged. tcp_keepintvl defaults to 150 (75 seconds).
TCP_KEEPCNT:斷開前的KeepAlive探測次數
The TCP_KEEPCNT option specifies the maximum number of keepalive probes to be sent. The value of TCP_KEEPCNT is an integer value between 1 and n, where n is the value of the systemwide tcp_keepcnt parameter.
如果心搏函數要維護客戶端的存活,即服務器必須每隔一段時間必須向客戶段發送一定的數據,那么使用SO_KEEPALIVE是有很大的不足的。因為SO_KEEPALIVE選項指"此套接口的任一方向都沒有數據交換"。在Linux 2.6系列上,上面話的理解是只要打開SO_KEEPALIVE選項的套接口端檢測到數據發送或者數據接受就認為是數據交換。因此在這種情況下使用 SO_KEEPALIVE選項 檢測對方是否非正常連接是完全沒有作用的,在每隔一段時間發包的情況, keep-alive的包是不可能被發送的。上層程序在非正常斷開的情況下是可以正常發送包到緩沖區的。非正常端開的情況是指服務器沒有收到"FIN" 或者 "RST"包。
總結
以上是生活随笔為你收集整理的[转]TCP(HTTP)长连接和短连接区别和怎样维护长连接的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Github项目解析(九)--实现Act
- 下一篇: angularjs-指令ng-disab