当我尝试调用.NET Web服务时出现此异常:
javax.xml.bind.JAXBException: class com.pixelware.mdv.tramites.TramiteXML nor any of its super class is known to this context.
客户端是使用CFX JAX-WS前端创建的Java库(使用WSDL预创建的类)
我试图调用的方法接受(嵌套在另一个对象中)一个Object(WSDL中的anyType)
看起来CXF中的JAXB引擎无法编组(序列化为XML)我的类。那是因为JAXB无法序列化一个类,如果它没有在它的上下文中注册,并且该类被传递它是主程序的一部分,而不是客户端库。
CXF文档显示了许多配置选项,看起来可以将属性additionalContextClasses添加到服务属性中。 我无法通过配置添加此属性,因为我的客户端是一个带有CFX生成的类的独立库。
我尝试使用以下代码以编程方式添加属性:
Map<String, Object> ctx = (BindingProvider)ws.getWSSoap()).getRequestContext();
ctx.put("jaxb.additionalContextClasses", new Class[] {TramiteXML.class});
但它不起作用。看起来可能必须在创建客户端之前完成此配置。
我也发现了这个post,问题相同(或非常相似),提出的解决方案并不容易。
难道不应该简单得多吗?也许我错过了什么。 有什么建议吗?
答案 0 :(得分:1)
好吧,我找到了。
我使用CXF提供的“原始”DIspatcher API使其工作。 我创建了一个这样的方法:
public ReturnType registrar(RequestType request)
{
// That's the call that didn't worked. Registrar is the name of the method
// return serviceCLient.registrar(user, password, request);
try {
JAXBContext context = JAXBContext.newInstance(RequestType.class, ReturnType.class,
request.geGenericContent().getClass());
Dispatch<Object> registrarDispatch = service.createDispatch(
RegistroElectronico.RegistroElectronicoSoap, context, Mode.PAYLOAD);
registrarDispatch.getRequestContext().put(Dispatch.SOAPACTION_USE_PROPERTY, Boolean.TRUE );
registrarDispatch.getRequestContext().put(Dispatch.SOAPACTION_URI_PROPERTY, "http://pixelware.com/RegistroTelematico/Registrar" );
Registrar registrar = new Registrar();
registrar.setLogin(this.user);
registrar.setPassword(this.password);
registrar.setSolicitud(request);
RegistrarResponse response = (RegistrarResponse) registrarDispatch.invoke(registrar);
return response.getRegistrarResult();
} catch (JAXBException e) {
throw new RuntimeException(e);
}
}
最后,Dispatcher API比我想象的更容易使用(幸运的是,每个Web服务方法调用都有一个类。)
诀窍是将我的动态对象类型添加到JAXBContext。
无论如何,我想知道为什么这样的事情不能由CXF框架自动完成