Post传输数据的几种格式

1,581 阅读3分钟

「这是我参与11月更文挑战的第13天,活动详情查看:2021最后一次更文挑战」。

POST请求是HTTP请求方法中的一个,而由于HTTP/1.1 没有对POST方法的body内容做规定,所以开发者可以选择提交数据的编码方式。用POST提交数据尤其是表单数据的时候,后端通常就指定了接收方式。作为前端可以了解一下日常都在使用这几种数据格式。

  • application/x-www-form-urlencoded

    最常见的post提交数据的格式,原生form表单如果不设置 enctype 属性,那默认就会按照 application/x-www-form-urlencoded 格式上传. 正如其名 form-urlencoded ,他会对字段进行转码,提交的数据按照 key1=1&key2=2 这种形式来提交,跟get方式提交参数是一样的,只不过放在了request body里面。

    优点是,实现简单,兼容性好,多数浏览器工具都默认支持。

    缺点是,没法实现复杂的数据,比如文件二进制流,符号会被编码,比如 [ ] 会被转成%5B跟%5D,空格会被转成 %20 等,PS:这种编码方式被称为百分比编号,是

    URL编码在特定上下文的统一资源定位符

    的编码机制。

    一个小问题:既然符号都被转为 %xx 那%用可以在url里面吗,怎么表示?

  • multipart/form-data

    这种是一般是用来提交文件、非ASCII码数据或者是二进制流数据,提交excel文件为例,打开控制台能看到如下的表单数据, 每一个字段都有一个分界线,用来分割不同字段。对比 application/x-www-form-urlencoded 会多了很多分界线,用来传普通的数据会比较浪费待带宽或者流量。

    ------WebKitFormBoundaryAWNCGovJRnKkqw7P
    Content-Disposition: form-data; name="key1"
    
    0
    ------WebKitFormBoundaryAWNCGovJRnKkqw7P
    Content-Disposition: form-data; name="key2"
    
    SAND
    
    ------WebKitFormBoundarymJFFnMAzq6h7VzIc
    Content-Disposition: form-data; name="file"; filename="xxx.xlsx"
    Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheetkey1: 0key2: SANDfile: (binary)
    

    key1: 0 key2: SAND file: (binary)

小问题2: multipart/form-data 格式可以传数组吗,怎么传? 

  • application/json

    这种格式就是正常的json数据,可以传数组,嵌套对象等,适合传递复杂嵌套的数据,特别适合RESTful风格的接口。各种工具如Chrome开发者工具跟postman等都有很好的支持,会以树形结构展示。提交JS对象需要用JSON.stringify 转化。

其中原生的表单只支持第一种跟第二种提交方式,enctype 属性还支持 text/pain, 不过日常开发比较少用。

答案

  1. 是可以的,%25就表示 %,其他保留字符参见wiki的对照表。

  2. 也是可以的,确定接口能够接受数组(有些后端会要求要求把数组拼成字符串)的情况下,JS里面实现方式如下:

    const formData = new FormData;
    const arr = ['a', 'b', 'c', 'd'];
    arr.forEach(e => formData.append('arr[]', e))
    }
    

参考

百分号编码

POST 请求的三种常见数据提交格式

四种常见的 POST 提交数据方式