JAX-WS SOAP服务在服务器无响应时会卡死

3
我使用JAX-WS wsgen工具从wsdl模式实现了SOAP客户端。
这是在Windows 32位JDK 1.6.0_45,JAX-WS RI 2.1.6,生成的源代码版本为2.1下完成的。
当服务没有响应时,我的代码在尝试调用Service构造函数时会卡住。
我花了很长时间寻找解决方案。我发现:
1)添加超时系统属性如:
sun.rmi.transport.connectionTimeout=50
sun.rmi.transport.tcp.handshakeTimeout=50
sun.rmi.transport.tcp.responseTimeout=50
sun.rmi.transport.tcp.readTimeout=50
sun.net.client.defaultConnectTimeout=50
sun.net.client.defaultReadTimeout=50
timeout=50

2) 向BindingProvider的RequestContext中添加超时属性:

port = service.getExampleServicePort();
        BindingProvider prov = (BindingProvider) port;
        prov.getRequestContext().put("com.sun.xml.internal.ws.request.timeout", requestTimeout);
        prov.getRequestContext().put("com.sun.xml.ws.request.timeout", requestTimeout);
        prov.getRequestContext().put("com.sun.xml.internal.ws.connect.timeout", connectTimeout);
        prov.getRequestContext().put("com.sun.xml.ws.connect.timeout", connectTimeout);

问题在于,当我调用生成的服务类的构造函数,该类扩展了 javax.xml.ws.Service 时,在我获取端口之前,代码会冻结。
   service = new ExampleService(url, new QName("http://query.services.example.com/", "ExampleService")); 
//freezes here

以下是引起问题的构造函数:

/**
 * This class was generated by the JAX-WS RI.
 * JAX-WS RI 2.1.6 in JDK 6
 * Generated source version: 2.1
 * 
 */
@WebServiceClient(name = "ExampleService", targetNamespace = "http://query.services.example.com/", wsdlLocation = "http://myservicehost/services/Query.asmx?WSDL")
public class ExampleService
    extends Service
{

    public ExampleService(URL wsdlLocation, QName serviceName) {
        super(wsdlLocation, serviceName);
    }

    //....
}

最后,这种服务方法只是挂起。
protected Service(java.net.URL wsdlDocumentLocation, QName serviceName) {
        delegate = Provider.provider().createServiceDelegate(wsdlDocumentLocation,
                serviceName,
                this.getClass());
    }

我该如何防止ExampleService在服务未响应时冻结(不使用其他库,如Apache Axis或JBoss WS)?

谢谢!

1个回答

3

我认为同一个答案适用于您的问题 - 将WSDL文档保存到本地。


2
好的,这真的很有帮助。原来,需要使用WSDL来实例化服务类。这在这个答案中有描述。但是如果WSDL被更改了,我使用过时的本地副本怎么办? - Artems
如果有人以向后兼容的方式更改了 WSLD(例如添加可能为空的新方法或参数),那还是可以的。如果服务契约以不兼容的方式更改(这只是粗心大意),无论您是下载 WSLD 还是将其保留在本地,您的客户端都会出现故障。 - Arunas Junevicius

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接