使用MultipartPostHandler使用Python POST表单数据 [英] Using MultipartPostHandler to POST form-data with Python

查看:375
本文介绍了使用MultipartPostHandler使用Python POST表单数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

问题:当使用Python的urllib2发布数据时,所有数据都被URL编码,并作为Content-Type发送:application / x-www-form-urlencoded。上传文件时,应将Content-Type设置为multipart / form-data,并将内容进行MIME编码。这个问题的讨论在这里:
http://code.activestate.com/recipes/ 146306 /



为了解决这个限制,一些尖锐的编码器创建了一个名为MultipartPostHandler的库,它创建一个可以与urllib2一起使用的OpenerDirector,主要是自动使用multipart /形式的数据。这个图书馆的副本在这里:
http:/ /peerit.blogspot.com/2007/07/multipartposthandler-doesnt-work-for.html



我是Python的新手,无法得到这个图书馆工作。我基本上写了以下代码。当我在本地HTTP代理中捕获它时,我可以看到数据仍然是URL编码的,而不是多部分的MIME编码。请帮我弄清楚我做错了什么或更好的方法来做到这一点。谢谢: - )

  FROM_ADDR ='my@email.com'

try:
data = open(file,'rb')。read()
除了:
print错误:无法打开文件%s阅读%file
print文件或文件夹它位于
sys.exit(1)

#构建POST请求
url =http://somedomain.com/?action=analyze
post_data = {}
post_data ['analysisType'] ='file'
post_data ['executable'] = data
post_data ['notification'] ='email'
post_data ['email'] = FROM_ADDR

#MIME编码POST有效负载
opener = urllib2.build_opener(MultipartPostHandler.MultipartPostHandler)
urllib2.install_opener(opener)
request = urllib2.Request(url,post_data)
request.set_proxy('127.0.0.1:8080','http')#用于使用Burp Proxy进行测试

#提出请求并捕获响应
try:
response = urllib2.urlopen(request)
print response.geturl()
除了urllib2.URLError,e:
打印文件上传失败...

EDIT1:感谢您的回复。我知道ActiveState的httplib解决方案(我链接到上面)。我宁愿抽出这个问题,并使用最少的代码继续使用urllib2我是如何。任何想法为什么开启者没有被安装和使用?

解决方案

似乎是最简单和最兼容的方式来解决这个问题是使用'海报'模块。

 #test_client.py 
from poster.encode import multipart_encode
来自poster.streaminghttp import register_openers
import urllib2

#注册流式的http处理程序与urllib2
register_openers()

#启动多部分/文件数据编码DSC0001.jpg
#image1是参数的名称,通常通过HTML< input>的name参数设置
#标签。

#标头包含必要的内容类型和内容长度
#datagen是一个生成器对象,生成编码参数
datagen,headers = multipart_encode({image1:打开(DSC0001.jpg)})

#创建Request对象
request = urllib2.Request(http:// localhost:5000 / upload_image,datagen,headers)
#实际请求,并得到响应
print urllib2.urlopen(request).read()

这个工作很完美,我没有必要用httplib弄脏。该模块可在此处使用:
http://atlee.ca/software/poster/index .html


Problem: When POSTing data with Python's urllib2, all data is URL encoded and sent as Content-Type: application/x-www-form-urlencoded. When uploading files, the Content-Type should instead be set to multipart/form-data and the contents be MIME encoded. A discussion of this problem is here: http://code.activestate.com/recipes/146306/

To get around this limitation some sharp coders created a library called MultipartPostHandler which creates an OpenerDirector you can use with urllib2 to mostly automatically POST with multipart/form-data. A copy of this library is here: http://peerit.blogspot.com/2007/07/multipartposthandler-doesnt-work-for.html

I am new to Python and am unable to get this library to work. I wrote out essentially the following code. When I capture it in a local HTTP proxy, I can see that the data is still URL encoded and not multi-part MIME encoded. Please help me figure out what I am doing wrong or a better way to get this done. Thanks :-)

FROM_ADDR = 'my@email.com'

try:
    data = open(file, 'rb').read()
except:
    print "Error: could not open file %s for reading" % file
    print "Check permissions on the file or folder it resides in"
    sys.exit(1)

# Build the POST request
url = "http://somedomain.com/?action=analyze"       
post_data = {}
post_data['analysisType'] = 'file'
post_data['executable'] = data
post_data['notification'] = 'email'
post_data['email'] = FROM_ADDR

# MIME encode the POST payload
opener = urllib2.build_opener(MultipartPostHandler.MultipartPostHandler)
urllib2.install_opener(opener)
request = urllib2.Request(url, post_data)
request.set_proxy('127.0.0.1:8080', 'http') # For testing with Burp Proxy

# Make the request and capture the response
try:
    response = urllib2.urlopen(request)
    print response.geturl()
except urllib2.URLError, e:
    print "File upload failed..."

EDIT1: Thanks for your response. I'm aware of the ActiveState httplib solution to this (I linked to it above). I'd rather abstract away the problem and use a minimal amount of code to continue using urllib2 how I have been. Any idea why the opener isn't being installed and used?

解决方案

It seems that the easiest and most compatible way to get around this problem is to use the 'poster' module.

# test_client.py
from poster.encode import multipart_encode
from poster.streaminghttp import register_openers
import urllib2

# Register the streaming http handlers with urllib2
register_openers()

# Start the multipart/form-data encoding of the file "DSC0001.jpg"
# "image1" is the name of the parameter, which is normally set
# via the "name" parameter of the HTML <input> tag.

# headers contains the necessary Content-Type and Content-Length
# datagen is a generator object that yields the encoded parameters
datagen, headers = multipart_encode({"image1": open("DSC0001.jpg")})

# Create the Request object
request = urllib2.Request("http://localhost:5000/upload_image", datagen, headers)
# Actually do the request, and get the response
print urllib2.urlopen(request).read()

This worked perfect and I didn't have to muck with httplib. The module is available here: http://atlee.ca/software/poster/index.html

这篇关于使用MultipartPostHandler使用Python POST表单数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆