你知道 HTTP 的狀態(tài)碼都有哪些嗎?它們的含義又是什么呢?
當(dāng)服務(wù)端返回 HTTP 響應(yīng)時(shí),會(huì)帶有一個(gè)狀態(tài)碼,用于表示特定的請(qǐng)求結(jié)果。比如 HTTP/1.1 200 OK,里面的 HTTP/1.1 表示協(xié)議版本,200 則是狀態(tài)碼,OK 則是對(duì)狀態(tài)碼的描述。

由協(xié)議版本、狀態(tài)碼、描述信息組成的行被稱為起始行,服務(wù)端返回的響應(yīng)報(bào)文中的第一行便是它,然后是響應(yīng)頭和響應(yīng)體。
而本篇文章,我們來詳細(xì)聊一聊狀態(tài)碼,看看它都有哪些,以及含義是什么?
首先狀態(tài)碼由三位數(shù)字組成,按照第一個(gè)數(shù)字的不同,可分為五個(gè)類別,每個(gè)類別的含義如下。
- 1xx(信息響應(yīng)):這類狀態(tài)碼表示臨時(shí)響應(yīng),意思是告訴客戶端,服務(wù)端已收到部分請(qǐng)求,請(qǐng)你繼續(xù)發(fā)送剩余的部分;
- 2xx(成功):這類狀態(tài)碼表示客戶端的請(qǐng)求已被成功處理;
- 3xx(重定向):這類狀態(tài)碼表示為了完成請(qǐng)求,需要進(jìn)一步的操作,比如跳轉(zhuǎn)到新位置;
- 4xx(客戶端錯(cuò)誤):這類狀態(tài)碼表示請(qǐng)求不合法,比如操作一個(gè)沒有權(quán)限的資源或者不存在的資源等等;
- 5xx(服務(wù)端錯(cuò)誤):這類狀態(tài)碼表示服務(wù)端內(nèi)部在處理請(qǐng)求時(shí)出現(xiàn)錯(cuò)誤,比如服務(wù)端的代碼報(bào)錯(cuò);
下面我們來分別介紹這五類狀態(tài)碼都有哪些,以及狀態(tài)碼對(duì)應(yīng)的描述是什么。
1xx 狀態(tài)碼
1xx 系列的 HTTP 狀態(tài)碼屬于信息響應(yīng)類別,這類狀態(tài)碼用于指示客戶端請(qǐng)求的初始部分已被接收,并且客戶端應(yīng)繼續(xù)其請(qǐng)求過程。
那么該系列的狀態(tài)碼都有哪些呢?
100 Continue
如果客戶端發(fā)送的請(qǐng)求體很大,比如上傳大文件,那么在發(fā)送整個(gè)請(qǐng)求體之前,可以先發(fā)送請(qǐng)求的頭部(包含一個(gè) Expect: 100-continue 字段)。相當(dāng)于告訴服務(wù)端,大的要來了,如果同意發(fā)送請(qǐng)求體,那么就返回一個(gè) 100 Contiune 響應(yīng)。
而服務(wù)端在接收到帶有 Expect: 100-continue 的請(qǐng)求頭部時(shí),可以先進(jìn)行一些預(yù)檢查,比如驗(yàn)證請(qǐng)求頭部的有效性、檢查是否有足夠的資源處理請(qǐng)求、或者檢查客戶端是否有權(quán)限。如果這些初步檢查通過,服務(wù)端則返回 100 Continue 響應(yīng),指示客戶端繼續(xù)發(fā)送請(qǐng)求體。
因此 100 Contiune 主要用于提高大型請(qǐng)求的處理效率,尤其是在帶寬受限或服務(wù)端處理能力有限的情況下。然而并非所有的 HTTP 客戶端和服務(wù)端都支持這個(gè)機(jī)制,在不支持的情況下,客戶端將直接發(fā)送整個(gè)請(qǐng)求體,不會(huì)等待 100 Continue 響應(yīng)。
1xx 系列的狀態(tài)碼從 HTTP/1.1 才開始支持,HTTP/1.0 不支持。
101 Switch Protocols
這個(gè)應(yīng)該都很熟悉,它一般用于協(xié)議升級(jí),比如將 HTTP 協(xié)議升級(jí)成 WebSocket。
首先不管使用什么協(xié)議,都有一個(gè)握手的過程,它是建立網(wǎng)絡(luò)連接時(shí)雙方進(jìn)行的一系列交互,旨在確保雙方能夠成功地通信。不同的協(xié)議有不同的握手機(jī)制,但它們通常都包括以下基本步驟:
- 協(xié)議識(shí)別:在握手過程的開始,通信雙方確定要使用的協(xié)議以及版本;
- 參數(shù)協(xié)商:根據(jù)所選協(xié)議,雙方可能需要協(xié)商一些參數(shù),如傳輸速率、加密方式、數(shù)據(jù)格式等;
- 身份驗(yàn)證:在某些協(xié)議中,如 SSL/TLS(用于 HTTPS),握手過程還包括身份驗(yàn)證,這是為了確保通信雙方的身份是合法和可信的;
- 連接確認(rèn):一旦上述步驟完成,雙方將相互確認(rèn)連接已建立,此時(shí)數(shù)據(jù)傳輸便可以開始;
但有一些協(xié)議在實(shí)現(xiàn)握手時(shí),搭了 HTTP 協(xié)議的便車,比如 WebSocket,它的握手過程其實(shí)就是一個(gè) HTTP GET 請(qǐng)求。利用 HTTP 本身的協(xié)議升級(jí)特性,偽裝成 HTTP,這樣就能繞過瀏覽器沙箱、網(wǎng)絡(luò)防火墻等限制。
因此建立 WebSocket 連接時(shí)會(huì)發(fā)送一個(gè) GET 請(qǐng)求,并帶上兩個(gè)專用的頭字段,表示這不是普通的 HTTP GET,而是要進(jìn)行協(xié)議升級(jí)。
- Connection: Upgrade,表示要求協(xié)議升級(jí);
- Upgrade: websocket,表示要升級(jí)成 WebSocket 協(xié)議;
另外,為了防止普通的 HTTP 消息被意外識(shí)別成 WebSocket,握手消息還額外增加了兩個(gè)用于認(rèn)證的頭字段。
- Sec-WebSocket-Key:一個(gè) Base64 編碼的 16 字節(jié)隨機(jī)數(shù),作為簡(jiǎn)單的認(rèn)證密鑰;
- Sec-WebSocket-Version:協(xié)議的版本號(hào),當(dāng)前必須是 13
服務(wù)端收到 HTTP 請(qǐng)求報(bào)文,看到上面的四個(gè)字段,就知道這不是一個(gè)普通的 GET 請(qǐng)求了,而是 WebSocket 的升級(jí)請(qǐng)求,表示客戶端想要建立 WebSocket 連接。
如果服務(wù)端同意建立 WebSocket 連接,那么會(huì)給客戶端返回 101 Switching Protocols 響應(yīng)報(bào)文,客戶端收到之后,就知道服務(wù)端同意了。
102 Processing
該狀態(tài)碼用于 WebDAV 協(xié)議,WebDAV 請(qǐng)求可能包含很多涉及文件操作的子請(qǐng)求,需要很長(zhǎng)一段時(shí)間才能完成。因此服務(wù)端可以直接返回 102 Processing,表示請(qǐng)求已被接收并正在處理中,但目前無響應(yīng)可用。這樣可以防止客戶端因長(zhǎng)時(shí)間得不到響應(yīng),而假設(shè)請(qǐng)求丟失。
關(guān)于 1xx 系列的狀態(tài)碼就是以上幾種,它們被稱為信息性狀態(tài)碼,用于表示請(qǐng)求的中間狀態(tài),因此在日常的 Web 瀏覽中并不常見。但 1xx 狀態(tài)碼在復(fù)雜的 HTTP 通信中扮演重要角色,特別是在優(yōu)化性能和處理大型請(qǐng)求、復(fù)雜請(qǐng)求時(shí)。
2xx 狀態(tài)碼
2xx 系列的狀態(tài)碼應(yīng)該最受開發(fā)者喜歡了,因?yàn)樗硎菊?qǐng)求被成功處理。
200 OK
這是最常見的成功狀態(tài)碼,它表示請(qǐng)求已成功處理,并且響應(yīng)體中包含了請(qǐng)求的結(jié)果。
201 Created
同樣表示請(qǐng)求已被成功處理,并且還創(chuàng)建了一個(gè)新資源。
當(dāng)客戶端通過 POST 請(qǐng)求向服務(wù)端發(fā)送數(shù)據(jù)以創(chuàng)建新資源(如新的數(shù)據(jù)庫記錄、文件等)時(shí),如果請(qǐng)求成功并且新資源被創(chuàng)建,服務(wù)端會(huì)響應(yīng) 201 Created。
與 200 OK 相比,201 Created 響應(yīng)不僅表明請(qǐng)求成功,而且還指出了一個(gè)新的資源已經(jīng)產(chǎn)生。響應(yīng)中一般會(huì)包含一個(gè) Location 字段,指明新創(chuàng)建資源的 URI,這對(duì)客戶端來說非常有用,因?yàn)樗梢灾苯邮褂眠@個(gè) URI 來訪問新創(chuàng)建的資源。
當(dāng)然啦,由于習(xí)慣,很多時(shí)候我們還是會(huì)返回 200,并將新創(chuàng)建資源的信息放在響應(yīng)體中。具體使用哪種看個(gè)人習(xí)慣,總之 200 和 201 沒太大區(qū)別,只是 201 意味著要明確地告訴客戶端,新的資源已經(jīng)創(chuàng)建了。
202 Accepted
表示服務(wù)端已收到請(qǐng)求,但尚未處理完成,這種設(shè)計(jì)可以覆蓋很多的場(chǎng)景,例如異步、需要長(zhǎng)時(shí)間處理的任務(wù)等。至于最后請(qǐng)求是成功還是失敗,則是未知的。
203 Non-Authoritative Information
該狀態(tài)碼表示客戶端使用了代理服務(wù)器,代理服務(wù)器將客戶端請(qǐng)求轉(zhuǎn)發(fā)給服務(wù)端之后,被成功處理了。但代理服務(wù)器在將響應(yīng)轉(zhuǎn)發(fā)給客戶端時(shí),對(duì)原始響應(yīng)內(nèi)容進(jìn)行了修改。
因此代理服務(wù)器也要將狀態(tài)碼(例如 200)修改為 203,來告知客戶端這一情況,方便客戶端做出相應(yīng)的處理。注:203 響應(yīng)可以被緩存。
204 No Content
該狀態(tài)碼表示請(qǐng)求已被成功處理,但服務(wù)端沒有返回任何內(nèi)容,指示客戶端不需要更新當(dāng)前的頁面視圖。
205 Reset Content
該狀態(tài)碼表示請(qǐng)求已被成功處理,服務(wù)端同樣沒有返回任何內(nèi)容,但指示客戶端需要更新當(dāng)前的頁面視圖,例如清空表單內(nèi)容或重置控件。
206 Partial Content
該狀態(tài)碼表示服務(wù)端已經(jīng)成功處理了客戶端發(fā)送的部分請(qǐng)求,主要用于以下場(chǎng)景。
分塊請(qǐng)求:當(dāng)客戶端只請(qǐng)求資源的一部分,比如客戶端使用 Range 請(qǐng)求頭指定要下載文件的特定部分時(shí),服務(wù)端會(huì)使用 206 Partial Content 響應(yīng)。
斷點(diǎn)續(xù)傳:在文件下載過程中,如果下載被中斷(例如因?yàn)榫W(wǎng)絡(luò)問題),那么恢復(fù)正常時(shí),客戶端可以只請(qǐng)求未下載的部分。服務(wù)端對(duì)這種請(qǐng)求的響應(yīng)就是 206 Partial Content,允許客戶端繼續(xù)從中斷的地方下載,而不是重新開始。
流媒體:在流媒體應(yīng)用中,客戶端可能只請(qǐng)求媒體文件的一小部分,以便快速加載和播放,服務(wù)端對(duì)這種請(qǐng)求的響應(yīng)也使用 206 Partial Content。
響應(yīng)頭信息:在返回 206 Partial Content 時(shí),服務(wù)端會(huì)包含有關(guān)響應(yīng)內(nèi)容的信息,如 Content-Range 頭部,這個(gè)頭部指明了返回的部分內(nèi)容在整個(gè)資源中的范圍。
減少數(shù)據(jù)傳輸:使用 206 Partial Content 可以減少網(wǎng)絡(luò)帶寬的使用,因?yàn)樗试S客戶端僅請(qǐng)求和下載所需的數(shù)據(jù)部分。
206 Partial Content 狀態(tài)碼是一個(gè)高效處理大型資源請(qǐng)求的重要機(jī)制,特別是在網(wǎng)絡(luò)條件不穩(wěn)定或資源非常大的情況下,它可以顯著提高數(shù)據(jù)傳輸?shù)男屎涂煽啃浴?/p>
207 Multi-Status
該狀態(tài)碼用于 WebDAV 協(xié)議,當(dāng)一個(gè)客戶端請(qǐng)求對(duì)多個(gè)資源產(chǎn)生作用時(shí),服務(wù)端會(huì)以 XML 的形式返回多個(gè)資源的狀態(tài),此時(shí)狀態(tài)碼為 207。
所以 207 Multi-Status 狀態(tài)碼在處理操作多個(gè)資源的請(qǐng)求時(shí)非常有用,特別是在 WebDAV 等分布式文件系統(tǒng)中,它提供了一種高效且靈活的方式來同時(shí)報(bào)告多個(gè)資源的狀態(tài)。
208 Already Reported
該狀態(tài)碼通常和 207 一起使用,在 WebDAV 中,一個(gè)操作可能涉及多個(gè)資源,而這些資源可能又包含在不同的集合中。通過使用 208 Already Reported,服務(wù)端能夠高效地表示哪些資源已經(jīng)被處理,從而避免在多狀態(tài)響應(yīng)中重復(fù)報(bào)告。
3xx 狀態(tài)碼
3xx 系列的狀態(tài)碼屬于重定向類別,用于告知客戶端資源的獲取方式已經(jīng)改變,需要采取額外動(dòng)作以完成請(qǐng)求。
比如訪問一個(gè)已經(jīng)廢棄的鏈接,服務(wù)端就會(huì)返回 3xx 狀態(tài)碼,并在響應(yīng)頭的 Location 字段中指定新鏈接??蛻舳税l(fā)現(xiàn)狀態(tài)碼為 3xx 之后,就會(huì)自動(dòng)重定向到 Location 中指定的新鏈接。
另外在 RFC2068 中,規(guī)定客戶端重定向次數(shù)不應(yīng)超過 5 次,以防止死循環(huán)。
300 Mutiple Choices
當(dāng)請(qǐng)求的資源有多種表示時(shí),服務(wù)端會(huì)返回 300,并提供一個(gè)資源列表,讓客戶端自行選擇。由于缺乏明確的細(xì)節(jié),因此該狀態(tài)碼不常用。
301 Moved Permanently
表示請(qǐng)求的資源已經(jīng)被永久移動(dòng)到了一個(gè)新的位置,該狀態(tài)碼的使用場(chǎng)景如下。
永久性重定向:當(dāng)服務(wù)端返回 301 Moved Permanently 響應(yīng)時(shí),它表明請(qǐng)求的資源已經(jīng)永久地移動(dòng)到了由 Location 字段指定的 URL,未來所有對(duì)該資源的請(qǐng)求都應(yīng)該使用這個(gè)新的URL。
更新書簽和鏈接:301 狀態(tài)碼告訴客戶端(如瀏覽器或搜索引擎)更新其鏈接或書簽。對(duì)于搜索引擎優(yōu)化(SEO)來說,這意味著應(yīng)將原先頁面的權(quán)重轉(zhuǎn)移給新的 URL。
搜索引擎優(yōu)化:在SEO的背景下,使用 301 Moved Permanently 是管理網(wǎng)站結(jié)構(gòu)變化的最佳實(shí)踐。它有助于維持舊 URL 的搜索排名和信譽(yù),并將其傳遞給新 URL。
重定向方法:與臨時(shí)重定向(如 302 Found 或 307 Temporary Redirect)不同,301 是永久性的。這告訴客戶端在未來的所有請(qǐng)求中都應(yīng)使用新的 URL,而不是臨時(shí)性地查找資源。
302 Found
表示請(qǐng)求的資源臨時(shí)位于不同的 URL,該狀態(tài)碼的使用場(chǎng)景如下。
臨時(shí)性重定向:當(dāng)服務(wù)端返回 302 Found 響應(yīng)時(shí),它表明請(qǐng)求的資源現(xiàn)在暫時(shí)位于由 Location 頭部指定的不同 URI 中。與 301 Moved Permanently 不同,302 Found 表示這種重定向只是暫時(shí)的。
原始 URL 保持有效:服務(wù)端期望客戶端在未來的請(qǐng)求中繼續(xù)使用原始的 URL,這意味著臨時(shí)重定向后,原始 URL 仍然被視為有效。
搜索引擎處理:對(duì)于搜索引擎優(yōu)化(SEO)來說,由于 302 Found 指示的是臨時(shí)重定向,搜索引擎通常保持對(duì)原始 URL 的索引,而不是轉(zhuǎn)移到新的地址。
其它用途:302 Found 也可以用于在網(wǎng)站維護(hù)期間或在進(jìn)行 A/B 測(cè)試時(shí),重定向到不同的 URL,同時(shí)保持原 URL 的有效性。
303 See Other
該狀態(tài)碼表示請(qǐng)求資源的響應(yīng)需要通過另一個(gè) URI 獲取,并且要通過 GET 方法訪問該 URI。
當(dāng)服務(wù)端處理完 POST 請(qǐng)求(如表單提交)后,它可以發(fā)送 303 See Other 狀態(tài)碼,告訴客戶端通過 GET 方法從指定的 URI 獲取資源或信息,這樣做可以防止刷新頁面時(shí)重新提交表單。
所以 303 See Other 狀態(tài)碼在處理特定類型的 Web 請(qǐng)求(尤其是表單提交)并進(jìn)行安全重定向時(shí)非常有用,它通過強(qiáng)制將后續(xù)請(qǐng)求的方法改為 GET,防止了表單重復(fù)提交這類問題。
304 Not Modified
該狀態(tài)碼表示從上次請(qǐng)求后,請(qǐng)求的資源未發(fā)生更改,因此客戶端可以繼續(xù)使用其緩存的版本。
關(guān)于資源緩存,這里解釋一下。當(dāng)服務(wù)端返回的響應(yīng)中包含以下字段,代表資源可以被緩存。
Cache-Control:這是最重要的緩存頭部之一,它可以設(shè)置多種指令來控制資源的緩存行為。如 max-age 指定資源可以緩存多久,no-cache 和 no-store 指示不緩存資源等。
- Cache-Control: max-age=3600,緩存 3600 秒;
- Cache-Control: no-cache,不緩存資源;
- Cache-Control: no-store,不緩存資源;
關(guān)于 no-cache 和 no-store,雖然都表示不緩存資源,但它們之間還是有一些區(qū)別的。
- no-cache 指示響應(yīng)不應(yīng)該被緩存,而是在每次請(qǐng)求時(shí)都要向服務(wù)端驗(yàn)證其有效性。它并不意味著資源不能被緩存,而是在使用緩存的副本之前,客戶端(如瀏覽器)必須向服務(wù)端進(jìn)行確認(rèn),檢查資源是否更新。這種方法通常用于保證獲取到的信息是最新的,同時(shí)仍然允許利用緩存來減少一些不必要的數(shù)據(jù)傳輸。
- no-store 是一種更加嚴(yán)格的指令,它告訴瀏覽器和中間緩存(如代理服務(wù)器),不應(yīng)該存儲(chǔ)任何關(guān)于客戶端請(qǐng)求和服務(wù)端響應(yīng)的信息。該指令通常用于敏感數(shù)據(jù),如銀行頁面或個(gè)人資料頁面,確保這些數(shù)據(jù)在傳輸后不會(huì)留在緩存中,從而提供更高的隱私保護(hù)。
Expires:該頭部提供一個(gè)日期,該日期之后資源被認(rèn)為過期。如果提供了 Cache-Control,那么 Expires 頭部通常會(huì)被忽略。
Last-Modified:指示資源最后被修改的時(shí)間,客戶端可以在后續(xù)的請(qǐng)求中使用 If-Modified-Since 頭部來檢查自該日期以來資源是否被修改。
ETag:提供資源的特定版本的標(biāo)識(shí),客戶端可以在后續(xù)請(qǐng)求中使用 If-None-Match 頭部,帶上這個(gè)標(biāo)簽來檢查資源是否有更新。
當(dāng)客戶端擁有某資源的緩存副本,并通過發(fā)送一個(gè)條件性請(qǐng)求(通常包含 If-Modified-Since 或 If-None-Match)來檢查資源是否更新時(shí),如果資源未更新,服務(wù)端就會(huì)返回 304 Not Modified。這意味著客戶端無需下載該資源,可以使用其緩存的副本,否則將返回 200 OK 和新的資源。
因此和其它 HTTP 響應(yīng)不同,304 Not Modified 響應(yīng)通常不包含響應(yīng)體,這是因?yàn)閷?shí)際的內(nèi)容沒有更改,不需要重新傳輸。
304 有助于減少不必要的網(wǎng)絡(luò)帶寬使用,因?yàn)樗苊饬酥匦孪螺d未更改的資源。所以 304 常用于網(wǎng)頁和 Web 應(yīng)用中,以優(yōu)化性能,例如瀏覽器可能緩存網(wǎng)站的靜態(tài)資源,并在后續(xù)訪問時(shí)使用 If-Modified-Since 頭部來檢查這些資源是否已更新。
總的來說,304 Not Modified 狀態(tài)碼在管理 Web 資源緩存方面發(fā)揮著重要作用,減少了不必要的網(wǎng)絡(luò)流量和加載時(shí)間,從而提高了網(wǎng)站或 Web 應(yīng)用的性能,特別是對(duì)于那些需要頻繁檢索大量靜態(tài)資源的網(wǎng)站。
307 Temporary Redirect
注:305 和 306 已經(jīng)被廢棄了,這里簡(jiǎn)單了解一下即可。
- 305 Use Proxy:該狀態(tài)碼表示請(qǐng)求的資源必須通過代理訪問,代理的地址由 Location 字段給出。
- 306 Switch Proxy:該狀態(tài)碼表示后續(xù)請(qǐng)求應(yīng)使用不同的代理來訪問資源。
305 和 306 在現(xiàn)如今的網(wǎng)絡(luò)請(qǐng)求中不會(huì)遇到,因此簡(jiǎn)單帶過,我們直接看 307。
首先 307 和 302 的作用相同,都表示臨時(shí)性重定向,即要訪問的資源臨時(shí)移動(dòng)到了另一個(gè) URI 上,但在 HTTP 方法的處理方面,兩者有所差異。
307 Temporary Redirect 要求客戶端在后續(xù)的重定向請(qǐng)求中使用與原始請(qǐng)求相同的 HTTP 方法。例如原始請(qǐng)求是一個(gè) POST 請(qǐng)求,那么在重定向后,客戶端也必須使用 POST 方法發(fā)送到新的 URI。
而 302 Found 最初設(shè)計(jì)時(shí)也要求客戶端保持相同的請(qǐng)求方法,但在實(shí)際使用中,許多客戶端(如瀏覽器)會(huì)將后續(xù)的重定向請(qǐng)求改為 GET 方法,即使原始請(qǐng)求是 POST 或其它方法。雖然這種行為與 HTTP/1.1 規(guī)范不符,但已經(jīng)成為事實(shí)上的標(biāo)準(zhǔn)。
所以 302、303、307 都表示臨時(shí)性重定向:
- 302 Found 的原始設(shè)計(jì)意圖是重定向時(shí)使用的方法不變,但許多客戶端(如瀏覽器)會(huì)默認(rèn)使用 GET,當(dāng)然也有客戶端沒有這么做。因此這就增加了模糊性,于是便有了 303 和 307;
- 303 See Other 明確指出客戶端在重定向時(shí)應(yīng)該使用 GET 方法,無論原始請(qǐng)求使用的是哪種方法。因此 303 可以確保在處理完 POST 請(qǐng)求(如表單提交)后引導(dǎo)瀏覽器加載一個(gè)新頁面,并且刷新或后退操作不會(huì)再次提交表單;
- 307 Temporary Redirect 則明確指出重定向時(shí),使用的請(qǐng)求方法要保持不變;
308 Permanent Redirect
308 和 301 是類似的,都表示永久性重定向,但 301 可能會(huì)導(dǎo)致請(qǐng)求方法從 POST 轉(zhuǎn)變?yōu)?GET,而 308 則明確要求請(qǐng)求方法保持不變。
以上就是 3xx 系列的狀態(tài)碼,它們使得資源的遷移、緩存、優(yōu)化更加靈活和有效,是網(wǎng)絡(luò)基礎(chǔ)設(shè)施中不可或缺的一部分,幫助網(wǎng)站和應(yīng)用程序管理資源的更改和更新。
4xx 狀態(tài)碼
4xx 系列的 HTTP 狀態(tài)碼表示客戶端錯(cuò)誤,這些狀態(tài)碼指出請(qǐng)求中有錯(cuò)誤,導(dǎo)致服務(wù)端無法或不會(huì)處理該請(qǐng)求。
400 Bad Request
該狀態(tài)碼表示由于客戶端錯(cuò)誤,服務(wù)端無法處理請(qǐng)求,主要在以下情況發(fā)生。
- 無效的請(qǐng)求語法:請(qǐng)求的格式不正確,例如 HTTP 頭部格式錯(cuò)誤或不完整。
- 錯(cuò)誤的請(qǐng)求數(shù)據(jù):請(qǐng)求數(shù)據(jù)有誤,例如無效的 JSON 數(shù)據(jù),錯(cuò)誤的參數(shù);
- 大小問題:請(qǐng)求體過大,超過了服務(wù)端愿意處理的大小;
- 編碼問題:請(qǐng)求的編碼不被服務(wù)端支持;
- 無效的請(qǐng)求消息:請(qǐng)求中包含無效的消息,如錯(cuò)誤的請(qǐng)求行或頭部;
400 Bad Request 是一個(gè)通用的錯(cuò)誤響應(yīng),表明服務(wù)端因客戶端的錯(cuò)誤而無法處理請(qǐng)求。這要求開發(fā)者對(duì)請(qǐng)求進(jìn)行仔細(xì)檢查和調(diào)整,所以正確的請(qǐng)求格式、有效的數(shù)據(jù)和合適的編碼是避免這種錯(cuò)誤的關(guān)鍵。
401 Unauthorized
該狀態(tài)碼表示請(qǐng)求未被服務(wù)端處理,因?yàn)樗鄙儆行У纳矸菡J(rèn)證,主要在以下情況觸發(fā):
- 未提供認(rèn)證信息:當(dāng)請(qǐng)求需要身份驗(yàn)證,但客戶端沒有提供任何認(rèn)證信息時(shí)。
- 認(rèn)證失?。杭词固峁┝苏J(rèn)證信息,如用戶名和密碼,但這些信息不正確或無法驗(yàn)證。
需要注意的是,Unauthorized 這個(gè)單詞的意思是未授權(quán),而不是未認(rèn)證,所以用它來描述 401 就不太準(zhǔn)確。關(guān)于認(rèn)證和授權(quán),這兩個(gè)概念容易讓人混淆,我們解釋一下。
認(rèn)證(Authentication)就是驗(yàn)證當(dāng)前用戶的身份是否合法的過程,比如指紋打卡,當(dāng)你的指紋和系統(tǒng)里錄入的指紋相匹配時(shí),就打卡成功。像用戶名密碼登錄、郵箱發(fā)送登錄鏈接、手機(jī)接收驗(yàn)證碼等等都屬于互聯(lián)網(wǎng)中的常見認(rèn)證方式,只要你能收到驗(yàn)證碼,就默認(rèn)你是賬號(hào)的主人。認(rèn)證主要是為了保護(hù)系統(tǒng)的隱私數(shù)據(jù)與資源。
授權(quán)(Authorization)則是誰(who)對(duì)什么(what)進(jìn)行了什么操作(how),和認(rèn)證不同,認(rèn)證是確認(rèn)用戶的合法性,以及讓服務(wù)端知道你是誰,而授權(quán)則是為了更細(xì)粒度地對(duì)資源進(jìn)行權(quán)限上的劃分。所以授權(quán)是在認(rèn)證通過后,控制不同的用戶訪問不同的資源。
并且授權(quán)是雙向的,可以是用戶給服務(wù)端授權(quán),也可以是服務(wù)端給用戶授權(quán)。
- 用戶給服務(wù)端授權(quán):比如你在安裝手機(jī)應(yīng)用的時(shí)候,APP 會(huì)詢問是否允許授予權(quán)限(訪問相冊(cè)、地理位置等權(quán)限);你在登錄微信小程序時(shí),小程序會(huì)詢問是否允許授予權(quán)限(獲取昵稱、頭像、地區(qū)、性別等個(gè)人信息)。
- 服務(wù)端給用戶授權(quán):比如你想追一個(gè)很火的劇,但被告知必須是 VIP 才能觀看,于是你充錢成為了 VIP,那么服務(wù)端便會(huì)給你授予觀看該?。ㄔL問該資源)的權(quán)限。
因此 401 狀態(tài)碼表示的是客戶端未認(rèn)證,但 Unauthorized 的中文翻譯是未授權(quán)。
403 Forbidden
該狀態(tài)碼表示服務(wù)端理解客戶端的請(qǐng)求,但因客戶端沒有訪問請(qǐng)求資源的權(quán)限,所以服務(wù)端拒絕執(zhí)行該請(qǐng)求,即使請(qǐng)求是有效的。
和 401 不同,返回 401 是因?yàn)檎?qǐng)求缺少有效的身份憑證,導(dǎo)致服務(wù)端不知道客戶端的身份。而 403 意味著服務(wù)端知道客戶端是誰,只是它沒有足夠的權(quán)限來觸發(fā)請(qǐng)求的執(zhí)行,因此拒絕訪問。
所以回顧一下認(rèn)證和授權(quán):
- 未認(rèn)證是 Unauthenticated;
- 未授權(quán)是 Unauthorized;
我們發(fā)現(xiàn) 401 Unauthorized 改成 401 Unauthenticated 會(huì)更合理一些,而 403 Forbbiden 對(duì)應(yīng)的才是 Unauthorized,因?yàn)闆]有訪問資源的權(quán)限不就是未授權(quán)嗎,即客戶端未被授予訪問指定資源的權(quán)限。
認(rèn)證和授權(quán)的中文很好區(qū)分,但英文就容易混淆了,因?yàn)殚L(zhǎng)得比較像。
補(bǔ)充:為了安全起見,服務(wù)端可能會(huì)故意使用 404 Not Found 而非 403 Forbidden 來隱藏資源的存在,避免暴露敏感信息。
404 Not Found
這個(gè)應(yīng)該是最知名的狀態(tài)碼了,它表示服務(wù)器找不到請(qǐng)求的資源。當(dāng)客戶端請(qǐng)求的資源在服務(wù)器上不存在或者未被發(fā)現(xiàn),就會(huì)返回 404。
出現(xiàn) 404,主要是以下幾個(gè)原因:
- 用戶輸入了錯(cuò)誤的 URL;
- 本來存在的資源被刪除、移動(dòng)或重命名,但卻沒有重定向;
- 服務(wù)器或網(wǎng)站的配置問題,導(dǎo)致無法訪問特定資源;
在 Web 開發(fā)中,我們通常也會(huì)自定義 404,比如你要找的頁面去火星了······,等等之類的。
雖然 404 通常被視為錯(cuò)誤,但合適的處理和用戶友好的錯(cuò)誤頁面可以在很大程度上改善用戶的瀏覽體驗(yàn)。對(duì)于網(wǎng)站管理員和開發(fā)者而言,妥善管理和最小化 404 錯(cuò)誤是提高網(wǎng)站質(zhì)量和用戶滿意度的重要部分。
405 Method Not Allowed
該狀態(tài)碼表示客戶端以錯(cuò)誤的 HTTP 方法去訪問請(qǐng)求的資源,比如一個(gè)資源只接受 GET 和 POST 請(qǐng)求,但客戶端嘗試使用 PUT 或 DELETE。
而當(dāng)返回 405 Method Not Allowed 時(shí),服務(wù)端通常會(huì)在響應(yīng)頭中包含一個(gè) Allow 字段,列出對(duì)該資源有效的請(qǐng)求方法。例如,Allow: GET, POST。
406 Not Acceptable
該狀態(tài)碼表示服務(wù)端無法提供與客戶端在請(qǐng)求的 Accept 頭字段中指定的內(nèi)容特征相匹配的響應(yīng),換句話說,服務(wù)端無法生成客戶端期望的響應(yīng)格式。
比如客戶端在 Accept 頭部中指定了一種服務(wù)端不支持的媒體類型(如 application/xml)。
另外當(dāng)客戶端請(qǐng)求的語言(通過 Accept-Language 指定)或編碼(通過 Accept-Encoding 指定)服務(wù)端無法提供時(shí),也可能返回此狀態(tài)碼。
對(duì)于開發(fā)者來說,這個(gè)狀態(tài)碼強(qiáng)調(diào)了內(nèi)容協(xié)商機(jī)制的重要性,即服務(wù)端需要根據(jù)客戶端的要求提供不同格式的響應(yīng)。對(duì)于終端用戶來說,遇到 406 錯(cuò)誤通常意味著他們的客戶端(例如 Web 瀏覽器或應(yīng)用)發(fā)送了服務(wù)端無法滿足的請(qǐng)求。在某些情況下,用戶可以嘗試更改請(qǐng)求的格式。
407 Proxy Authentication Required
與 401 類似,但它表示請(qǐng)求需要通過代理發(fā)送,而客戶端沒有通過代理服務(wù)器的認(rèn)證。
以上是 4xx 系列比較常見的狀態(tài)碼,還有一些不常見的,我們簡(jiǎn)單羅列一下。
- 408 Request Timeout:表示客戶端未在服務(wù)端預(yù)備等待的時(shí)間內(nèi)完成請(qǐng)求的發(fā)送;
- 409 Conflict:表示請(qǐng)求與服務(wù)端當(dāng)前狀態(tài)沖突,常見于并發(fā)編輯同一資源導(dǎo)致的問題;
- 410 Gone:表示請(qǐng)求的資源已被永久刪除,類似于 404,但它是永久性的,明確告知客戶端該位置永遠(yuǎn)找不到指定的資源;
- 411 Length Required:服務(wù)端要求請(qǐng)求必須包含 Content-Length 頭部;
- 412 Precondition Failed:服務(wù)端未滿足請(qǐng)求頭中的一個(gè)或多個(gè)前提條件;
- 413 Payload Too Large:請(qǐng)求實(shí)體太大,服務(wù)端拒絕處理請(qǐng)求;
- 414 URI Too Long:請(qǐng)求的 URI 過長(zhǎng),服務(wù)端拒絕處理;
- 415 Unsupported Media Type:客戶端在其請(qǐng)求中指定了服務(wù)端無法或不愿處理的媒體類型,比如上傳一個(gè)服務(wù)端無法處理的文件格式。要注意它和 406 的區(qū)別:
406 指的是服務(wù)端無法生成客戶端接受的響應(yīng)類型;
415 指的是服務(wù)端不支持客戶端上傳的文件類型;
- 416 Range Not Satisfiable:客戶端請(qǐng)求的范圍無法滿足;
- 417 Expectation Failed:服務(wù)器無法滿足 Expect 請(qǐng)求頭中的期望值;
- 429 Too Many Requests:客戶端發(fā)送的請(qǐng)求過多,通常用于限制請(qǐng)求速率;
4xx 系列的狀態(tài)碼提供了服務(wù)端對(duì)于特定錯(cuò)誤情況的反饋,幫助客戶端開發(fā)者診斷問題并采取相應(yīng)措施。
5xx 狀態(tài)碼
5xx 系列的 HTTP 狀態(tài)碼表示服務(wù)器錯(cuò)誤,這些狀態(tài)碼表明客戶端的請(qǐng)求本身可能沒有問題,但由于服務(wù)器遇到問題而無法完成請(qǐng)求。
500 Internal Server Error
這是最常見的服務(wù)器錯(cuò)誤狀態(tài)碼,表明服務(wù)端遇到了一個(gè)意外情況,阻止了其完成請(qǐng)求。比如服務(wù)端代碼報(bào)錯(cuò)了,但又沒有異常捕獲,這個(gè)時(shí)候會(huì)直接拋出 500。
501 Not Implemented
該狀態(tài)碼表示服務(wù)器不支持當(dāng)前請(qǐng)求所需要的功能,當(dāng)服務(wù)器無法識(shí)別請(qǐng)求方法,并且無法支持其對(duì)任何資源的請(qǐng)求時(shí),可能會(huì)返回這個(gè)狀態(tài)碼。
502 Bad Gateway
當(dāng)服務(wù)器作為網(wǎng)關(guān)或代理,從上游服務(wù)器收到無效響應(yīng)時(shí),會(huì)返回此狀態(tài)碼。相信 502 大家也經(jīng)常會(huì)遇到,伴隨而來往往是 NGINX。
NGINX 將請(qǐng)求轉(zhuǎn)發(fā)給后端服務(wù),但后端服務(wù)報(bào)錯(cuò)了,沒有提供正常響應(yīng),這時(shí) NGINX 就會(huì)返回 502 給客戶端。因此當(dāng)你看到 502 時(shí),就應(yīng)該知道 NGINX 代理正常工作,但它背后的服務(wù)出錯(cuò)了。
503 Service Unavailable
該狀態(tài)碼表明服務(wù)器目前無法使用(由于超載或停機(jī)維護(hù)),通常這只是暫時(shí)狀態(tài)。
504 Gateway Timeout
當(dāng)服務(wù)器作為網(wǎng)關(guān)或代理,沒有及時(shí)從上游服務(wù)器收到請(qǐng)求時(shí),會(huì)返回這個(gè)狀態(tài)碼。
505 HTTP Version Not Supported
該狀態(tài)碼表明服務(wù)器不支持請(qǐng)求中使用的 HTTP 協(xié)議版本。
以上就是 5xx 系列常見的狀態(tài)碼,這些狀態(tài)??表示客戶端的請(qǐng)求正常,但問題出現(xiàn)在服務(wù)端。
小結(jié)
以上就是 HTTP 狀態(tài)碼,它是 Web 通信的核心組成部分,為理解客戶端和服務(wù)端之間的交互提供了基礎(chǔ)。這些狀態(tài)碼提供了關(guān)于請(qǐng)求是否成功,以及如果不成功,原因是什么的關(guān)鍵信息。
了解每個(gè)狀態(tài)碼的含義,可以讓我們?cè)?Web 開發(fā)中迅速定位到問題。





























