2012-07-05 121 views
0

我正在尝试使用由我们的开发人员创建的Webservice,它允许我们在某些限制内将文件上载到系统中。从Webservice返回的Python SUDS unicode解码错误

使用肥皂水,我得到以下信息:

Suds (https://fedorahosted.org/suds/) version: 0.4 GA build: R699-20100913 

Service (ConnectToEFS) tns="http://tempuri.org/" 
    Prefixes (3) 
     ns0 = "http://schemas.microsoft.com/2003/10/Serialization/" 
     ns1 = "http://schemas.microsoft.com/Message" 
     ns2 = "http://tempuri.org/" 
    Ports (1): 
     (BasicHttpBinding_IConnectToEFS) 
     Methods (2): 
      CreateContentFolder(xs:string FileCode, xs:string FolderName, xs:string ContentType, xs:string MetaDataXML,) 
      UploadFile(ns1:StreamBody FileByteStream,) 
     Types (4): 
      ns1:StreamBody 
      ns0:char 
      ns0:duration 
      ns0:guid 

我的方法使用UploadFile如下:

def webserviceUploadFile(self, targetLocation, fileName, fileSource): 
    fileSource = './test_files/' + fileSource 
    ntlm = WindowsHttpAuthenticated(username=uname, password=upass) 
    client = Client(webservice_url, transport=ntlm) 
    client.set_options(soapheaders={'TargetLocation':targetLocation, 'FileName': fileName}) 
    body = client.factory.create('AIRDocument') 
    body_file = open(fileSource, 'rb') 
    body_data = body_file.read() 
    body.FileByteStream = body_data 
    return client.service.UploadFile(body) 

运行这让我以下结果:

Traceback (most recent call last): 
    File "test_cases.py", line 639, in test_upload_file_invalid_extension 
    result_string = self.HM.webserviceUploadFile('9999', 'AD-1234-5424__44.exe', 
'test_data.pdf') 
    File "test_cases.py", line 81, in webserviceUploadFile 
    return client.service.UploadFile(body) 
    File "build\bdist.win32\egg\suds\client.py", line 542, in __call__ 
    return client.invoke(args, kwargs) 
    File "build\bdist.win32\egg\suds\client.py", line 595, in invoke 
    soapenv = binding.get_message(self.method, args, kwargs) 
    File "build\bdist.win32\egg\suds\bindings\binding.py", line 120, in get_message 
    content = self.bodycontent(method, args, kwargs) 
    File "build\bdist.win32\egg\suds\bindings\document.py", line 63, in bodycontent 
    p = self.mkparam(method, pd, value) 
    File "build\bdist.win32\egg\suds\bindings\document.py", line 105, in mkparam 
    return Binding.mkparam(self, method, pdef, object) 
    File "build\bdist.win32\egg\suds\bindings\binding.py", line 287, in mkparam 
    return marshaller.process(content) 
    File "build\bdist.win32\egg\suds\mx\core.py", line 62, in process 
    self.append(document, content) 
    File "build\bdist.win32\egg\suds\mx\core.py", line 75, in append 
    self.appender.append(parent, content) 
    File "build\bdist.win32\egg\suds\mx\appender.py", line 102, in append 
    appender.append(parent, content) 
    File "build\bdist.win32\egg\suds\mx\appender.py", line 243, in append 
    Appender.append(self, child, cont) 
    File "build\bdist.win32\egg\suds\mx\appender.py", line 182, in append 
    self.marshaller.append(parent, content) 
    File "build\bdist.win32\egg\suds\mx\core.py", line 75, in append 
    self.appender.append(parent, content) 
    File "build\bdist.win32\egg\suds\mx\appender.py", line 102, in append 
    appender.append(parent, content) 
    File "build\bdist.win32\egg\suds\mx\appender.py", line 198, in append 
    child.setText(tostr(content.value)) 
    File "build\bdist.win32\egg\suds\sax\element.py", line 251, in setText 
    self.text = Text(value) 
    File "build\bdist.win32\egg\suds\sax\text.py", line 43, in __new__ 
    result = super(Text, cls).__new__(cls, *args, **kwargs) 
UnicodeDecodeError: 'ascii' codec can't decode byte 0xe2 in position 10: ordinal 
not in range(128) 

经过大量研究并与Web服务的开发人员交谈之后,我修改了body_data = b ody_file.read()到body_data = body_file.read()解码( “UTF-8”),这让我这个错误:

Traceback (most recent call last): 
    File "test_cases.py", line 639, in test_upload_file_invalid_extension 
    result_string = self.HM.webserviceUploadFile('9999', 'AD-1234-5424__44.exe', 'test_data.pdf') 
    File "test_cases.py", line 79, in webserviceUploadFile 
    body_data = body_file.read().decode("utf-8") 
    File "C:\python27\lib\encodings\utf_8.py", line 16, in decode 
    return codecs.utf_8_decode(input, errors, True) 
UnicodeDecodeError: 'utf8' codec can't decode byte 0xe2 in position 10: invalid 
continuation byte 

这是不到有用的。

多研究问题后,我尝试添加“错误=”忽略'的UTF-8编码,这是结果:

<TransactionDescription>Error in INTL-CONF_France_PROJ_MA_126807.docx: An exception has been thrown when reading the stream.. Inner Exception: System.Xml.XmlException: The byte 0x03 is not valid at this location. Line 1, position 318. 
    at System.Xml.XmlExceptionHelper.ThrowXmlException(XmlDictionaryReader reader, String res, String arg1, String arg2, String arg3) 
    at System.Xml.XmlUTF8TextReader.Read() 
    at System.ServiceModel.Dispatcher.StreamFormatter.MessageBodyStream.Exhaust(XmlDictionaryReader reader) 
    at System.ServiceModel.Dispatcher.StreamFormatter.MessageBodyStream.Read(Byte[] buffer, Int32 offset, Int32 count). Source: System.ServiceModel</TransactionDescription> 

还几乎树桩我就做什么。基于webservice的结果堆栈跟踪,它看起来像是想要UTF-8,但是我似乎无法在没有Python或SUDS的情况下将其转移到webservice上,或者忽略编码中的问题。我正在使用的系统仅采用MicroSoft办公室类型文件(doc,xls等),PDF和TXT文件,因此使用我对编码有更多控制的内容不是一种选择。我也尝试检测示例PDF和示例DOCX所使用的编码,但是使用它所建议的(Latin-1,ISO8859-x和几个窗口XXXX)全部被Python和SUDS接受,但不被web服务接受。

另请注意,在显示的示例中,它最经常引用对无效扩展的测试。即使在成功上传的测试中,这个错误也是适用的,这是唯一一次最终堆栈跟踪出现的时间。

回答

2

您可以使用此base64.b64encode(body_file.read()),这将返回base64字符串值。所以你的请求变量必须是一个字符串。