0
  • 聊天消息
  • 系統(tǒng)消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會員中心
創(chuàng)作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

前端和后端工程師眼中的HTTP

工程師人生 ? 來源:網(wǎng)絡整理 ? 作者:工程師吳畏 ? 2018-09-18 10:15 ? 次閱讀

HTTP,是Web工程師每天打交道最多的一個基本協(xié)議。很多工作流程、性能優(yōu)化都圍繞HTTP協(xié)議來進行,但是我們對HTTP的理解是否全面呢?如果前端工程師和后臺工程師坐在一起玩捉鬼游戲,他們對HTTP的描述可能會截然不同,從這兩個角色的視角看過去,HTTP呈現(xiàn)出截然不同的形態(tài)。

HTTP簡介

超文本傳輸協(xié)議(HyperText Transfer Protocol,HTTP)是互聯(lián)網(wǎng)上應用最為廣泛的一種網(wǎng)絡協(xié)議。設計HTTP的最初目的是提供一種發(fā)布和接收HTML頁面的方法。OSI模型1義了整個世界計算機相互連接的標準,總共分為7層,其中最上層(也就是第7層)就是應用層,HTTP、HTTPS、FTP、TELNET、SSH、SMTP和POP3都屬于應用層。這是軟件工程師最關心的一層。

SI模型越靠近底層,就越接近硬件。在HTTP協(xié)議中,并沒有規(guī)定必須使用它或它支持的層。事實上,HTTP可以在任何互聯(lián)網(wǎng)協(xié)議或其他網(wǎng)絡上實現(xiàn)。HTTP假定其下層協(xié)議提供可靠的傳輸,因此,任何能夠提供這種保證的協(xié)議都可以被其使用,也就是其在TCP/IP協(xié)議族使用TCP作為其傳輸層。

關于HTTP版本

HTTP已經(jīng)演化出了很多版本,它們中的大部分都是向下兼容的??蛻舳嗽谡埱蟮拈_始告訴服務器它采用的協(xié)議版本號,而后者則在響應中采用相同或者更早的協(xié)議版本。

當前應用最廣泛的HTTP版本為HTTP/1.1,它自從1999年發(fā)布以來,距寫作本書時已有16年的時間。比起HTTP/1,它增加了幾個重要特性,比如緩存處理(在下一章介紹)和持續(xù)連接,以及其他一些性能優(yōu)化。

2015年2月,HTTP/2正式發(fā)布。新的HTTP版本有一些重大更新,除了一如既往地向下兼容HTTP/1以外,還有一些優(yōu)化,比如減小網(wǎng)絡傳輸延遲,并簡化服務器向瀏覽器傳輸內容的過程。主流的服務器(Apache、Nginx等)和瀏覽器(Firefox、Chrome、Safari以及iOSAndroid的瀏覽器等)的最新版都已經(jīng)支持HTTP/2,剩下的就需要網(wǎng)站管理員把服務器升級到最新版了。

例子

下面是一個HTTP客戶端與服務器之間會話的例子,運行于www.google.com,端口80。

客戶端首先發(fā)出請求。

第一行指定方法、資源路徑、協(xié)議版本。當然這是一個簡化后的例子,實際請求中還會有當前Google登錄賬戶的cookie、HTTPS頭、瀏覽器接受何種類型的壓縮格式和UA2代碼等。

服務器隨之應答。

在這一串HTTPS頭之后,會緊跟著一個空行,然后是HTML格式的文本組成的Google主頁。

介紹完關于HTTP的基本知識,我們來分別看看前端工程師和后臺工程師分別是怎樣看待這個最熟悉的小伙伴的。

前端視角

前端工程師的職責之一是,讓網(wǎng)站又快又好地展現(xiàn)在用戶的瀏覽器中。

從這個角度來說,對HTTP的理解是這樣的:打開HttpWatch3,然后隨意訪問一個網(wǎng)站。HttpWatch會按照瀏覽器請求的次序,列出打開這個網(wǎng)站的時候發(fā)生的請求細節(jié)。

發(fā)出的請求列表。

每個請求的開始時間。

每個請求從開始到結束花費的時間。

每個請求的類型(比如是文本、CSS、JS,還是圖片或者字體等)。

每個請求的狀態(tài)碼(比如是200、還是from cache、304、404等)。

每個請求產(chǎn)生的流量消耗。

每個請求gzip壓縮前的體積,以及在本地gzip解壓后的體積。

通過查看站點的HTTP請求信息,可以得到很多優(yōu)化信息。每一個前端工程師都知道的基本優(yōu)化方法是:盡量減少同一域下的HTTP請求數(shù),以及盡量減少每一個資源的體積。

盡量減少同一域下的HTTP請求數(shù)

瀏覽器常常限定了對同一域名發(fā)起的并發(fā)連接數(shù)的上限。IE6/7和Firefox2的設計規(guī)則是,同時只能對一個域名發(fā)起兩個并發(fā)連接。新版本的各種瀏覽器普遍把這一上限設定為4至8個。如果瀏覽器需要對某個域進行更多的連接,則需要在用完了當前連接之后,重復使用或者重新建立TCP連接。

QQ空間的CSS貼圖由程序自動生成,保證最佳的圖片質量、最合理的圖片擺放和最小的體積。

由于瀏覽器針對資源的域名限制并發(fā)連接數(shù),而不是針對瀏覽器地址欄中的頁面域名,所以很多靜態(tài)資源可以放在其他域名下(不同的子域名也被認為是不同的域名)。如果您只有一臺服務器,可以把這些不同的域名同時指向一個IP,也就提高了對這臺服務器的并發(fā)連接數(shù)限制(不過要小心服務器壓力過大)。

把靜態(tài)資源放在非主域名下,這種做法除了可以增加瀏覽器并發(fā),還有一個好處是,減少HTTP請求中攜帶的不必要的cookie數(shù)據(jù)。cookie是某些網(wǎng)站為了辨別用戶身份而儲存在用戶瀏覽器中的數(shù)據(jù)。cookie的作用域是整個域名,也就是說如果某個cookie存放在google.com域名下,那么對于google.com域名下的所有HTTP請求頭都會帶上cookie數(shù)據(jù)。如果Google把所有的資源都放在google.com下,那么所有資源的請求都會帶上cookie數(shù)據(jù)。對于靜態(tài)資源來說,這是毫無必要的,因為這對帶寬和鏈接速度都造成了影響。所以我們一般把靜態(tài)資源放在單獨的域名下。

除此之外,前端工程師經(jīng)常做的優(yōu)化是合并同一域名下的資源,比如把多個CSS合并為一個CSS,或者將圖片組合為CSS貼圖。

還有一些優(yōu)化建議是省掉不必要的HTTP請求,比如內嵌小型CSS、內嵌小型JavaScript、設置緩存,以及減少重定向。這些做法雖然各不相同,但是如果了解HTTP請求的過程,就知道這些優(yōu)化方法的最終目的都是最大化利用有限的請求數(shù)。

盡量減少每一個資源的體積

我們不光要限制請求數(shù),還要盡量減少每一個資源的體積。因為資源的體積越大,在傳輸中消耗的流量就越多,等待時間也越久。

在面試應聘者的時候,我會問的一個基礎題目是“常用的圖片格式有哪些,它們的使用場景是什么”。如果能選擇合適的圖片格式,就能夠用更小的體積,達到更好的顯示效果。對圖片格式的敏感,能反映出工程師對帶寬和速度的不懈追求。

此外,對于比較大的文本資源,必須開啟gzip壓縮。因為gzip對于含有重復“單詞”的文本文件,壓縮率非常高,能有效提高傳輸過程。

對于一個CSS資源的請求耗時,我想說明兩個細節(jié)。

這個CSS資源請求的體積是36.4KB(這是gzip壓縮過的體積),解壓縮之后,CSS內容實際上是263KB,可以算出壓縮后體積是原來的13.8%。

整個連接的建立花費了30%的時間,發(fā)出請求到等待收到第一個字節(jié)回復花費了20%的時間,下載CSS資源的內容花費了50%的時間。

如果沒有設置gzip,下載這個CSS文件會需要好幾倍的時間。

后臺視角

前端工程師對HTTP的關注點在于盡量減少同一域下的HTTP請求數(shù),以及盡量減少每一個資源的體積。與之不同,后臺工程師對于HTTP的關注在于讓服務器盡快響應請求,以及減少請求對服務器的開銷。

后臺工程師知道,瀏覽器限定對某個域的并發(fā)連接數(shù),很大程度上是瀏覽器對服務器的一種保護行為。瀏覽器作為一種善意的客戶端,為了保護服務器不被大量的并發(fā)請求弄得崩潰,才限定了對同一個域的最大并發(fā)連接數(shù)。而一些“惡意”的客戶端,比如一些下載軟件,它作為一個HTTP協(xié)議客戶端,不考慮到服務器的壓力,而發(fā)起大量的并發(fā)請求(雖然用戶感覺到下載速度很快),但是由于它違反了規(guī)則,所以經(jīng)常被服務器端“防范”和屏蔽。

那么為什么服務器對并發(fā)請求數(shù)這么敏感?

雖然服務器的多個進程看上去是在同時運行,但是對于單核CPU的架構來說,實際上是計算機系統(tǒng)同一段時間內,以進程的形式,將多個程序加載到存儲器中,并借由時間共享,以在一個處理器上表現(xiàn)出同時運行的感覺。由于在操作系統(tǒng)中,生成進程、銷毀進程、進程間切換都很消耗CPU和內存,因此當負載高時,性能會明顯降低。

提高服務器的請求處理能力

在早期系統(tǒng)中(如Linux 2.4以前),進程是基本運作單位。在支持線程的系統(tǒng)(Linux2.6)中,線程才是基本的運作單位,而進程只是線程的容器。由于線程開銷明顯小于進程,而且部分資源還可以共享,因此效率較高。

Apache是市場份額最大的服務器,超過50%的網(wǎng)站運行在Apache上。Apache 通過模塊化的設計來適應各種環(huán)境,其中一個模塊叫做多處理模塊(MPM),專門用來處理多請求的情況。Apache安裝在不同系統(tǒng)上的時候會調用不同的默認MPM,我們不用關心具體的細節(jié),只需要了解Unix上默認的MPM是prefork。為了優(yōu)化,我們可以改成worker模式。

prefork和worker模式的最大區(qū)別就是,prefork的一個進程維持一個連接,而worker的一個線程維持一個連接。所以prefork更穩(wěn)定但內存消耗也更大,worker沒有那么穩(wěn)定,因為很多連接的線程共享一個進程,當一個線程崩潰的時候,整個進程和所有線程一起死掉。但是worker的內存使用要比prefork低得多,所以很適合用在高HTTP請求的服務器上。

近年來Nginx越來越受到市場的青睞。在高連接并發(fā)的情況下,Nginx是Apache服務器不錯的替代品或者補充:一方面是Nginx更加輕量級,占用更少的資源和內存;另一方面是Nginx 處理請求是異步非阻塞的,而Apache 則是阻塞型的,在高并發(fā)下Nginx 能保持低資源、低消耗和高性能。

由于Apache和Nginx各有所長,所以經(jīng)常的搭配是Nginx處理前端并發(fā),Apache處理后臺請求。

值得一提的是,新秀Node.js也是采用基于事件的異步非阻塞方式處理請求,所以在處理高并發(fā)請求上有天然的優(yōu)勢。

DDoS攻擊

DDoS是Distributed Denial of Service的縮寫,DDoS攻擊翻譯成中文就是“分布式拒絕服務”攻擊。

簡單來說,就是黑客入侵并控制了大量用戶的計算機(俗稱“肉雞”),然后在這些計算機上安裝了DDoS攻擊軟件。我們知道瀏覽器作為一種“善意”的客戶端,限制了HTTP并發(fā)連接數(shù)。但是DDoS就沒有這樣的道德準則,每一個DDoS攻擊客戶端都可以自由設置TCP/IP并發(fā)連接數(shù),并且連接上服務器之后,它不會馬上斷開連接,而是保持這個連接一段時間,直到同時連接的數(shù)量大于最大連接數(shù),才斷開之前的連接。

就這樣,攻擊者通過海量的請求,讓目標服務器癱瘓,無法響應正常的用戶請求,以此達到攻擊的效果。

對于這樣的攻擊,幾乎沒有什么特別好的防護方法。除了增加帶寬和提高服務器能同時接納的客戶數(shù),另一種方法就是讓首頁靜態(tài)化。DDoS攻擊者喜歡攻擊的頁面一般是會對數(shù)據(jù)庫進行寫操作的頁面,這樣的頁面無法靜態(tài)化,服務器更容易宕機。DDoS攻擊者一般不會攻擊靜態(tài)化的頁面或者圖片,因為靜態(tài)資源對服務器壓力小,而且能夠部署在CDN上。

這里介紹的只是最簡單的TCP/IP攻擊,而DDoS是一個概稱,具體來說,有各種攻擊方式,比如CC攻擊、SYN攻擊、NTP攻擊、TCP攻擊和DNS攻擊等。

BigPipe

前端跟后端在HTTP上也能有交集,BigPipe就是一個例子。

現(xiàn)有的HTTP數(shù)據(jù)請求流程是:客戶端建立連接,服務器同意連接,客戶端發(fā)起請求,服務器返回數(shù)據(jù),客戶端接受并處理數(shù)據(jù)。這個處理流程有兩個問題。

現(xiàn)有的阻塞模型,黃色代表服務器生成頁面,白色代表網(wǎng)絡傳輸,紫色代表瀏覽器渲染頁面。

第一,HTTP協(xié)議的底層是TCP/IP,而TCP/IP規(guī)定3次握手才建立一次連接。每一個新增的請求都要重新建立TCP/IP連接,從而消耗服務器的資源,并且浪費連接時間。對于幾種不同的服務器程序(Apache、Nginx和Node.js等),所消耗的內存和CPU資源也不太一樣,但是新的連接無法避免,沒有從本質上解決問題。

第二個問題是,在現(xiàn)有的阻塞模型中,服務器計算生成頁面需要時間。等服務器完全生成好整個頁面,才開始網(wǎng)絡傳輸,網(wǎng)絡傳輸也需要時間。整個頁面都完全傳輸?shù)綖g覽器中之后,在瀏覽器中最后渲染還是需要時間。三者是阻塞式的,每一個環(huán)節(jié)都在等上一個環(huán)節(jié)100%完成才開始。頁面作為一個整體,需要完整地經(jīng)歷3個階段才能出現(xiàn)在瀏覽器中,效率很低。

BigPipe是Facebook公司科學家Changhao Jiang發(fā)明的一種非阻塞式模型,這種模型能完美解決上面的兩個問題。

通俗來解釋,BigPipe首先把HTML頁面分為很多部分,然后在服務器和瀏覽器之間建立一條管道(BigPipe就是“大管道”的意思),HTML的不同部分可以源源不斷地從服務器傳輸?shù)綖g覽器。BigPipe首先輸送的內容是框架性HTML結構,這個框架結構可能會定義每個Pagelet模塊的位置和寬高,但是這些pagelet都是空的,就像只有鋼筋混泥土骨架的毛坯房。

BigPipe頁面的渲染流程。

服務器傳輸完框架性HTML結構之后,對瀏覽器說:“我這個請求還沒結束,我們保持這個連接不要斷開,不過您可以先用我給您的這部分來渲染?!?/p>

所以瀏覽器就開始渲染這個“不完整的HTML”,毛坯房頁面很快出現(xiàn)在用戶眼前,具體的頁面模塊都顯示“正在加載”。

接下來管道里源源不斷地傳輸過來很多模塊,這時候最開始加載在服務器中的JS代碼開始工作,它會負責把每一個模塊依次渲染到頁面上。

在用戶的感知上,頁面非常快地出現(xiàn)在眼前,但是所有的模塊都顯示正在加載中,然后主要的區(qū)域(比如重要的用戶動態(tài))優(yōu)先出現(xiàn),接下來是logo、邊欄和各種掛件等。

為什么BigPipe能夠讓服務器對瀏覽器說“我這個請求還沒結束,我們保持這個連接不要斷開”呢?答案是HTTP1.1的分塊傳輸編碼。

HTTP 1.1引入分塊傳輸編碼,允許服務器為動態(tài)生成的內容維持HTTP持久鏈接。如果一個HTTP消息(請求消息或應答消息)的Transfer-Encoding消息頭的值為chunked,那么消息體由數(shù)量不確定的塊組成——也就是說想發(fā)送多少塊就發(fā)送多少塊——并以最后一個大小為0的塊為結束。

實現(xiàn)這個架構需要深刻理解HTTP 1.1的規(guī)則,而且要有前端的知識。在我看來,這就是一個極佳的全棧工程師改變世界的例子。

截止寫書時,Chrome、Safari和Opera已經(jīng)支持HTTP/2并默認開啟,它允許服務器向瀏覽器“推送”內容。也就是說,返回的條目數(shù)可以比請求的條目數(shù)多,這樣服務器可以在一開始就推送所有它認為瀏覽器“應該需要”的資源,而不需要瀏覽器接受并解析完HTML頁面才開始請求下載CSS、JavaScript等。而且,后面的請求可以復用之前已經(jīng)建立的底層連接。

聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權轉載。文章觀點僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規(guī)問題,請聯(lián)系本站處理。 舉報投訴
  • 工程師
    +關注

    關注

    59

    文章

    1571

    瀏覽量

    68574
  • HTTP
    +關注

    關注

    0

    文章

    510

    瀏覽量

    31358
  • 前端
    +關注

    關注

    1

    文章

    194

    瀏覽量

    17794
收藏 人收藏

    評論

    相關推薦

    正是拼的年紀|65歲電子工程師上班VLOG #65歲退休 #電子工程師 #搞笑 #上班vlog

    電子工程師
    安泰小課堂
    發(fā)布于 :2024年07月25日 11:31:02

    用二創(chuàng),1:1復刻工程師的職場現(xiàn)狀

    工程師
    揚興科技
    發(fā)布于 :2024年07月19日 18:30:07

    嵌入式軟件工程師和硬件工程師的區(qū)別?

    嵌入式軟件工程師和硬件工程師的區(qū)別? 嵌入式軟件工程師 嵌入式軟件工程師是軟件開發(fā)領域中的一種專業(yè)工程師,他們主要負責設計和開發(fā)嵌入式軟件,
    發(fā)表于 05-16 11:00

    大廠電子工程師常見面試題#電子工程師 #硬件工程師 #電路知識 #面試題

    電子工程師電路
    安泰小課堂
    發(fā)布于 :2024年04月30日 17:33:15

    萬用表模擬前端后端的區(qū)別

    萬用表模擬前端后端的區(qū)別主要體現(xiàn)在它們在信號處理過程中的作用和功能上。簡單來說,模擬前端主要負責信號的采集、調理和初步轉換,而后端則側重于對前端
    的頭像 發(fā)表于 03-16 15:37 ?2148次閱讀

    什么是模擬前端和模擬后端 模擬前端與模擬后端的區(qū)別

    模擬前端和模擬后端是電子系統(tǒng)設計中的兩個關鍵部分,它們在信號處理過程中扮演著不同的角色,各自具有獨特的功能和重要性。
    的頭像 發(fā)表于 03-16 15:21 ?2808次閱讀

    模擬前端和數(shù)字后端哪個好 模擬前端和數(shù)字后端的區(qū)別

    模擬前端和數(shù)字后端都是電子系統(tǒng)設計中的重要環(huán)節(jié),它們各自扮演著不可或缺的角色,難以簡單地進行優(yōu)劣比較。
    的頭像 發(fā)表于 03-16 15:09 ?1033次閱讀

    模擬前端后端的區(qū)別

    模擬前端和模擬后端在電子系統(tǒng)設計中各自扮演著重要的角色,它們之間有著明顯的區(qū)別。
    的頭像 發(fā)表于 03-15 15:59 ?1123次閱讀

    企業(yè)老工程師和高校老師有啥區(qū)別

    電子工程師硬件
    電子發(fā)燒友網(wǎng)官方
    發(fā)布于 :2024年02月28日 17:50:00