Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why doesn't JAXB generate setters for Lists

When I generate JAXB classes from an XSD, the elements with maxOccurs="unbounded" gets a getter method generated for them, but no setter method, as follows:

/**  * Gets the value of the element3 property.  *   * <p>  * This accessor method returns a reference to the live list,  * not a snapshot. Therefore any modification you make to the  * returned list will be present inside the JAXB object.  * This is why there is not a <CODE>set</CODE> method for the element3 property.  *   * <p>  * For example, to add a new item, do as follows:  * <pre>  *    getElement3().add(newItem);  * </pre>  *   *   * <p>  * Objects of the following type(s) are allowed in the list  * {@link Type }  *   *   */ public List<Type> getElement3() {     if (element3 == null) {         element3 = new ArrayList<Type>();     }     return this.element3; } 

The method comment makes it crystal clear on how can I use it, but my question is as follows:
Why doesn't JAXB just generate a setter, following the Java Beans rules? I know I can write the setter method myself, but is there any advantage to the approach suggested in the generated getter method?

This is my XSD:

<?xml version="1.0" encoding="UTF-8"?> <schema xmlns="http://www.w3.org/2001/XMLSchema" xmlns:tns="http://www.example.org/DoTransfer/" targetNamespace="http://www.example.org/DoTransfer/">      <element name="CollectionTest" type="tns:CollectionTest"></element>      <complexType name="CollectionTest">         <sequence>             <element name="element1" type="string" maxOccurs="1" minOccurs="1"></element>             <element name="element2" type="boolean" maxOccurs="1" minOccurs="1"></element>             <element name="element3" type="tns:type" maxOccurs="unbounded" minOccurs="1" nillable="true"></element>         </sequence>     </complexType>       <complexType name="type">         <sequence>             <element name="subelement1" type="string" maxOccurs="1" minOccurs="1"></element>             <element name="subelement2" type="string" maxOccurs="1" minOccurs="0"></element>         </sequence>     </complexType> </schema> 
like image 320
Ahmad Y. Saleh Avatar asked Dec 17 '12 11:12

Ahmad Y. Saleh


People also ask

What is the difference between setter and getter?

Getters and setters are used to protect your data, particularly when creating classes. For each instance variable, a getter method returns its value while a setter method sets or updates its value. Given this, getters and setters are also known as accessors and mutators, respectively.

How do you avoid writing getters and setters?

Solution : create another class in between them that stores your item in the item list and the qty ordered for that item (Let's say the class is called OrderLine). OrderLine will have Item and qty as fields. Pass the return value to the itemList. This way, you avoid getters.


1 Answers

Here is the justification from the JAXB specification - page 60.

Design Note – There is no setter method for a List property. The getter returns the List by reference. An item can be added to the List returned by the getter method using an appropriate method defined on java.util.List. Rationale for this design in JAXB 1.0 was to enable the implementation to wrapper the list and be able to perform checks as content was added or removed from the List.

So if the implementation of the List was overriding add/remove to perform validation, replacing that 'special' List with (for instance) an ArrayList would defeat these checks.

like image 158
jdessey Avatar answered Sep 19 '22 13:09

jdessey