好程序員web前端教程JavaScript系列之HTTP:http 是我們前後臺交互的時候的傳輸協議(即超文本傳輸協議)
HTTP 的工作流程
.和服務器建立鏈接
.建立鏈接後,發送一個請求給服務器(請求)
.服務器接受到請求以後進行相應的處理並給出一個迴應(響應)
.斷開於服務器的鏈接
和服務器建立鏈接
怎麼和服務器建立鏈接呢?
需要保證客戶端的接受和發送正常,服務器端的接受和發送正常
這裏就涉及到一個東西叫做 TCP/IP 協議
建立鏈接的主要步驟叫做 三次握手
1、客戶端發送一個消息給到服務端
此時: 服務端知道了 客戶端可以正常發送消息 服務端知道了 服務端可以正常接受消息
2、服務端回給客戶端一個消息
此時:
服務端知道了 客戶端可以正常發送消息
服務端知道了 服務端可以正常接受消息
客戶端知道了 客戶端可以正常發送消息
客戶端知道了 客戶端可以正常接受消息
客戶端知道了 服務端可以正常接受消息
客戶端知道了 服務端可以正常發送消息
3、客戶端再回給服務端一個消息
此時:
服務端知道了 客戶端可以正常發送消息
服務端知道了 服務端可以正常接受消息
客戶端知道了 客戶端可以正常發送消息
客戶端知道了 客戶端可以正常接受消息
客戶端知道了 服務端可以正常接受消息
客戶端知道了 服務端可以正常發送消息
服務端知道了 服務端可以正常發送消息
服務端知道了 客戶端可以正常接受消息
至此,依照 TCP/IP 協議的建立鏈接就建立好了
雙方都知道雙方可以正常收發消息
就可以進入到第二步,通訊了
發送一個請求
建立完鏈接以後就是發送請求的過程
我們的每一個請求都要把我們的所有信息都包含請求
每一個請求都會有一個 請求報文
在 請求報文 中會包含我們所有的請求信息(也就是我們要和服務端說的話都在裏面)
我們的請求報文中會包含幾個東西
1、請求行
POST /user HTTP/1.1
POST 請求方式
/user 請求URL(不包含域名)
HTTP/1.1 請求協議版本
2、請求頭(請求頭都是鍵值對的形式出現的)
user-agent: Mozilla/5.0 # 產生請求的瀏覽器信息accept: application/json # 表示客戶端希望接受的數據類型Content-Type: application/x-www-form-urlencoded # 客戶端發送的實體數據格式Host: 127.0.0.1 # 請求的主機名(IP)
3、請求空行(請求頭和請求主體之間要留一個空白行)
就是一個空行
4、請求體(本次請求攜帶的數據)
GET 請求是沒有請求體數據的
POST 請求才有請求體數據
接下來看一個完整的請求報文
POST /user HTTP/1.1 # 請求行
Host: www.user.com
Content-Type: application/x-www-form-urlencoded
accept: application/json
User-agent: Mozilla/5.0. # 以上是首部
(此處必須有一空行) # 空行分割header和請求內容
name=world # 請求體
接受一個響應
客戶端的請求發送到服務端以後
服務端進行對應的處理
會給我們返回一個響應
每一個響應都會有一個 響應報文
在 響應報文 中會包含我們所有的響應信息(也就是服務端在接受到客戶端請求以後,給我們的回信)
我們的 響應報文 中會包含幾個信息
1、狀態行
HTTP/1.1 200 OK
HTTP/1.1 服務器使用的 HTTP 協議版本
200 響應狀態碼
OK 對響應狀態碼的簡單解釋
2、響應頭
Date: Jan, 14 Aug 2019 12:42:30 GMT # 服務器時間
Server: Apache/2.4.23 (Win32) OpenSSL/1.0.2j PHP/5.4.45 # 服務器類型
Content-Type: text/html # 服務端給客戶端的數據類型
Content-Length: 11 # 服務端給客戶端的數據長度
3、響應體
hello world
服務端給客戶端的響應數據
斷開於服務端的鏈接
之前我們的建立鏈接是基於 TCP/IP 協議的 三次握手
我們的斷開鏈接是基於 TCP/IP 協議的 四次揮手
.客戶端發送一個我要斷開的消息給服務端
.服務端接受到以後發送一個消息告訴客戶端我已經進入關閉等待狀態
.服務端再次發送一個消息告訴客戶端,這個是我的最後一次消息給你,當我再接受到消息的時候就會關閉
.客戶端接受到服務端的消息以後,告訴服務器,我已經關閉,這個是給你的最後一個消息
完成一個 HTTP 請求
至此,一個 HTTP 請求就完整的完成了
一個 HTTP 請求必須要包含的四個步驟就是
.建立鏈接
.發送請求
.接受響應
.斷開鏈接
在一個 HTTP 請求中,請求的部分有請求報文,接受響應的部分有響應報文
請求報文包含
.請求行
.請求頭
.請求空行
.請求體
響應報文
.狀態行
.響應頭
.響應體
常見的 HTTP 響應狀態碼
在一個 HTTP 請求的響應報文中的狀態行會有一個響應狀態碼
這個狀態碼是用來描述本次響應的狀態的
通常會出現五種狀態碼
.100 ~ 199
.200 ~ 299
.300 ~ 399
.400 ~ 499
.500 ~ 599
100 ~ 199
一般我們看不到,因爲表示請求繼續
100: 繼續請求,前面的一部分內容服務端已經接受到了,正在等待後續內容
101: 請求者已經準備切換協議,服務器頁表示同意
200 ~ 299
2 開頭的都是表示成功,本次請求成功了,只不過不一樣的狀態碼有不一樣的含義(語義化)
200: 標準請求成功(一般表示服務端提供的是網頁)
201: 創建成功(一般是註冊的時候,表示新用戶信息已經添加到數據庫)
203: 表示服務器已經成功處理了請求,但是返回的信息可能來自另一源
204: 服務端已經成功處理了請求,但是沒有任何數據返回
300 ~ 399
3 開頭也是成功的一種,但是一般表示重定向
301: 永久重定向
302: 臨時重定向
304: 使用的是緩存的數據
305: 使用代理
400 ~ 499
4 開頭表示客戶端出現錯誤了
400: 請求的語法服務端不認識
401: 未授權(你要登錄的網站需要授權登錄)
403: 服務器拒絕了你的請求
404: 服務器找不到你請求的 URL
407: 你的代理沒有授權
408: 請求超時
410: 你請求的數據已經被服務端永久刪除
500 ~ 599
5 開頭的表示服務端出現了錯誤
500: 服務器內部錯誤
503: 服務器當前不可用(過載或者維護)
505: 請求的協議服務器不支持
常見的 HTTP 請求方式
每一個 HTTP 請求在請求行裏面會有一個東西叫做請求方式
不同的請求方式代表的含義不同
.GET: 一般用於獲取一些信息使用(獲取列表)
.POST: 一般用於發送一些數據給服務端(登錄)
.PUT: 一般用於發送一些數據給服務當讓其添加新數據(註冊)
.DELETE: 一般用域刪除某些數據
.HEAD: 類似於 GET 的請求,只不過一般沒有響應的具體內容,用於獲取報文頭
.CONNECT: HTTP/1.1 中預留的方式,一般用於管道鏈接改變爲代理的時候使用
.PATCH: 是和 PUT 方式類似的一個方式,一般用於更新局部數據
.OPTIONS: 允許客戶端查看服務端性能
我們比較常用的就是 GET 和 POST
GET 請求
參數以 querystring 的形式發送,也就是直接拼接在 請求路徑的後面
GET 請求會被瀏覽器主動緩存
GET 請求根據不同的瀏覽器對長度是有限制的
IE: 2083 個字符
FireFox: 65536 個字符
Safari: 80000 個字符
Opera: 190000 個字符
Chrome: 8182 個字符
APACHE(server): 理論上接受的最大長度是 8192 個字符(有待商榷)
對參數的類型有限制,只接受 ASCII 碼的格式
GET 請求是明文發送,相對不安全
POST 請求
參數以 request body的形式發送,也就是放在請求體中
POST 請求不會被瀏覽器主動緩存,除非手動設置
POST 請求理論上是沒有限制的,除非服務端做了限制
對參數類型沒有限制,理論上可以傳遞任意數據類型,只不過要和請求頭對應
POST 請求是密文發送,相對安全