正在从 http 上的 python returns 500 将 blob 上传到 BlobStore
Uploading blob to BlobStore from python returns 500 on http
我正在尝试从 python 将 blob 上传到 BlobStore 并且它在 https://...appspot.com and https://...com/ 上工作但是当从 http 执行完全相同的代码时它不起作用并且 BlobStore returns 500 错误。
我尝试过使连接始终安全,即使在不安全的情况下也是如此。
这是我的代码:
@staticmethod
def save_to_blobstore(_request, id, file_contents, file_type, file_name = 'fixmeh.png'):
upload_url = blobstore.create_upload_url('/upload-item/blob-key/{}'.format(id))
if upload_url.startswith('http://') and 'localhost.com' not in _request.get_host():
upload_url = 'https' + upload_url[4:]
# ----- CREATING FORMDATA -----
boundary = 'WebKitFormBoundaryE19zNvXGzXaLvS5C'
body = '\r\n'.join([
'--' + boundary,
'Content-Disposition: form-data; name="file"; filename="{}"'.format(file_name),
'Content-Type: {}'.format(file_type),
'',
file_contents,
'',
'--' + boundary + '--',
'',
])
headers = {
'Content-Type' : 'multipart/form-data; boundary={}'.format(boundary),
'User-Agent' : 'Mozilla/5.0 (X11; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0',
}
logging.critical('blobstore save')
# TODO Why the hell do we receive deadline limit exceeded?
request = urllib2.Request(upload_url)
# ----- FORCING SECURE CONNECTION EXCEPT ON LOCALHOST -----
if 'localhost.com' in _request.get_host():
conn = httplib.HTTPConnection(request.get_host(), timeout = 50)
else:
conn = httplib.HTTPSConnection(request.get_host(), timeout = 50)
conn._follow_redirects = True
logging.info(['upload_url', upload_url ])
logging.info(['get_host', request.get_host() ])
logging.info(['get_selector', request.get_selector() ])
conn.request('POST', request.get_selector(), body, headers)
try:
response = conn.getresponse()
response_body = response.read()
logging.info(response_body)
# TODO we need to have an exception if the response is not 200
except DeadlineExceededError:
logging.exception('Saving blob - DeadlineExceededError')
except:
logging.exception('Saving blob')
当通过 HTTP 执行时,这是来自 BlobStore 的 return,尽管它没有多大帮助。有没有办法在 https://console.developers.google.com/project/.../logs 或其他任何地方记录 blobstore 错误。
<html><head>
<meta http-equiv="content-type" content="text/html;charset=utf-8">
<title>500 Server Error</title></head>
<body text=#000000 bgcolor=#ffffff>
<h1>Error: Server Error</h1>
<h2>The server encountered an error and could not complete your request.
<p>Please retry your last submission.</p>
<p>If the problem persists, please contact the person responsible for the application you're using, or, if you are that person,
<a href="http://code.google.com/appengine/community.html">report</a> your
problem and mention this error message and the query that caused it.</h2>
</body></html>
你能帮我解释一下为什么它可能无法在 http 上工作但在 https 上工作吗? (请注意它适用于 SDK 上的 http - 那里没有 ssl,这只发生在 appspot 上)
我使用此代码进行完整上传 url 使用 webapp2 路由:
upload_url = create_upload_url(webapp2.uri_for('blob_update', _full=True))
处理程序使用名为 webapp2 的路由:'blob_update'
class BlobUpdate(blobstore_handlers.BlobstoreUploadHandler):
""" has named route : blob_update :
webapp2.Route(r'/blob_update', handler='....BlobUpdate', name='blob_update') """
def post(self):
""" blob upload handler returns the new blobkey"""
blob_info = self.get_uploads('file')[0]
....
非常感谢您的指导和快速回复。我从您的代码中汲取了一些想法并调整了我的代码。
我真的不想用google.appengine.api.urlfetch,遗憾的是我现在没有时间试验。
这是最后的代码,以防万一有人偶然发现东西(另请参阅 voscausa 的 url“App Engine update blob”:
back_url = '{}{}/upload-item/blob-key/{}'.format(_request.protocol, _request.get_host(), id)
# logging.info(back_url)
upload_url = blobstore.create_upload_url(back_url)
BNDR = b'WebKitFormBoundaryE19zNvXGzXaLvS5C' # '--PythonBlobstorevarBoundaryVXGzXaLvS5C'
CRLF = b'\r\n'
DD = b'--'
body = b''.join([
DD + BNDR + CRLF,
b'Content-Disposition: form-data; name="file"; filename="{}"'.format(file_name) + CRLF,
b'Content-Type: {}'.format(file_type) + CRLF,
CRLF,
file_contents + CRLF,
DD + BNDR + DD + CRLF,
])
headers = {
b'Content-Type' : b'multipart/form-data; boundary={}'.format(BNDR),
# b'User-Agent' : b'Mozilla/5.0 (X11; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0',
}
try:
response = urlfetch.fetch(
url = upload_url,
payload = body,
method = urlfetch.POST,
deadline = 40,
follow_redirects = False,
headers = headers
)
if response.status_code == 200:
logging.info(response.content)
else:
logging.info(response)
logging.error(response.content)
logging.exception('URL : {} fetch ERROR : {}'.format(upload_url, response.status_code))
except (urlfetch.DownloadError, DeadlineExceededError), e:
logging.exception('fetch {} download or deadline error, exception : {}'.format(upload_url, str(e)))
我正在尝试从 python 将 blob 上传到 BlobStore 并且它在 https://...appspot.com and https://...com/ 上工作但是当从 http 执行完全相同的代码时它不起作用并且 BlobStore returns 500 错误。
我尝试过使连接始终安全,即使在不安全的情况下也是如此。
这是我的代码:
@staticmethod
def save_to_blobstore(_request, id, file_contents, file_type, file_name = 'fixmeh.png'):
upload_url = blobstore.create_upload_url('/upload-item/blob-key/{}'.format(id))
if upload_url.startswith('http://') and 'localhost.com' not in _request.get_host():
upload_url = 'https' + upload_url[4:]
# ----- CREATING FORMDATA -----
boundary = 'WebKitFormBoundaryE19zNvXGzXaLvS5C'
body = '\r\n'.join([
'--' + boundary,
'Content-Disposition: form-data; name="file"; filename="{}"'.format(file_name),
'Content-Type: {}'.format(file_type),
'',
file_contents,
'',
'--' + boundary + '--',
'',
])
headers = {
'Content-Type' : 'multipart/form-data; boundary={}'.format(boundary),
'User-Agent' : 'Mozilla/5.0 (X11; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0',
}
logging.critical('blobstore save')
# TODO Why the hell do we receive deadline limit exceeded?
request = urllib2.Request(upload_url)
# ----- FORCING SECURE CONNECTION EXCEPT ON LOCALHOST -----
if 'localhost.com' in _request.get_host():
conn = httplib.HTTPConnection(request.get_host(), timeout = 50)
else:
conn = httplib.HTTPSConnection(request.get_host(), timeout = 50)
conn._follow_redirects = True
logging.info(['upload_url', upload_url ])
logging.info(['get_host', request.get_host() ])
logging.info(['get_selector', request.get_selector() ])
conn.request('POST', request.get_selector(), body, headers)
try:
response = conn.getresponse()
response_body = response.read()
logging.info(response_body)
# TODO we need to have an exception if the response is not 200
except DeadlineExceededError:
logging.exception('Saving blob - DeadlineExceededError')
except:
logging.exception('Saving blob')
当通过 HTTP 执行时,这是来自 BlobStore 的 return,尽管它没有多大帮助。有没有办法在 https://console.developers.google.com/project/.../logs 或其他任何地方记录 blobstore 错误。
<html><head>
<meta http-equiv="content-type" content="text/html;charset=utf-8">
<title>500 Server Error</title></head>
<body text=#000000 bgcolor=#ffffff>
<h1>Error: Server Error</h1>
<h2>The server encountered an error and could not complete your request.
<p>Please retry your last submission.</p>
<p>If the problem persists, please contact the person responsible for the application you're using, or, if you are that person,
<a href="http://code.google.com/appengine/community.html">report</a> your
problem and mention this error message and the query that caused it.</h2>
</body></html>
你能帮我解释一下为什么它可能无法在 http 上工作但在 https 上工作吗? (请注意它适用于 SDK 上的 http - 那里没有 ssl,这只发生在 appspot 上)
我使用此代码进行完整上传 url 使用 webapp2 路由:
upload_url = create_upload_url(webapp2.uri_for('blob_update', _full=True))
处理程序使用名为 webapp2 的路由:'blob_update'
class BlobUpdate(blobstore_handlers.BlobstoreUploadHandler):
""" has named route : blob_update :
webapp2.Route(r'/blob_update', handler='....BlobUpdate', name='blob_update') """
def post(self):
""" blob upload handler returns the new blobkey"""
blob_info = self.get_uploads('file')[0]
....
非常感谢您的指导和快速回复。我从您的代码中汲取了一些想法并调整了我的代码。
我真的不想用google.appengine.api.urlfetch,遗憾的是我现在没有时间试验。
这是最后的代码,以防万一有人偶然发现东西(另请参阅 voscausa 的 url“App Engine update blob”:
back_url = '{}{}/upload-item/blob-key/{}'.format(_request.protocol, _request.get_host(), id)
# logging.info(back_url)
upload_url = blobstore.create_upload_url(back_url)
BNDR = b'WebKitFormBoundaryE19zNvXGzXaLvS5C' # '--PythonBlobstorevarBoundaryVXGzXaLvS5C'
CRLF = b'\r\n'
DD = b'--'
body = b''.join([
DD + BNDR + CRLF,
b'Content-Disposition: form-data; name="file"; filename="{}"'.format(file_name) + CRLF,
b'Content-Type: {}'.format(file_type) + CRLF,
CRLF,
file_contents + CRLF,
DD + BNDR + DD + CRLF,
])
headers = {
b'Content-Type' : b'multipart/form-data; boundary={}'.format(BNDR),
# b'User-Agent' : b'Mozilla/5.0 (X11; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0',
}
try:
response = urlfetch.fetch(
url = upload_url,
payload = body,
method = urlfetch.POST,
deadline = 40,
follow_redirects = False,
headers = headers
)
if response.status_code == 200:
logging.info(response.content)
else:
logging.info(response)
logging.error(response.content)
logging.exception('URL : {} fetch ERROR : {}'.format(upload_url, response.status_code))
except (urlfetch.DownloadError, DeadlineExceededError), e:
logging.exception('fetch {} download or deadline error, exception : {}'.format(upload_url, str(e)))