第一,设置请求头的Content-Type,以明确请求体类型,并声明数据段的分隔符是什么。
即:Content-Type: multipart/form-data; boundary=abcdefgh
boundary的值就是定义分割符,它就是一个普通的ASCII字符串,可以随意定义,但是一般要满足:a、足够的长度。b、足够的随机性。
这两点是为了保证分割符不会污染数据本身。(分割符和数据实质上来说是混在一起的一段数据)。
第二、数据分段的规则。
--${boundary} 用来分隔每个数据段。
--${boundary}-- 用来表示整个请求体结束。
例如:
--9a8f7e25b7f276955e4f41094c87281db5db920e1
Content-Disposition: form-data; name="fieldname"
PHP is the best language in the world.
--9a8f7e25b7f276955e4f41094c87281db5db920e1
Content-Disposition: form-data; name="file"; filename="image.jpg"
${二进制数据}
--9a8f7e25b7f276955e4f41094c87281db5db920e1--
上面这段请求体数据就是一个典型的form表单文件上传的例子。注意请求体中每行数据的换行符是 "\r\n"
通过上面的分析,其实要自己来包装一个form表单请求也是不难的,下面就用javascript简单地展示一下示例代码:
function wrapbody(){ var boundary = '--9a8f7e25b7f276955e4f41094c87281db5db920e1', end_boundary = boundary + '--', end_line = '\r\n'; var body = ''; body += boundary + end_line; body += 'Content-Disposition: form-data; name="fieldname"' + end_line; body += end_line; body += 'PHP is the best language in the world.' + end_line; body += boundary + end_line; body += 'Content-Disposition: form-data; name="file"; filename="image.jpg"' + end_line; body += end_line; body += fs.readFileSync('/root/demo/image.jpg') + end_line; body += end_boundary; return body; }