[英]How to change the name of the XmlRootElement in JAXB deppending on the object?
I have the following objects 我有以下物品
Film 电影
@Entity
@Table(name="film")
@XmlRootElement(name = "film")
public class Film implements Serializable {
@Id
@Column(name="id")
private String fbId;
@Column(name="title")
private String title;
@ManyToMany
@JoinTable(
name="direction",
joinColumns={@JoinColumn(name="film", referencedColumnName="id")},
inverseJoinColumns={@JoinColumn(name="person", referencedColumnName="id")})
private Collection<Person> directors;
@OneToMany(cascade={CascadeType.ALL}, mappedBy="film")
@MapKey(name="character")
private Map<String, Performance> performances;
//GETTERS
@XmlAttribute(name = "fbId")
public String getFreebaseId() {
return this.fbId;
}
@XmlElementRefs({
@XmlElementRef(name="director", type=Person.class)
})
public Collection<Person> getDirectors() {
return this.directors;
}
@XmlAnyElement(lax=true)
public Collection<Performance> getPerformances() {
ArrayList performancesArray = new ArrayList<Performance>();
for (Map.Entry<String, Performance> entry : this.performances.entrySet()) {
Performance value = entry.getValue();
performancesArray.add(value);
}
return performancesArray;
}
}
Person 人
@Entity
@Table(name="person")
public class Person implements Serializable {
@Id
@Column(name="id")
private String fbId;
@Column(name="first_name")
private String firstName;
@Column(name="last_name")
private String lastName;
@OneToMany(cascade={CascadeType.ALL}, mappedBy="actor")
@XmlTransient
private Collection<Performance> performances;
//GETTERS
@XmlAttribute(name = "fbId")
public String getFreebaseId() {
return this.fbId;
}
@XmlElement(name = "firstName")
public String getFirstName() {
return this.firstName;
}
@XmlElement(name = "lastName")
public String getLastName() {
return this.lastName;
}
@XmlTransient
public Collection<Performance> getPerformances() {
return this.performances;
}
}
Each film has one (or many) directors and performances which are "Persons". 每部电影都有一个(或许多)导演和表演,即“人物”。 I don't need a class for directors but I do for perfomances because they have more info. 我不需要为导演上课,但我会为性能而做,因为他们有更多的信息。
Performance 性能
@Entity
@Table(name="performance")
@XmlRootElement(name = "performace")
public class Performance implements Serializable {
@Id
@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="film")
private Film film;
@Id
@Column(name="film_character")
private String character;
@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="actor")
private Person actor;
//TO STRING
public String toString() {
return this.actor.toString() + " - " + this.character;
}
//GETTERS
@XmlTransient
public Film getFilm() {
return this.film;
}
@XmlElementRefs({
@XmlElementRef(name = "firstName", type = Person.class),
@XmlElementRef(name = "lastName", type = Person.class)
})
public Person getActor() {
return this.actor;
}
@XmlElement(name = "character")
public String getCharacter() {
return this.character;
}
}
When I run this through JAXB I get this: 当我通过JAXB运行时,我得到了这个:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<film fbId="1">
<description>Nice film</description>
<person fbId="1">
<firstName>Quentin</firstName>
<lastName>Tarantino</lastName>
</person>
<performace>
<person fbId="4">
<firstName>Steve</firstName>
<lastName>Buscemi</lastName>
</person>
<character>Billy</character>
</performace>
<performace>
<person fbId="2">
<firstName>Jhon</firstName>
<lastName>Travolta</lastName>
</person>
<character>Vincent</character>
</performace>
<performace>
<person fbId="3">
<firstName>Samuel</firstName>
<lastName>L Jackson</lastName>
</person>
<character>Jules</character>
</performace>
<performace>
<person fbId="1">
<firstName>Quentin</firstName>
<lastName>Tarantino</lastName>
</person>
<character>Jimmie</character>
</performace>
<title>Pulp Fiction</title>
</film>
Is there a way to change the name of the "person"? 有没有办法改变“人”的名字? To get something like this: 得到这样的东西:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<film fbId="1">
<description>Nice film</description>
<director fbId="1">
<firstName>Quentin</firstName>
<lastName>Tarantino</lastName>
</director>
<performace fbId="4">
<firstName>Steve</firstName>
<lastName>Buscemi</lastName>
<character>Billy</character>
</performace>
<performace fbId="2">
<firstName>Jhon</firstName>
<lastName>Travolta</lastName>
<character>Vincent</character>
</performace>
<performace fbId="3">
<firstName>Samuel</firstName>
<lastName>L Jackson</lastName>
<character>Jules</character>
</performace>
<performace fbId="1">
<firstName>Quentin</firstName>
<lastName>Tarantino</lastName>
<character>Jimmie</character>
</performace>
<title>Pulp Fiction</title>
</film>
Options: 选项:
Director
extends Person
with its own @XmlRootElement
Make Director
使用自己的@XmlRootElement
扩展Person
JAXBElement<? extends Person>
使用JAXBElement<? extends Person>
JAXBElement<? extends Person>
instead of Person
JAXBElement<? extends Person>
而不是Person
The problem is, @XmlElementRef.name does not work for @XmlRootElement
, read here : 问题是,@ XmlElementRef.name不适用于@XmlRootElement
,请在此处阅读:
If type() is JAXBElement.class , then namespace() and name() point to a factory method with XmlElementDecl. 如果type()是JAXBElement.class,则namespace()和name()指向带有XmlElementDecl的工厂方法。 The XML element name is the element name from the factory method's XmlElementDecl annotation or if an element from its substitution group (of which it is a head element) has been substituted in the XML document, then the element name is from the XmlElementDecl on the substituted element. XML元素名称是工厂方法的XmlElementDecl批注中的元素名称,或者如果在XML文档中替换了其替换组中的元素(其为head元素),则元素名称来自替换的XmlElementDecl元件。
If type() is not JAXBElement.class, then the XML element name is the XML element name statically associated with the type using the annotation XmlRootElement on the type. 如果type()不是JAXBElement.class,则XML元素名称是使用类型上的注释XmlRootElement与类型静态关联的XML元素名称。 If the type is not annotated with an XmlElementDecl, then it is an error. 如果类型未使用XmlElementDecl进行批注,那么这是一个错误。
If type() is not JAXBElement.class, then this value must be "". 如果type()不是JAXBElement.class,则此值必须为“”。
By the way 顺便说说
@XmlElementRefs({
@XmlElementRef(name = "firstName", type = Person.class),
@XmlElementRef(name = "lastName", type = Person.class)
})
does not seem valid to me. 对我来说似乎没有用。 @XmlElementRef
are not supposed to map properties of the target class. @XmlElementRef
不应映射目标类的属性。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.