Google App Engine - 从Python代码上传文件到Blobstore时出错 [英] Google App Engine - Error uploading file to blobstore from Python code
问题描述
我正在处理一个应用程序来处理打到我的邮箱的电子邮件。我修改了我的邮件设置,将收到的邮件转发到 myapp 。到达 myapp 的邮件将被路由到处理程序脚本( handle_incoming_email.py )。我的 app.yaml 文件看起来像这样
app.yaml
application:myapp
版本:1-1
运行时:python27
api_version:1
线程安全:false
default_expiration:360d
处理程序:
- url:/_ah/mail/.+
脚本:myapp / utils / handle_incoming_email.py
邮件处理程序脚本如下所示
handle_incoming_email.py
导入日志记录
导入urllib
导入base64
导入traceback $ b $ from google.appengine.ext导入webapp
from google.appengine.ext从google.appengine.api导入blobstore
从google.appengine.ext.webapp.util导入urlfetch
从google.appengine.ext.webapp.mail_handlers导入run_wsgi_app
import InboundMailHandler
$ b class ReceiveEmail(InboundMailHandler):
def receive(self,message):
try:
用于filename,filecontents在message.attachments:
if filecontents.encoding:
#data = filecontents
data = filecontents.decode()
#data = filecontents.payload
#data = filecontents .payload.decode()
#data = base64.b64decode(filecontents.decode())
#data = base64.b64decode(filecontents.payload)
#data = base64.b64decode(filecontents .payload.decode())
$ b $ upload_url = blobstore.create_upload_url('http://myapp.appspot.com/settings/saveItem/')
form_fields = {'field_name':data }
form_data = urllib.urlencode(form_fields)
result = urlfetch.fetch(url = upload_url,$ b $ payload = form_data,
method = urlfetch.POST,
hea除了异常,e:
traceback.print_exc()之外,
的logging.info(结果)
应用程序/ x-www-form-urlencoded'
application = webapp.WSGIApplication([ReceiveEmail.mapping()],debug = True)
$ b def main():
run_wsgi_app(application )
if __name__ ==__main__:
main()
我的要求是创建一个与每个邮件附件相对应的实体。为此,我需要解析邮件中的附件并将其上传到Blobstore。但是,当我尝试将附件上传到blobstore时,出现以下错误:
请求的内容类型在此URL上不被接受。
正如您在handle_incoming_email.py中的注释代码中所看到的,我尝试了不同的方法(试错法)以获取正确的数据,但是没有用。
有人可以指导我解决这个问题!
谢谢!!!
我认为这段代码示例会解决您的问题。您可能只需要使用此代码中的encode_multipart_formdata函数。不要忘了设置正确的内容类型。
class BlobstoreUpload(blobstore_handlers.BlobstoreUploadHandler):
def post(self ):
upload_files = self.get_uploads('file')
blob_info = upload_files [0]
返回self.response.write(blob_info.key())
@classmethod
def encode_multipart_formdata(cls,fields,files,mimetype ='image / png'):
参数:
fields:
files:数据序列(名称,文件名,值)元素作为文件上传到
返回:
准备好urlfetch的(content_type,body)序列
boundary ='paLp12Buasdasd40tcxAp97curasdaSt40bqweastfarcUNIQUE_STRING'
crlf ='\r\''
line = [ ]
for(key,value)in field:
line.append(' - '+ boundary)
line.append('Content-Dis位置:form-data; name =%s'%key)
line.append('')
line.append(value)
for(key,filename,value)in文件:
line.append(' - '+ boundary)
line.append('Content-Disposition:form-data; NAME = %S;文件名=%s'%(键,文件名))
line.append('Content-Type:%s'%mimetype)
line.append('')
line。 append(value)
line.append(' - %s--'%boundary)
line.append('')
body = crlf.join(line)
content_type ='multipart / form-data; border =%s'%boundary
return content_type,body
$ b class UserProfile(webapp2.RequestHandler):
def post(self):
picture = self.request.POST.get('picture')
#将新图片写入blob
content_type,body = BlobstoreUpload.encode_multipart_formdata(
[],[('file ',name,image)])
response = urlfetch.fetch(
url = blobstore.create_upload_url(self.uri_for('blobstore-upload')),
payload = body,
method = urlfetch.POST,
headers = {'Content-Type':content_type},
截止日期= 30
)
blob_key = response.content
I am working on an app to process emails hitting my mailbox. I have modified my mail settings to forward incoming mails to myapp. The mails reaching myapp will be routed to the handler script ("handle_incoming_email.py") where it will be processed. My app.yaml file looks like this
app.yaml
application: myapp
version: 1-1
runtime: python27
api_version: 1
threadsafe: false
default_expiration: "360d"
handlers:
- url: /_ah/mail/.+
script: myapp/utils/handle_incoming_email.py
The mail handler script is given below
handle_incoming_email.py
import logging
import urllib
import base64
import traceback
from google.appengine.ext import webapp
from google.appengine.ext import blobstore
from google.appengine.api import urlfetch
from google.appengine.ext.webapp.util import run_wsgi_app
from google.appengine.ext.webapp.mail_handlers import InboundMailHandler
class ReceiveEmail(InboundMailHandler):
def receive(self, message):
try:
for filename, filecontents in message.attachments:
if filecontents.encoding:
# data = filecontents
data = filecontents.decode()
# data = filecontents.payload
# data = filecontents.payload.decode()
# data = base64.b64decode(filecontents.decode())
# data = base64.b64decode(filecontents.payload)
# data = base64.b64decode(filecontents.payload.decode())
upload_url = blobstore.create_upload_url('http://myapp.appspot.com/settings/saveItem/')
form_fields = {'field_name': data}
form_data = urllib.urlencode(form_fields)
result = urlfetch.fetch(url=upload_url,
payload=form_data,
method=urlfetch.POST,
headers={'Content-Type': 'application/x-www-form-urlencoded'})
logging.info(result)
except Exception, e:
traceback.print_exc()
application = webapp.WSGIApplication([ReceiveEmail.mapping()], debug=True)
def main():
run_wsgi_app(application)
if __name__ == "__main__":
main()
My requirement is to create an entity corresponding to each mail with attachment. For this, I need to parse the attachment from the mail and upload it to blobstore. However, when I try to upload the attachment to blobstore, I get the following error:
The request's content type is not accepted on this URL.
As you can see in the commented code in "handle_incoming_email.py", I tried different methods (trial-and-error) to get the data correct, but to no avail.
Could someone guide me in fixing this!
Thanks!!!
I think this code sample will solve you problem. You probably need to use only encode_multipart_formdata function from this code. And do not forget to set properly content type.
class BlobstoreUpload(blobstore_handlers.BlobstoreUploadHandler):
def post(self):
upload_files = self.get_uploads('file')
blob_info = upload_files[0]
return self.response.write(blob_info.key())
@classmethod
def encode_multipart_formdata(cls, fields, files, mimetype='image/png'):
"""
Args:
fields: A sequence of (name, value) elements for regular form fields.
files: A sequence of (name, filename, value) elements for data to be
uploaded as files.
Returns:
A sequence of (content_type, body) ready for urlfetch.
"""
boundary = 'paLp12Buasdasd40tcxAp97curasdaSt40bqweastfarcUNIQUE_STRING'
crlf = '\r\n'
line = []
for (key, value) in fields:
line.append('--' + boundary)
line.append('Content-Disposition: form-data; name="%s"' % key)
line.append('')
line.append(value)
for (key, filename, value) in files:
line.append('--' + boundary)
line.append('Content-Disposition: form-data; name="%s"; filename="%s"' % (key, filename))
line.append('Content-Type: %s' % mimetype)
line.append('')
line.append(value)
line.append('--%s--' % boundary)
line.append('')
body = crlf.join(line)
content_type = 'multipart/form-data; boundary=%s' % boundary
return content_type, body
class UserProfile(webapp2.RequestHandler):
def post(self):
picture = self.request.POST.get('picture')
# Write new picture to blob
content_type, body = BlobstoreUpload.encode_multipart_formdata(
[], [('file', name, image)])
response = urlfetch.fetch(
url=blobstore.create_upload_url(self.uri_for('blobstore-upload')),
payload=body,
method=urlfetch.POST,
headers={'Content-Type': content_type},
deadline=30
)
blob_key = response.content
这篇关于Google App Engine - 从Python代码上传文件到Blobstore时出错的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!