骡子问题:不止一个JAXBContext

时间:2014-09-09 12:22:27

标签: jaxb mule

我们在与JAXB上下文相关的Mule Adapter中面临一个问题,需要一些相同的意见 我们使用xpath来评估我们的适配器中的选择块中的一些表达式,例如下面的

<choice doc:name="Choice">
<when expression="//env:abc/env:Body/ref:dataelement/ref:/ref:element" evaluator="xpath">
        ......
</when>

现在,这在我们的应用程序中完全正常,但当其他团队中的一个团队在其应用程序中将此适配器用作jar时,会出现问题。

当他们尝试使用此适配器时,它们会低于错误,

Message : More than one object of type class javax.xml.bind.JAXBContext registered but only one expected. 
Type : org.mule.api.registry.RegistrationException 
Code : MULE_ERROR--2 
JavaDoc : http://www.mulesoft.org/docs/site/current3/apidocs/org/mule/api/registry /RegistrationException.html.

在使用记录器等进行调试之后,我们缩小到上面使用的选择块,这会导致此特定问题。另外,谷歌搜索了一下,发现其中一个帖子指出了同样的问题。

另外,为了确认我们注释掉了具有xpath表达式的选择块,并且流程继续进行,但是再次破坏了xpath以其他方式使用的地方。

https://www.mulesoft.org/jira/browse/MULE-5926

有人可以建议任何合适的解决方法来解决此问题吗?

3 个答案:

答案 0 :(得分:1)

我同意你的看法。这是骡子中尚未解决的问题。

我们实现的一个解决方案是不在jar文件中提供的配置中定义jaxb上下文。

与jar文件一起,使用它向最终应用程序发出指令,将JAXB包包含在它们的JAXB Context对象定义中。

这样只有一个JAXB上下文,它将顺利运行。

希望这有帮助。

答案 1 :(得分:0)

这有点晚了,但有效的解决方案是

<mulexml:jaxb-context name=“JAXB_Context“ packageNames=“org.example.test1:org.example.test2“ doc:name=“JAXB Context1“ />

请注意,包名之间必须没有空格。

感谢:http://dominikbial.de/quicktipp-working-with-more-than-one-package-name-in-a-jaxb-context-config-in-mule-esb/

答案 2 :(得分:0)

截至目前,我们无法在骡子中添加多个JAXBContext。作为替代方案,您可以编写自定义变换器。

我实现了像

这样的东西
public interface MyAppJaxbObj2XmlComponent<I,O> extends 
MyAppComponent<I,O>,Callable {  
  public O marshal(I input) throws Exception;
}

Abstart变压器

public abstract class AbstractMyAppJaxbObj2XmlComponent<I,O> implements 
 MyAppJaxbObj2XmlComponent<I,O>{
  private Class<I> inputType;   
    public AbstractMyAppJaxbObj2XmlComponent(){
    this.inputType = (Class<I>) new TypeToken<I>(getClass()) 
 {}.getRawType();
 }

 public AbstractMyAppJaxbObj2XmlComponent(Class<I> type){
    this.inputType = type;
 }

@Override
public Object onCall(MuleEventContext eventContext) throws Exception {
    I input = eventContext.getMessage().getPayload(inputType);
    O output = marshal(input);
    return output;
 }
}

您的流量变换器将在启动期间加载您需要的jaxb。

@Component
public class MyFlowJaxbObj2XmlComponent extends 
AbstractMyAppJaxbObj2XmlComponent<RequestPayloadType,String> {
@PostConstruct
 public void init() {
  //Load your schema during startup
 }
}

您也可以使用流体界面作为替代方案。