POST請求的消息主體放在entity body中,服務端根據(jù)請求頭中的Content-Type字段來獲取消息主體的編碼方式,進而進行解析數(shù)據(jù)。
一、application/x-www-form-urlencoded
最常見的 POST 提交數(shù)據(jù)的方式,原生Form表單,如果不設置 enctype 屬性,默認為application/x-www-form-urlencoded 方式提交數(shù)據(jù)。
首先,Content-Type被指定為 application/x-www-form-urlencoded;其次,提交的表單數(shù)據(jù)會轉(zhuǎn)換為鍵值對并按照 key1=val1&key2=val2 的方式進行編碼,key 和 val 都進行了 URL 轉(zhuǎn)碼。大部分服務端語言都對這種方式有很好的支持。
另外,如利用AJAX 提交數(shù)據(jù)時,也可使用這種方式。例如 jQuery,Content-Type 默認值都是”application/x-www-form-urlencoded;charset=utf-8”。
二、multipart/form-data
另一個常見的 POST 數(shù)據(jù)提交的方式, Form 表單的 enctype 設置為multipart/form-data,它會將表單的數(shù)據(jù)處理為一條消息,以標簽為單元,用分隔符(這就是boundary的作用)分開,類似我們上面Content-Type中的例子。
由于這種方式將數(shù)據(jù)有很多部分,它既可以上傳鍵值對,也可以上傳文件,甚至多個文件。當上傳的字段是文件時,會有Content-Type來說明文件類型;Content-disposition,用來說明字段的一些信息。每部分都是以 –boundary 開始,緊接著是內(nèi)容描述信息,然后是回車,最后是字段具體內(nèi)容(字段、文本或二進制等)。如果傳輸?shù)氖俏募?,還要包含文件名和文件類型信息。消息主體最后以 –boundary– 標示結(jié)束。
三、application/json
Content-Type: application/json 作為響應頭比較常見。實際上,現(xiàn)在越來越多的人把它作為請求頭,用來告訴服務端消息主體是序列化后的 JSON 字符串,其中一個好處就是JSON 格式支持比鍵值對復雜得多的結(jié)構(gòu)化數(shù)據(jù)。由于 JSON 規(guī)范的流行,除了低版本 IE 之外的各大瀏覽器都原生支持JSON.stringify,服務端語言也都有處理 JSON 的函數(shù),使用起來沒有困難。
Google 的 AngularJS 中的 Ajax 功能,默認就是提交 JSON 字符串。
四、text/xml
XML的作用不言而喻,用于傳輸和存儲數(shù)據(jù),它非常適合萬維網(wǎng)傳輸,提供統(tǒng)一的方法來描述和交換獨立于應用程序或供應商的結(jié)構(gòu)化數(shù)據(jù),在JSON出現(xiàn)之前是業(yè)界一大標準(當然現(xiàn)在也是),相比JSON的優(yōu)缺點大家有興趣可以上網(wǎng)search。因此,在POST提交數(shù)據(jù)時,xml類型也是不可缺少的一種,雖然一般場景上使用JSON可能更輕巧、靈活。
五、binary (application/octet-stream)
在Chrome瀏覽器的Postman工具中,還可以看到”binary“這一類型,指的就是一些二進制文件類型。如application/pdf,指定了特定二進制文件的MIME類型。就像對于text文件類型若沒有特定的子類型(subtype),就使用 text/plain。類似的,二進制文件沒有特定或已知的 subtype,即使用 application/octet-stream,這是應用程序文件的默認值,一般很少直接使用 。
對于application/octet-stream,只能提交二進制,而且只能提交一個二進制,如果提交文件的話,只能提交一個文件,后臺接收參數(shù)只能有一個,而且只能是流(或者字節(jié)數(shù)組)。
很多web服務器使用默認的 application/octet-stream 來發(fā)送未知類型。出于一些安全原因,對于這些資源瀏覽器不允許設置一些自定義默認操作,導致用戶必須存儲到本地以使用。一般來說,設置正確的MIME類型很重要。