2012-05-29 72 views
0

寻找如何发布使用Python大文件后,我碰到this和我写了基于这样的软件,但是当我运行它,我得到了以下错误消息:Python的HTTP POST失败

Traceback (most recent call last): 
    File "Test3.py", line 187, in <module> 
    main() 
    File "Test3.py", line 184, in main 
    do_upload(options, args) 
    File "Test3.py", line 48, in do_upload 
    response = urllib2.urlopen(request) 
    File "C:\Python27\lib\urllib2.py", line 126, in urlopen 
    return _opener.open(url, data, timeout) 
    File "C:\Python27\lib\urllib2.py", line 400, in open 
    response = meth(req, response) 
    File "C:\Python27\lib\urllib2.py", line 513, in http_response 
    'http', request, response, code, msg, hdrs) 
    File "C:\Python27\lib\urllib2.py", line 438, in error 
    return self._call_chain(*args) 
    File "C:\Python27\lib\urllib2.py", line 372, in _call_chain 
    result = func(*args) 
    File "C:\Python27\lib\urllib2.py", line 521, in http_error_default 
    raise HTTPError(req.get_full_url(), code, msg, hdrs, fp) 
urllib2.HTTPError: HTTP Error 500: Internal Server Error 

这里是我的代码,运行我使用--upload "path_to_file" [space] "filename"的程序。我是python编程新手,所以大部分内容仍然让我困惑。

def do_upload(options, args): 
    url = 'http://127.0.0.1/test_server/upload' 

    path = args[0] 
    # print path 
    filename = args[1] 
    if not os.access(args[0], os.F_OK): 
       print "Directory/file Doesn't exist" 
       exit(1) 

    os.chdir(path) 
    f = open(filename, 'rb') 
    mmapped_file_as_string = mmap.mmap(f.fileno(), 0, access=mmap.ACCESS_READ) 


    request = urllib2.Request(url, mmapped_file_as_string) 
    contenttype = mimetypes.guess_type(filename)[0] 
    request.add_header(contenttype, 'application/octet-stream') 
    response = urllib2.urlopen(request) 


    #close everything 
    mmapped_file_as_string.close() 
    f.close() 

UPDATE

我从上面,现在我得到一些套接字错误改变了代码。

更新代码

def do_upload(options, args): 

    host = 'http://localhost:80' 
    selector = '/test_server/upload' 
    url = 'http://localhost:80/test_server/upload' 

    if len(args) == 2: 
     print "len of args = 2" 
     files = "File is " + str(args[1]) 
     print files 
     path = args[0] 
     print "Path is " + str(args[0]) 



    content_type, body = encode_multipart_formdata(files) 
    h = httplib.HTTP(host) 
    h.putrequest('POST', selector) 
    h.putheader('content-type', content_type) 
    h.putheader('content-length', str(len(body))) 
    h.endheaders() 
    h.send(body) 
    errcode, errmsg, headers = h.getreply() 
    return h.file.read() 

    f = open(files, 'rb') 
    mmapped_file_as_string = mmap.mmap(f.fileno(), 0, access=mmap.ACCESS_READ) 
    request = urllib2.Request(url, mmapped_file_as_string) 
    request.add_header('Content-Type', content_type) 
    response = urllib2.urlopen(request) 

    mmapped_file_as_string.close() 
    f.close() 


def encode_multipart_formdata(files): 

    BOUNDARY = '----------ThIs_Is_tHe_bouNdaRY_$' 
    CRLF = '\r\n' 
    L = [] 

    for (filename) in files: 
     L.append('--' + BOUNDARY) 
     L.append('Content-Disposition: form-data; filename="%s"' % (filename)) 
     L.append('Content-Type: %s' % get_content_type(filename)) 
     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 

def get_content_type(filename): 
    return mimetypes.guess_type(filename)[0] or 'application/octet-stream' 

错误消息

Traceback (most recent call last): 
    File "Test3.py", line 208, in <module> 
    main() 
    File "Test3.py", line 205, in main 
    do_upload(options, args) 
    File "Test3.py", line 41, in do_upload 
    h.endheaders() 
    File "C:\Python27\lib\httplib.py", line 951, in endheaders 
    self._send_output(message_body) 
    File "C:\Python27\lib\httplib.py", line 811, in _send_output 
    self.send(msg) 
    File "C:\Python27\lib\httplib.py", line 773, in send 
    self.connect() 
    File "C:\Python27\lib\httplib.py", line 754, in connect 
    self.timeout, self.source_address) 
    File "C:\Python27\lib\socket.py", line 553, in create_connection 
    for res in getaddrinfo(host, port, 0, SOCK_STREAM): 
socket.gaierror: [Errno 11004] getaddrinfo failed 
+0

你能发表'test_server/upload'代码吗? – dm03514

+0

完成! ,我想提一件事情,我可以使用cURL上传文件,但没有任何问题。 – cyberbemon

回答

4

要设置一个不存在的报头,而不是Content-Type头:

request.add_header(contenttype, 'application/octet-stream') 

将其改为:

request.add_header('Content-Type', contenttype) 

改为。

然而,您最大的问题在于您没有上传多部分POST,而只是将文件本身作为POST正文,而您的服务器只需要分段上传。

看看这个SO回答为一个非常简单的方法来生成一个适当的multipart POST机构:https://stackoverflow.com/a/681182/100297。请注意,您必须相应地调整您的Content-Type标头。

+0

没有修复它,它从错误消息中更改了前3行并将它们替换为这些“File3.test3.py”,第178行,在 main() 文件“Test3.py”,第175行,在主 do_upload(options,args) 文件“Test3.py”,第39行,在do_upload response = urllib2.urlopen(request)' – cyberbemon

+0

谢谢,看看代码我有点困惑, def post_multipart(主机,选择器,字段,文件):'该函数中的选择器意味着 – cyberbemon

+0

它是URL的路径部分; '/ test_server/upload'在你的情况。 –