开发者

Can not bind attribute to object with XStream Java lib

I'm having trouble in unmarshalling xml with XStream to an Object. The attribute value for operation is never set to field operation in my ImportItem object. For my other elements that contain attributes I use custom converters but I would prefer not to use a customer converter for person. Is this possible and how should I do it to bind operation to the Item object?

XML:

<persons>
    <person operation="insert">
       <personNumber>196211065104</personNumber>
       <startDate>2011-04-13T00:00:00.000+02:00</startDate
       <expireDate>2012-04-14T00:00:00.000+02:00</expireDate
       <orderDate>2011-04-12T00:00:00.000+02:00</orderDate>
       <contact type="name">Joe</name>
       <contact type="email">test@test.com</contact>
       <contact type="landLine">12345678</contact>
    </person>
</persons>

My factory looks like this:

public class XStreamFactory {
    public static XStream instace() {
        XStream xs = new XStream();
        xs.aliasType("person", ImportItem.class);
        xs.useAttributeFor(ImportItem.class, "operation"); <-------
        xs.aliasType("persons", ImportBatch.class);
        xs.aliasType("contact", ImportContactData.class);


        xs.registerConverter(new ImportContactConverter());
        xs.registerConverter(new DateConverter());
        xs.registerConverter(new ImportOperationConverter()); <-------

        xs.addImplicitCollection(ImportBatch.class, "items");
        xs.addImplicitCollection(ImportItem.class, "contactData", ImportContactData.class);

        return xs;
    }

}

Batch:

@SuppressWarnings({"UnusedDeclaration"})
public class ImportBatch {

    private List<ImportItem> items;

    public List<ImportItem> getItems() {
        return items;
    }

    @Override
    public String toString() {
        return "ImportBatch{" +
               "items=\n 开发者_如何转开发 " + StringUtils.join(items, "\n  ") +
               "\n}";
    }
}

ImportItem:

@SuppressWarnings({"UnusedDeclaration"})
public class ImportItem {

    private ImportOperation operation;
    private String personNumber;
    private Date startDate;
    private Date expireDate;
    private Date orderDate;
    private List<ImportContactData> contactData;

    public ImportOperation getOperation() {
        return operation;
    }

    public void setOperation(ImportOperation operation) {
        this.operation = operation;
    }

    public String getCompanyName() {
        return companyName;
    }

    public String getOrganisationNumber() {
        return organisationNumber;
    }

    public String getItescoID() {
        return itescoID;
    }

    public String getAdID() {
        return adID;
    }

    public Date getStartDate() {
        return startDate;
    }

    public Date getExpireDate() {
        return expireDate;
    }

    public String getContactEmail() {
        return contactDataFor(email);
    }

    public String getContactPerson() {
        return contactDataFor(businessPerson);
    }

    public String getContactPhone() {
        return contactDataFor(landLine);
    }        
}

New ImportOperation code: <------

public class ImportOperation {

    public enum OperationType{insert, update, delete}

    private OperationType operation;

    public ImportOperation(OperationType operation) {
        this.operation = operation;
    }

    public OperationType getOperation() {
        return operation;
    }

    public void setOperation(OperationType operation) {
        this.operation = operation;
    }


}

New converter code: <------

public class ImportOperationConverter implements SingleValueConverter {

    public String toString(Object obj) {
        return ((ImportOperation)obj).getOperation().toString();
    }

    public Object fromString(String str) {
        return new ImportOperation(ImportOperation.OperationType.valueOf(str));
    }

    public boolean canConvert(Class clazz) {
        return clazz == ImportOperation.class;
    }
}


You need to tell XStream that the field operation is an xml attribute.

add

xs.useAttributeFor(ImportItem.class, "operation");

@see XStream Alias Tutorial

The reason is, that XStream map everything to XML fields by default. If you unmarshalling an object and an Object field is not defined in the XML then XStream will set it to NULL by default. -- Putting this two pieces together explain the behaviour, and tell you what to do. -> Configure the mapping so that the Person.operation is mapped to the attribute.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜