`

ksoap2-android和cxf服务连接时的序列化问题处理

 
阅读更多

目前项目要用到webservice来和后端交互,后端使用的cxf编写,用的jaxb做序列化。当中遇到了ksoap2-android发出的报文不能被正确解析的问题,遂在这里发文以共享。

 

          当中一共遇到了3个问题:

(1)命名空间前缀的问题

(2)复杂对象的命名问题

 

最后一个问题容易解决,在此逐一说明:

 

(1)命名空间前缀的问题:

           在webservice中,一个请求报文能够被正确解析,报文的格式是首先的。在其官网提供的资料中,一般很少提及服务端是什么类型,网上有见到用axis做服务端的。不过,由于cxf本身的一些较好特性,我们的项目中使用了cxf。ksoap2-android提供了一个开关项Dotnet来控制一个元素是否添加名字空间前缀,来解决兼容性问题。但是, 在调试过程中发现,在请求包的body元素的第一层元素,就是调用方法元素上,如果不携带命名空间,对端无法正确解析,这是因为cxf在发布WSDL时,其中的元素都带有命名空间,而此时使用的Dotnet开关是true,也许是设计者习惯于这种方式吧,其实按照字面理解,此时应当是:true表明要兼容DOTNET,所以会加上命名空间前缀,而false表明不需要兼容,则不加前缀。不过这个问题无伤大雅。

           改变开关后,所有元素都加上了前缀,但是参数部分又无法解析,根据错误信息判断是参数部分不能使用加前缀方式来标明命名空间,而应使用属性方式。

          此问题的解决是下载了其源码包,并从原来的SoapSerializationEnvelope和SoapObject分别派生新的子类。

SoapSerializationEnvelope的序列化时,读取带序列化对象的Dotnet参数来确定是否使用前缀方式的命名空间。SoapObject的派生对象则相应的添加Dotnet属性供序列化方法读取。这样的话,就是分开处理的策略,从而解决了这个问题。

    (2)复杂对象的命名问题

         调用参数的添加官方文档给了示例,但是不够明确详尽,在这里补充之:请求包的参数元素的名字应当和其在WSDL中的方法描述中的名字一致。对此,在构建请求的对象时,将SoapObject以相应名称的Property添加即可。对于复杂类型对象,在构建对应的SoapObject时,其第二个参数要使用短类名类进行。有的文档中在给出实例时,称第二个参数为methodname,是不对的,其应当是elementName的含义。

 

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics