Java 如何将不属于BindingProvider子类的对象显式转换为BindingProvider对象?
我有一个web服务,其中我正在使用客户端API中的服务接口对象操作SOAP头 我需要将端口对象强制转换为Java 如何将不属于BindingProvider子类的对象显式转换为BindingProvider对象?,java,web-services,jakarta-ee,jax-ws,soap-client,Java,Web Services,Jakarta Ee,Jax Ws,Soap Client,我有一个web服务,其中我正在使用客户端API中的服务接口对象操作SOAP头 我需要将端口对象强制转换为BindingProvider对象。但我的端口对象并没有直接为该类创建子类。那么JVM怎么可能不抱怨呢 而且它也有效。ClassCastException没有运行时错误 代码段: public SearchDocument getSearchDocumentService(String wsdlUri, AuthBean auth){ SearchDocument_Servic
BindingProvider
对象。但我的端口对象并没有直接为该类创建子类。那么JVM怎么可能不抱怨呢
而且它也有效。ClassCastException没有运行时错误
代码段:
public SearchDocument getSearchDocumentService(String wsdlUri, AuthBean auth){
SearchDocument_Service serv = null;
serv = SearchDocument_Service.getServiceInstance(wsdlUri);
SearchDocument searchDoc = serv.getSearchDocument();
populateAuthAndHandlerInfo((BindingProvider)searchDoc, auth);//how is it that jvm doesn't complain here
return searchDoc;
}
private void populateAuthAndHandlerInfo(BindingProvider port, AuthBean auth) {
Binding binding = port.getBinding();
List<Handler> handlerList = binding.getHandlerChain();
handlerList.add(new EDMSSoapAuthHandler());
binding.setHandlerChain(handlerList);
Map<String, Object> context = port.getRequestContext();
context.put("clientAuthInfo", auth);
}
有几种方法可以回答你的问题 从高层次的角度来看 但我的端口对象并没有直接为该类创建子类。那么JVM怎么可能不抱怨呢 嗯<代码>搜索文档是一个界面。那么,当你打电话的时候
SearchDocument searchDoc = serv.getSearchDocument();
然后,searchDoc
是实现接口的给定类型的实例,但是没有指定这个具体类是什么。它可以是任何东西,包括实现SearchDocument
和BindingProvider
的具体类,因为两者都是接口,任何给定类型都可以同时自由实现多个接口。
所以这里一定发生了这样的事情,对吧
来自JAX-WS规范
查看JAXWS规范可能会进一步启发您。您可以在下载,但我将在第4.2.3章为您引述一些要点:
代理在运行时提供对服务端点接口的访问,而无需静态生成stubclass。请参阅java.lang.reflect.Proxy
有关JDK支持的动态代理的更多信息
一致性(实现BindingProvider):代理实例必须实现javax-.xml.ws.BindingProvider
使用服务实例的getPort方法创建代理:T getPort(类sei)返回指定sei的代理
现在很容易把这些碎片重新组合起来
什么是java.lang.reflect.Proxy
东西。
在JVM中,有一个用于创建代理对象的API<代码>代理对象(实例)是JVM中的一种特殊类型的beast,可以在运行时动态创建,并且可以使每个代理符合任何给定的接口。这就像在运行时而不是编译时创建一个类,而不必编写java源文件。当然,有各种各样的限制,但也有许多可能性
一种是对JVM说:“嘿,给我一个Proxy
对象,它同时实现接口SearchDocument
和BindingProvider
”。JVM也是如此。它返回一个对象,其具体类是Proxy
(通常是Proxy$x,其中x是一个数字),并经过精心设计以实现这两个接口
如果您想知道这在这一点上是否有用,那么不,它不是,因为创建一个没有实现的类型是毫无意义的。但是有一种方法可以提供一种实现和行为,通过您编程的InvocationHandler
(另一个讨论就是这样的)
因此,在这一点上,我们从规范中得到的是,如果我们在javax.xml.ws.Service
上调用getPort
,那么结果必须是一个JDK代理,它还必须实现BindingProvider
回到你的案子上来
我敢打赌,这正是您调用时发生的情况:SearchDocument\u服务
,它最终调用了一个getPort
方法,并确保结果实现了BindingProvider
,因为JAXWS说它必须这样做,而您的SearchDocument
“业务”界面,因为这对你是有用的。搞定了!!正如您所说,在SearchDocument\u服务
impl类中调用了一个getPort()方法。我现在完全明白了。尽管所有这些都只是作为一个整体来处理有点复杂(代理>网络>服务端点>等等,等等,等等!)。谢谢GPI:)我会给这个是+1,一旦我得到一个代表15不是一个问题,我不介意我的代表这么多。也许你仍然可以接受这个答案。这很复杂,但是能够在接口之间屏蔽实现是非常聪明的(如果你想一想,WSDL端口类型就是一个接口,所以在我看来,JAXWS代理接口来放置序列化/XML和网络逻辑的方式是非常聪明的!)。
SearchDocument searchDoc = serv.getSearchDocument();