• java 跟.net webservice 互通问题


    最近忙一个跟国外公司合作的项目,国外公司提供的web service不是我用的.net 平台,折腾了良久,发现了不少问题,归纳一下,

    首先我这边拿到的是国外提供的wsdl 文件,我用microsoft的wsdl.exe 生成我需要的cs代码,通过这种方式来完成对国外web service的调用,用wsdl.exe ,如图所示:

    打开命令提示窗口后:

    这样我们就可以调用国外的web services了,但是请注意:

    微软生成的代码比wsdl中所定义的方法,属性多了不少的东西,就个人理解说明一下:

    1.为每一个方法提供了异步调用的方法,如一个方法名为CreateOrder,则多了 BeginCreateOrder,EndCreateOrder,CreateOrderAsync,OnCreateOrderOperationCompleted

    具体方法的使用和说明可参考微软msdn的说明

    2.具体参数是enum和特殊日期类型,microsoft自动为我们增加了Specified后缀的bool字段,如enum类型 flag,增加的名称flagSpecified,请记得无比需要设该值为true,才可能为非.net 的web service 传值.否则soap 包是不会有值的.


    跟踪soap 包的工具可用tcpTrace等

    国外的客户端需要回调我提供的.net 的web service环境,但国外公司调用报错:

      <?xml version="1.0" encoding="utf-8" ?>

    - <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">

    - <soap:Body>

    - <soap:Fault>

      <faultcode>soap:Client</faultcode>

      <faultstring>Server did not recognize the value of HTTP Header SOAPAction: .</faultstring>

      <detail />

      </soap:Fault>

      </soap:Body>

      </soap:Envelope>

    网上找了些资料,放在这里,今天需要验证下是否可行:

    最近做项目,涉及到web-service调用,现学了一个星期,现简单的做一个小结。下面实现的是对传喜物流系统(http://vip.cxcod.com/PodApi/GetPodStr.asmx?wsdl)的订单跟踪(web-service调用)功能。

    一. 使用axis1.x调用webservice方法

    Axis的最常用版本:1.4和2.0版本。以下为1.4版本

     核心代码:

      // webserviceURL

          service_url = "http://vip.cxcod.com/PodApi/GetPodStr.asmx?wsdl";

          Service service = new Service();

          Call call = (Call) service.createCall();

          call.setTargetEndpointAddress(new java.net.URL(service_url));

    // 设置要调用的方法

    // http://intelink.net/是wsdl中definitions根节点的targetNamespace属性值

    call.setOperationName(new QName("http://intelink.net/","GetStrByJobno"));

    // 该方法需要的参数

    call.addParameter("CustNo",

      org.apache.axis.encoding.XMLType.XSD_STRING,

      javax.xml.rpc.ParameterMode.IN);

    call.addParameter("passwd",

       org.apache.axis.encoding.XMLType.XSD_STRING,

       javax.xml.rpc.ParameterMode.IN);

    call.addParameter("Jobno",

       org.apache.axis.encoding.XMLType.XSD_STRING,

       javax.xml.rpc.ParameterMode.IN);

    // 方法的返回值类型

    call.setReturnType(org.apache.axis.encoding.XMLType.XSD_STRING);

    // call.setUseSOAPAction(true); //call.setSOAPActionURI("http://intelink.net/GetStrByJobno");

    // 调用该方法, new Object[] { CustNo, passwd, Jobno}为参数列表

    String xmlStr = call.invoke(new Object[] { CustNo, passwd, Jobno}).toString();

    } catch (Exception e) {

    e.printStackTrace();

    }

    JAVA用这种方式调用webservice,需要注意的地方:

    1. 服务器未能识别 HTTP 标头 SOAPAction 的值:

    症状一:

    Web Service + ASP.NET 应用程序部署到服务器默认目录中,在IE中用http://<服务器地址>/<程序目录名>/<默认启动页面名>发生“服务器未能识别 HTTP 标头 SOAPAction 的值”错误。

    症状二:

    在Java平台上调用.NET Web Service的服务时,出现"服务器未能识别 HTTP 标头 SOAPAction 的值"。

    症状三:

    在Java平台下调用.NET WEB Service,出现数据时有时无。

    解决对策:

    给.NET的WebService类(即.asmx文件下的类)添加属性[SoapDocumentService(RoutingStyle=SoapServiceRoutingStyle.RequestElement)]

    小知识:

    什么是SoapAction?它在WSDL中有何作用?

    SOAPAction HTTP request header被用来标识SOAP HTTP请求的目的地,其值是个URI地址。SOAP发送并不限制格式、URI特征或其必须可解析,那么在这种情况下,发送一个HTTP SOAP请求时,其HTTP客户端必须使用/指明SOAPAction HTTP request header。

    SOAPAction header的内容可以被用在服务端,诸如:防火墙适当的过滤基于HTTP的SOAP请求消息等场景。SOAPAction header的值为空串("")表示SOAP消息的目的地由HTTP请求的URI标识;无值则表示没有指定这条消息的目的地。

    本人补充:

    在.NET环境调用.NET WebService出现 “SOAPAction 值在 XML Web services 的所有方法中不唯一的错误”,也可以通过此法解决。

    2. 为了Java能够调用WebService的方法,所以。NETP写的WebServiced的每个方法都要声明为Rpc方法,即添加"[SoapRpcMethod.....]".

    例如:[WebMethod]

            [SoapRpcMethod(Use=SoapBindingUse.Literal,Action= http://tempuri.org/HelloWorld", RequestNamespace = "http://tempuri.org/", ResponseNamespace = "http://tempuri.org/")]

    3. 对返回值、参数的处理上:

    应尽量将webservice方法的返回值、参数都写成字符串(String)不要使用复杂对象类型,这样便于在网络上传输。避免了复杂对象类型的不易转换问题。。。对于返回类型是字符串数组型的,可以设置返回类型为org.apache.axis.encoding.XMLType.SOAP_VECTOR或java.lang.String[].class.

    二.利用xfire调用WebService

    XFire是新一代的Java Web服务引擎,XFire使得在JavaEE应用中发布Web服务变得轻而易举。和其他Web服务引擎相比,XFire的配置非常简单,可以非常容易地和Spring集成,它使得Java开发人员终于可以获得和.Net开发人员一样的开发效率。

    核心代码:

    Service service = new ObjectServiceFactory().create(IWebservice.class);

    XFireProxyFactory factory =

    new XFireProxyFactory(XFireFactory.newInstance().getXFire());

    String url= "http://localhost:8080/webservices/services/webservices";

    IWebservice iw = (IWebservice) factory.create(service, url);

    List list=iw.getTest();

  • 相关阅读:
    基于UML的科研管理系统 的设计与实现06
    基于UML的科研管理系统 的设计与实现05
    基于UML的科研管理系统 的设计与实现04
    基于UML的科研管理系统 的设计与实现03
    《暗时间》读后感
    毕业设计之文献综述目录
    基于UML的科研管理系统 的设计与实现02
    基于UML的科研项目管理系统的设计与实现01
    【手撕】中序遍历二叉树
    【手撕】二叉树前序遍历
  • 原文地址:https://www.cnblogs.com/encounter/p/2188788.html
Copyright © 2020-2023  润新知