2014-04-03 66 views
3

我試圖上傳文件,使用requests庫提交POST。Python請求UTF-8文件名中的扼流圈

這工作得很好:

theFile = { 'LUuploadFile': ("linea.ipa", open(path_to_file, 'rb'), 'application/octet-stream') } 
request = requests.post(url, files=theFile) 

這將引發一個錯誤:

theFile = { 'LUuploadFile': ("línea.ipa", open(path_to_file, 'rb'), 'application/octet-stream') } 
request = requests.post(url, files=theFile) 

的錯誤是非常奇怪:

( <class 'requests.exceptions.ConnectionError'>, 
    ConnectionError(MaxRetryError("HTTPSConnectionPool(host='fupload.apperian.com', port=443): 
     Max retries exceeded with url: /upload?transactionID=... 
    (Caused by <class 'socket.error'>: [Errno 32] Broken pipe)",),), 
    <traceback object at 0x100a8e3f8>) 

這不是服務器,它接受的文件名,如果我用curl

curl --form "[email protected]́nea.ipa" http://... 
+0

我在猜測'requests'將' - '字符作爲UTF-8編碼直接插入到套接字中,作爲Content-Disposition標題的一部分,這是不允許的。你有沒有嘗試百分比編碼的文件名? – univerio

+0

@univerio - 實際上,這正是'捲曲'所做的。 'requests'將它編碼爲'filename * = utf-8''li%CC%81nea.ipa' [(rfc5987)](http://tools.ietf.org/html/rfc5987),服務器可能不支持... – mata

+0

工作線和非工作線之間的區別在於,工作線是指'linea',小寫字母i,而一旦不工作,就會在'i'上帶有重音標記'línea'。我的屏幕上的差異不是很明顯。 – khagler

回答

1

這意味着,一些在特定的服務器無法正確執行(根據RFC 5987)的Content-Disposition解析。我不能更具體,因爲有任何許多「移動部分」到Web應用程序服務器(例如,您可能使用nginx + fastcgi + PHP),任何一個(或全部:))可能會被打破。您可能會發現this SO thread以及this page有用,它會從另一端(使用UTF-8名稱下載文件)解決問題,但歸結爲同一問題(解析「Content-Disposition」標頭)。

爲什麼它的價值requests正在做「正確」的事情(根據標準),但是如果服務器上的某些組件不符合標準(或者它不可能)即使是在服務器上 - 例如可能有一個代理正在通過導致問題的低谷)。

+0

這很有幫助。結合上面的評論(「捲曲」不是逃避)現在是合理的。太糟糕了,我不在那裏工作了:) – egrunin