JDK中JAXB常用註解
-
@XmlRootElement
@Retention(RUNTIME)
@Target({TYPE})//作用在類上
public @interface XmlRootElement {
//指定生成的元素所屬的名稱空間
String namespace() default "##default";
//指定生成元素的名字,若不指定則預設使用類名小寫作為元素名
String name() default "##default";
}
類級別的註解,將類對映為xml全域性元素,也就是根元素。就像spring配置檔案中的beans。常與@XmlType,@XmlAccessorType,@XmlAccessorOrder連用。
主意:如果屬性欄位是Null,也就是沒有給屬性設定值,那麼JDK自帶的JXABContext將JavaBean轉成XML字串時,是沒有該屬性欄位的節點的。
-
@XmlElement
@Retention(RUNTIME) @Target({FIELD, METHOD, PARAMETER}) public @interface XmlElement { //指定生成元素的名字 String name() default "##default"; //指定元素的文字值是否可以為空,預設為false。 boolean nillable() default false; //指定該元素是否必須出現,預設為false boolean required() default false; //指定該元素所屬的名稱空間 String namespace() default "##default"; //指定該元素預設的文字值 String defaultValue() default "\u0000"; }
欄位,方法,引數級別的註解。該註解可以將被註解的欄位(非靜態)對映為本地元素,也就是子元素。預設使用欄位名。常與@XmlValue,@XmlJavaTypeAdapter,@XmlElementWrapper連用。 注意: 如果註解加在set方法上,是沒問題的。 但是如果要加在filed欄位上,那麼需要與@XmlAccessorType(XmlAccessType.FIELD)一起使用,否則會報錯(任何註解如果要加在欄位上都需要這樣)。
-
@XmlAttribute
@Retention(RUNTIME) @Target({FIELD, METHOD}) public @interface XmlAttribute { //屬性名 String name() default "##default"; //屬性是否必需 boolean required() default false; //名稱空間 String namespace() default "##default" ; }
欄位和方法級別的註解。該註解會將欄位對映成本類對應元素的屬性,屬性名預設使用欄位名。
-
@XmlTransient
@Retention(RUNTIME) @Target({FIELD, METHOD, TYPE})
public @interface XmlTransient {}
類,欄位,方法級別的註解。可使JAXB在對映xml元素時忽略被註解的類,欄位,get/set對應欄位。需要注意的是該註解與所有其他JAXB註釋相互排斥,也就是說與其他註釋連用就會報錯。該註解沒有屬性。
-
@XmlAccessorType
@Inherited @Retention(RUNTIME) @Target({PACKAGE, TYPE})
public @interface XmlAccessorType {
//可取的值是一個名為XmlAccessType的列舉型別裡的值
XmlAccessType value() default XmlAccessType.PUBLIC_MEMBER;
}
包和類級別的註解。javaEE的API對該註解的解釋是:控制欄位是否被預設序列化。通俗來講,就是決定哪些欄位或哪些get/set方法對應的欄位會被對映為xml元素,需要注意的是欄位或get/set方法的訪問許可權(public/private)會影響欄位是否被對映為xml元素。
XmlAccessType的列舉型別包括:
-
XmlAccessType.PROPERTY 1.當使用了該值,只要欄位有對應的get/set方法對(注意是成對出現,只有其中一個不會發生對映),不需要使用@XmlElement註解,不論該方法的訪問許可權是什麼(即使是private),jaxb就會將該欄位對映成xml元素。不過最好加上@XmlElement註解,get/set方法任選一個即可,都加上會報錯。 2.若在一個欄位有set/get方法對但又在欄位上新增@XmlElement註解會報屬性重複的錯誤。 3.若沒有set/get方法對,則需要在欄位上使用@XmlElement註解才可以對映為xml元素,否則不會發生對映。 4.若get/set方法上使用了@XmlTransient註解,但想要對應欄位發生對映,需要在對應欄位上新增@XmlElement註解,此時不會報錯,並將該欄位對映為xml元素。
-
XmlAccessType.FIELD(一般就是這個) 1.每個非靜態的欄位(無論訪問許可權如何)都會被jaxb對映為xml元素,即使沒有get/set方法對,即使沒有使用@XmlElement元素,但最好加上該註解以表明該欄位要被對映為xml元素。 2.雖然沒有get/set方法對,也會發生對映,但加上get/set方法對也不會報錯,因為我們經常會使用這兩個方法。但注意,不能再在這兩個方法上使用@XmlElement方法,否則會報屬性重複的錯誤。 3.若在欄位上使用了@XmlTransient註解,但還想讓該欄位發生對映,需要在該欄位對應的get/set方法上新增@XmlElement
-
XmlAccessType.PUBLIC_MEMBER (該值為預設值) 1.每個訪問許可權為public的欄位,或者每個訪問許可權為public的get/set方法對,都會將欄位對映為xml元素,即使不使用@XmlElement,但最好加上。不可同時存在public欄位和對應的get/set方法對,不然會報屬性重複的錯誤。 2.若使用@XmlElement註解,需要注意只能在欄位或get/set方法新增,兩者任選其一,否則會報屬性重複的錯誤。 3.若欄位不為public,get/set方法為public並使用了@XmlTransient,需要在欄位上新增@XmlElement才會發生對映。 若欄位為public並使用了@XmlTransient,get/set方法對不為public,需要在get/set方法上使用@XmlElement才會對映。
-
XmlAccessType.NONE 任何欄位,get/set方法對都不會發生對映,除非使用某些註解。 如@XmlElement,@XmlElementWrapper等。
-
@XmlAccessorOrder
@Inherited @Retention(RUNTIME) @Target({PACKAGE, TYPE})
public @interface XmlAccessorOrder {
XmlAccessOrder value() default XmlAccessOrder.UNDEFINED;
}
包和類級別的註解。控制生成元素的順序。 只有一個value屬性,可取的值是一個名為XmlAccessOrder的列舉型別的兩個值: XmlAccessOrder.ALPHABETICAL :按照字母表的順序對生成的元素排序。 XmlAccessOrder.UNDEFINED(預設):按照類中欄位的順序生成元素的順序。
-
@XmlElementWrapper
@Retention(RUNTIME) @Target({FIELD, METHOD})
public @interface XmlElementWrapper {
//包裝標籤名
String name() default "##default";
//包裝標籤名稱空間
String namespace() default "##default";
//指定元素的文字值是否可以為空,預設為false。
boolean nillable() default false;
//是否必需
boolean required() default false;
}
欄位和方法級別的註解。圍繞被對映的xml元素生成包裝元素。主要用在集合物件對映後生成包裝對映結果的xml元素。 一般用在集合欄位上。
-
@XmlJavaTypeAdapter
@Retention(RUNTIME) @Target({PACKAGE,FIELD,METHOD,TYPE,PARAMETER})
public @interface XmlJavaTypeAdapter {
//自定義的介面卡類.class
Class<? extends XmlAdapter> value();
Class type() default DEFAULT.class;
static final class DEFAULT {}
}
包、類、欄位,方法、引數級別的註解。解決java日期(Date),數字(Number)格式化問題。 該註解的用法就是自定義介面卡並繼承XmlAdapter類,實現裡面的marshal和unmarshal方法,並在該註解上引用。
-
@XmlValue
@Retention(RUNTIME) @Target({FIELD, METHOD})
public @interface XmlValue {}
欄位和方法級別的註解。該註解的作用,簡單理解就是定義xml元素文字值的型別,例如在一個類的String型別欄位上使用該註解,則生成的元素文字值型別就是xsd:string,也就是定義一個xsd中的simpleType.若類中還有一個欄位並使用了@XmlAttribute註解,則是定義一個xsd中的complexType。
-
@XmlType
@Retention(RUNTIME) @Target({TYPE})
public @interface XmlType {
String name() default "##default" ;
String[] propOrder() default {""};
String namespace() default "##default" ;
Class factoryClass() default DEFAULT.class;
static final class DEFAULT {}
String factoryMethod() default "";
}
類級別的註解。該註解有些複雜,主要使用的是它的propOrder屬性,簡單來說是用來定義xsd中的simpleType或complexType,從生成的xml中來看,它的作用就是指定生成元素的順序,具體看下圖:
簡單解釋下每行什麼意思:
-
若指定該註解的propOrder為{},會生成ComplexType並且使用xs:all指示器,表示所有被對映的元素都必須出現在xml中
-
若propOrder的值為{“name”, “addr”, “area”}(大括號中都是Person類的欄位名稱),會生成ComplexType並使用xs:sequence指示器,表示生成的xml元素必須按照propOrder指定的順序出現,也就間接實現了排序。
-
若不指定propOrder屬性(這與指定propOrder但值為{}不同),沒有欄位,會生成ComplexType幷包含一個空的xs:sequence指示器。
-
若不指定propOrder屬性,但含有被@XmlValue註解的欄位和被@XmlAttribute註解的欄位,會生成一個含有simpleContent的ComplexType。
-
若不指定propOrder屬性,但含有被@XmlValue註解的欄位而沒有被@XmlAttribute註解的欄位,會生成一個含有simpleType的ComplexType。