This article mainly introduces how to send form-data requests and splice form-data content in Python. This article uses requests to send multipartform-data requests, for more information about how to use python to send multipart/form-data
The post simulation method of ulrlib2 is as follows:
import urllib2boundary='-------------------------7df3069603d6' data=[] data.append('--%s' % boundary) data.append('Content-Disposition: form-data; name="app_id"\r\n') data.append('xxxxxx') data.append('--%s' % boundary) data.append('Content-Disposition: form-data; name="version"\r\n') data.append('xxxxx') data.append('--%s' % boundary) data.append('Content-Disposition: form-data; name="platform"\r\n') data.append('xxxxx') data.append('--%s' % boundary) data.append('Content-Disposition: form-data; name="libzip"; filename="C:\Users\danwang3\Desktop\libmsc.zip"') data.append('Content-Type: application/octet-stream\r\n') fr=open('C:\Users\danwang3\Desktop\libmsc.zip') content=fr.read() data.append(content) print content fr.close() data.append('--%s--\r\n'%boundary) httpBody='\r\n'.join(data) print type(httpBody) print httpBody postDataUrl='http://xxxxxxxx' req=urllib2.Request(postDataUrl,data=httpBody)
After testing, when sending a binary file using the above method, the server reports an error and the data is faulty!
The problem lies in the encoding of '\ r \ n'. join (data). data contains binary data. This encoding may be used to convert data to UTF-8 format. Of course, there is a problem.
I searched a lot of materials and found that data in the multipart/form-data format can be submitted using the requests library.
A multipart/form-data form is captured in http as follows:
#Content-Disposition: form-data;name="app_id" 123456#-----------------------------7df23df2a0870#Content-Disposition: form-data;name="version" 2256 -----------------------------7df23df2a0870 Content-Disposition:form-data; name="platform" ios -----------------------------7df23df2a0870 Content-Disposition: form-data;name="libzip";filename="C:\Users\danwang3\Desktop\libmsc.zip" Content-Type: application/x-zip-compressed
<二进制文件数据未显示>
---------------------------7df23df2a0870—
The above data can be simulated in requests as follows:
files={'app_id':(None,'123456'), 'version':(None,'2256'), 'platform':(None,'ios'), 'libzip':('libmsc.zip',open('C:\Users\danwang3\Desktop\libmsc.zip','rb'),'application/x-zip-compressed') }
Sending the post request is simple.
response=requests.post(url,files=files)
That's simple.
On the official website, requests simulates a form data in the following format:
Files = {'name ':( , , , )}
The post data simulated by this row is:
Content-Disposition: form-data; name='name';filename=
Content-Type:
--boundary
If filename and content-Type are not written, there will be no data in the response to post simulation.
Generally, requests does not automatically manage cookies as urllib2 does.
You can send the cookie together in the requests request.
The cookie format used by requests is as follows:
newCookie={}newCookie['key1']='value1'newCookie['key2]='value2'newCookie['key3']='value3'
Cookie sending can be used:
response=requests.post(url,cookies=newCookie)
In this way, you can
Concatenate form-data post content
#! \ Urs \ bin \ env python # encoding: UTF-8 # Set the encoding method from http2 import http import urllib def ReadFileAsContent (filename): # print filename try: with open (filename, 'rb') as f: filecontent = f. read () failed t Exception, e: print 'the Error Message in ReadFileAsContent (): '+ e. message return ''return filecontent def get_content_type (filename): import mimetypes return mimetypes. guess_type (filename) [0] or 'application/octet-stream' def isfiledata (p_str): import re r_c = re. compile ("^ f '(. *) '$ ") rert = r_c.search (str (p_str) # rert = re. search ("^ f '(. *) '$ ", p_str) if rert: return rert. group (1) else: return None def encode_multipart_formdata (fields ): ''''' this function is used to concatenate the body Content of a multipart/form-data http request and return the spliced body Content and the Content-Type header definition ''' import random import OS BOUNDARY = '---------- % s' % ''. join (random. sample ('0123456789abcdef ', 15) CRLF =' \ r \ n' L = [] for (key, value) in fields: filepath = isfiledata (value) if filepath: l. append ('--' + BOUNDARY) L. append ('content-Disposition: form-data; name = "% s"; filename = "% s" '% (key, OS. path. basename (filepath) L. append ('content-Type: % s' % get_content_type (filepath) L. append ('') L. append (ReadFileAsContent (filepath) else: L. append ('--' + BOUNDARY) L. append ('content-Disposition: form-data; name = "% s" '% key) L. append ('') L. append (value) L. append ('--' + BOUNDARY + '--') L. append ('') body = CRLF. join (L) content_type = 'multipart/form-data; boundary = % s' % BOUNDARY return content_type, body
Note that the dictionary value of the file data is in the format of f'/path/to/file'. The Calling method is as follows:
form_data = [('gShopID','489'),("addItems", r"f'D:\case3guomei.xml'"), ('validateString', '92c99a2a36f47c6aa2f0019caa0591d2')] form_data_re = encode_multipart_formdata(form_data) print form_data_re
The returned Content is a tuples. The first parameter is the Content-Type value in the request header, and the second parameter is the Content of the specific post. Then, use the post method of httplib to send the message.