今天在调用webservice 接口时,报如下错误
org.apache.cxf.interceptor.Fault: Marshalling Error: XXXX is not known to this context
原因: cxf的一个方法或者说一个请求中,多次调用webservice时,不允许存在多个webservice的wsdl地址
解决办法: 每次调用每次修改wsdl前,重置上下文
public class WsInvoker {
/**
* 调用接口,
* @param wsdl
* @param method
* @param jsons 不定参,可以多个参数
* @return
*/
public String invoke(String wsdl, String method, String... jsons) {
String result = "";
if (null != jsons && jsons.length > 0) {
JaxWsDynamicClientFactory dcf = JaxWsDynamicClientFactory.newInstance();
Client client = dcf.createClient(wsdl);
if (null != client) {
try {
Object[] objects = client.invoke(method, jsons);
result = objects[0].toString();
} catch (Exception e) {
e.printStackTrace();
}
}
}
return result;
}
}
重置上下文的代码如下
public void calculate(){
//在一个方法中连续调用多次WebService接口,每次调用前需要重置上下文
ClassLoader cl = Thread.currentThread().getContextClassLoader();
WsInvoker wsInvoker = new WsInvoker();
String json="test";
Thread.currentThread().setContextClassLoader(cl);//调用接口前重置上下文
String result1 = wsInvoker.invoke(WSDL1,METHOD1, json); //获取接口返回的数据
String json="test";
Thread.currentThread().setContextClassLoader(cl);//调用接口前重置上下文
String result2 = wsInvoker.invoke(WSDL1,METHOD2, json); //menthod已经变了
String json="test";
Thread.currentThread().setContextClassLoader(cl);//调用接口前重置上下文
String result3 = wsInvoker.invoke(WSDL2,METHOD3, json); //wsdl和method都变了
}
另外需要注意的地方是,ClassLoader必须在最外层的请求中生成,
如果是在被调用的方法中生成,且有多次调用该方法,则还是会报错