WebSocket

在H5碱屁,js代碼新增了WebSocket的API掂咒。這玩意兒迹蛤,從使用上來說,不難仑扑,也就onopen、onclose置鼻、onmessage镇饮、onerror這幾個接口而已,前段時間使用的時候箕母,就還是不由自主地去看一些這方面的東西储藐。

Websocket是基于TCP協(xié)議上實現(xiàn)的,也有借助HTTP協(xié)議嘶是,但與HTTP1.X協(xié)議不同地方是钙勃,WebSocket是長連接,雙方只需要一個握手動作(這里是借助HTTP協(xié)議)聂喇,就可以建立一條連接通道辖源,接著就能相互傳輸數(shù)據(jù)了;而HTTP1.X是短連接的,每次發(fā)起請求都要在TCP層來個3次握手同木,數(shù)據(jù)傳輸完或到指定的超時時間后就斷開連接浮梢,若要多次請求,就要不斷發(fā)起請求彤路,這樣挺占帶寬秕硝。
Websocket在服務器方面,只需增加支持即可洲尊,如Python的tornado框架就支持远豺,golang也挺多的坞嘀,但我用的是大猩猩:gorilla。web服務器上,nginx在1.3.13版本也支持移必;其他web server,自行去搜索吧憎瘸。瀏覽器方面除了老IE系幌甘,其他瀏覽器目前的新版本基本都支持WebSocket线婚。

Javascript的接口

var conn = new WebSocket("ws://ip:port/");
conn.onclose = function(evt) {
    console.log(evt);
}

conn.onmessage = function(evt) {
    console.log(evt);
}

conn.onopen = function(evt) {
    console.log(evt);
}

conn.onerror = function(evt) {
    console.log(evt);
}

各接口看名稱就知道是什么意思了泪姨。
瀏覽器與服務端建立連接的時候,要經(jīng)過一個Websocket握手協(xié)議

GET /ws HTTP/1.1
Upgrade: websocket
Connection: Upgrade
Host: 172.16.1.11
Origin: http://example.com
Sec-WebSocket-Key: BVuKSx8KJKN2VAGM0i6gjw==
Sec-WebSocket-Version: 13

這是正常的HTTP的GET請求,然后在請求頭里增加了

Upgrade: websocket
Connection: Upgrade

這等于告訴web服務器,發(fā)起的請求是Websocket協(xié)議的,要用Websocket協(xié)議方式來處理請求。

在請求頭里,還增加了

Sec-WebSocket-Key: BVuKSx8KJKN2VAGM0i6gjw==

看值的話替蛉,就應該能猜到它浅,是通過BASE64編碼而成的值典唇,這是瀏覽器隨機生成的。

HTTP響應頭
HTTP/1.1 101 Switching Protocols
Upgrade: websocket
Connection: Upgrade
Sec-WebSocket-Accept: sr0Tsn4bYggO1mzRZHpiOQO+FYE=

Sec-WebSocket-Accept這個是通過服務器確認寒波,并加密后的Sec-WebSocket-Key级野。下面的這個響應頭代表告訴客戶端,升級成Websocket協(xié)議懒闷,屬于HTTP最后負責地方

Upgrade: websocket
Connection: Upgrade

為什么說是HTTP最后負責的地方?因為WebSocket只是借助了HTTP協(xié)議去握手昔园,僅此而已蔓榄。此后信息通訊時,并不基于HTTP協(xié)議默刚,而是基于更底層的TCP協(xié)議甥郑。WebSocket是一個和HTTP協(xié)議一樣是基于TCP協(xié)議上的應用層協(xié)議。

數(shù)據(jù)收發(fā)

Websocket是可以發(fā)數(shù)據(jù)類型消息荤西,也可以發(fā)控制類型消息澜搅。
數(shù)據(jù)類型消息包含:純文本消息,二進制消息
控制類型消息包含:Ping邪锌,Pong勉躺,Close

更準確的說,WebSocket消息傳輸包含數(shù)據(jù)幀和控制幀觅丰,控制幀包含Ping饵溅,Pong,Close

這3個幀的Opcode各不相同:
  1. Ping幀的Opcode是9舶胀,0x09
  2. Pong幀的Opcode是10概说,0x0A
  3. Close幀的Opcode是8碧注,0x08
數(shù)據(jù)幀包含文本幀和二進制幀
  1. 文本幀的Opcode是1,0x01
  2. 二進制幀的Opcode是2糖赔,0x02

還有一個既非數(shù)據(jù)幀萍丐,也非控制幀,是0x00放典,代表繼續(xù)幀逝变。
通過上面幾個數(shù)字看到,還缺了幾個數(shù)字奋构,這幾個缺了的數(shù)字是協(xié)議保留壳影,以備后用。

保留幀
  1. 0x03——0x07:保留用于未來的非控制幀
  2. 0x0B——0x0F:保留用于未來的控制幀

還有其他的具體解釋在:傳送門

ping幀的數(shù)據(jù)傳輸
ping

可以看到opcode是數(shù)字9

pong幀的數(shù)據(jù)傳輸
pong

可以看到opcode是數(shù)字10

close幀

下圖是服務器主動斷開連接弥臼,opcode為10宴咧,在紅框處,有一個十六進制的數(shù)字径缅,還有一串英文解釋掺栅。
第一個Close表示的是關閉的代碼,第二個Close表示的是關閉的原因纳猪。
關閉的reason也可以自定義氧卧,但reason內(nèi)容的長度別過長(之前試過大概在128個字節(jié)左右,具體的可以再試試)氏堤,否則數(shù)據(jù)傳輸不了導致無法斷開的問題沙绝。
websocket的狀態(tài)碼具體詳解在這:傳送門

92701058-92E0-4E07-AFDA-2F394CD66CF1.png

在js的接口中,沒有主動發(fā)起ping接口的調(diào)用鼠锈,這一般是在服務器那發(fā)起ping請求闪檬,瀏覽器接收到ping幀后,就會回個pong幀脚祟,從而達到心跳效果谬以。

發(fā)送文本數(shù)據(jù)

從web界面向服務器發(fā)送32個‘f’强饮,截取傳輸數(shù)據(jù)如下圖:


C4B0F5CA-49D3-4F27-8193-ABA7A52DB91D.png

Payload length代表數(shù)據(jù)長度由桌。以字節(jié)的形式表示:7位、7+16位邮丰、或者7+64位行您。如果這個值以字節(jié)表示是0-125這個范圍,那這個值就表示傳輸數(shù)據(jù)的長度剪廉;如果這個值是126娃循,則隨后的兩個字節(jié)表示的是一個16進制無符號數(shù),用來表示傳輸數(shù)據(jù)的長度斗蒋;如果這個值是127,則隨后的是8個字節(jié)表示的一個64位無符號數(shù)捌斧,這個數(shù)用來表示傳輸數(shù)據(jù)的長度笛质。多字節(jié)長度的數(shù)量是以網(wǎng)絡字節(jié)的順序表示。負載數(shù)據(jù)的長度為擴展數(shù)據(jù)及應用數(shù)據(jù)之和捞蚂,擴展數(shù)據(jù)的長度可能為0,因而此時負載數(shù)據(jù)的長度就為應用數(shù)據(jù)的長度妇押。Payload length不包括Masking-key在內(nèi)。
Masking-key姓迅,呃敲霍,掩碼鍵。
還有好多其他說明丁存,都去傳送門里看吧肩杈。。

其他

之前在網(wǎng)上無意間看到這圖解寝,覺得挺不錯的扩然,描述建立連接時,websocket和TCP層的握手關系聋伦,很一目了然


handshake

在建立建立之后与学,每次端對端之間發(fā)送數(shù)據(jù),另一端在TCP層都會回發(fā)個ACK表示確認嘉抓。
WebSocket只是個協(xié)議索守,不是只能運行在瀏覽器上,自行用手機/其他客戶端也可以實現(xiàn)抑片,只需遵循協(xié)議即可(目前協(xié)議文檔是RFC6455)卵佛,個人覺得,假如沒有其他更好想法敞斋,用這個協(xié)議來代替很多TCP層的數(shù)據(jù)傳輸格式也是不錯的截汪。

還有一個是IBM公司搞的MQTT協(xié)議,之前了解過其主要用于嵌入式設備植捎,說是比較省電(相對于HTTP協(xié)議來比較那的確是)衙解,使用發(fā)布/訂閱消息模式,提供一對多的消息發(fā)布焰枢,解除應用程序耦合蚓峦。它跟Websocket一樣也是基于TCP協(xié)議的,都有各自的協(xié)議頭格式济锄。

呃暑椰,網(wǎng)上搜的時候,很多人都有對這些方面研究了荐绝,解釋的更好
張善友

最后編輯于
?著作權歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末一汽,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子低滩,更是在濱河造成了極大的恐慌召夹,老刑警劉巖岩喷,帶你破解...
    沈念sama閱讀 217,277評論 6 503
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異监憎,居然都是意外死亡均驶,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,689評論 3 393
  • 文/潘曉璐 我一進店門枫虏,熙熙樓的掌柜王于貴愁眉苦臉地迎上來妇穴,“玉大人,你說我怎么就攤上這事隶债√谒” “怎么了?”我有些...
    開封第一講書人閱讀 163,624評論 0 353
  • 文/不壞的土叔 我叫張陵死讹,是天一觀的道長瞒滴。 經(jīng)常有香客問我,道長赞警,這世上最難降的妖魔是什么妓忍? 我笑而不...
    開封第一講書人閱讀 58,356評論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮愧旦,結(jié)果婚禮上世剖,老公的妹妹穿的比我還像新娘。我一直安慰自己笤虫,他們只是感情好旁瘫,可當我...
    茶點故事閱讀 67,402評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著琼蚯,像睡著了一般酬凳。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上遭庶,一...
    開封第一講書人閱讀 51,292評論 1 301
  • 那天宁仔,我揣著相機與錄音,去河邊找鬼峦睡。 笑死翎苫,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的赐俗。 我是一名探鬼主播拉队,決...
    沈念sama閱讀 40,135評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼阻逮!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起秩彤,我...
    開封第一講書人閱讀 38,992評論 0 275
  • 序言:老撾萬榮一對情侶失蹤叔扼,失蹤者是張志新(化名)和其女友劉穎事哭,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體瓜富,經(jīng)...
    沈念sama閱讀 45,429評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡鳍咱,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,636評論 3 334
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了与柑。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片谤辜。...
    茶點故事閱讀 39,785評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖价捧,靈堂內(nèi)的尸體忽然破棺而出丑念,到底是詐尸還是另有隱情,我是刑警寧澤结蟋,帶...
    沈念sama閱讀 35,492評論 5 345
  • 正文 年R本政府宣布脯倚,位于F島的核電站,受9級特大地震影響嵌屎,放射性物質(zhì)發(fā)生泄漏推正。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,092評論 3 328
  • 文/蒙蒙 一宝惰、第九天 我趴在偏房一處隱蔽的房頂上張望植榕。 院中可真熱鬧,春花似錦尼夺、人聲如沸内贮。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,723評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽夜郁。三九已至,卻和暖如春粘勒,著一層夾襖步出監(jiān)牢的瞬間竞端,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,858評論 1 269
  • 我被黑心中介騙來泰國打工庙睡, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留事富,地道東北人。 一個月前我還...
    沈念sama閱讀 47,891評論 2 370
  • 正文 我出身青樓乘陪,卻偏偏與公主長得像统台,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子啡邑,可洞房花燭夜當晚...
    茶點故事閱讀 44,713評論 2 354

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

  • 前言 本文為初入研究 Websocket協(xié)議,對于真正應用中,各種語言都有實現(xiàn)庫,建議采用庫,而不是自己實現(xiàn),本文...
    MeIsLZHua閱讀 8,582評論 6 39
  • 上篇介紹了HTTP1.1協(xié)議的基本內(nèi)容贱勃,這篇文章將繼續(xù)分析WebSocket協(xié)議,然后對這兩個進行簡單的比較。 W...
    TheAlchemist閱讀 36,522評論 15 113
  • 琪寶 暖風吹過我的窗臺 抬眸贵扰,隱約的綠影浮現(xiàn) 原來仇穗,一樹春意早已悄然襲來 我的熱情捱過寒冬的掩埋 冰雪的覆蓋 褪去...
    琪寶angel閱讀 269評論 1 1
  • 人大概都曾有這樣的感覺,遇到一個人有似曾相識的感覺戚绕,我胡亂猜想纹坐,也許是在街角的某次擦肩而過,我們四目相對舞丛,心中雖沒...
    檣腳摘蘑菇閱讀 489評論 0 0
  • http://www.exp99.com/htmlcss/htmlcss_229.htmlhttp://www.f...
    孫雪冬閱讀 187評論 0 0