Search code examples
javainheritancemarshallingcompositionjaxb2

change inheritance to composition for existing jaxb class structure keeping the current xml structure unchanged


In my code base I have B extdnds A but I want to make it: B uses A. This is my try:

@XmlAccessorType(XmlAccessType.NONE)
public class A {

    @XmlElement(name ="aString")
    private String aString;

B class contains A (composition):

@XmlAccessorType(XmlAccessType.NONE)
public class B {

    @XmlElement
    private A a = new A(); // has A

    @XmlElement
    private String bString;

There is Root that contains list of B

@XmlRootElement
@XmlAccessorType(XmlAccessType.NONE)
public class ABs {

    @XmlElement(name = "b-list")
    private final List<B> bList = Constraints.constrainedList(new ArrayList<B>(), Constraints.notNull());


    public void add(B...bb) {
        for(B b : bb) {
            bList.add(b);
        }
    }
}

My test, marshals Bs to Systetem.out

 ABs abs = new ABs();
        abs.add( new B("bStringValue", "aStringValue"));

        JAXBContext context = JAXBContext.newInstance(ABs.class);

        Marshaller m = context.createMarshaller();
        m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);

        m.marshal(abs, System.out);

Result:

<aBs>
    <b-list>
        <a>
            <aString>aStringValue</aString>
        </a>
        <bString>bStringValue</bString>
    </b-list>
</aBs>

But I want result like this: as if I use inheritance. Like as if B extends A :

<aBs>
    <b-list>
        <aString>aStringValue</aString>
        <bString>bStringValue</bString>
    </b-list>
</aBs>

How can I do this?

EDIT:

The question is really about: How to omit/ignore tag <a> for A class when use it in B class. I.e. to not marshal to <a> but to all fields/tags that inside <a>

Like:

@XmlElement(name = "") // empty
private A a = new A();

But this does not work


Solution

  • The answer is here:

    Is it possible to ignore a wrapper class during JAXB marshalling

    The answer is: impossible.

    Actually my question is kind of duplication of that one. But my question is related to architectural side of issue.

    It seems that JAXB is not the best thing to use If you want to stay with XML structure like it was before (imagine that XML is REST API you not suppose to change, but still you wish to change classes around it) but change the way the classes connect to each other.

    It(jaxb) breaks a freedom. The classes become a bit (too much I mean) anemic..