aoqi@0: /* aoqi@0: * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved. aoqi@0: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. aoqi@0: * aoqi@0: * This code is free software; you can redistribute it and/or modify it aoqi@0: * under the terms of the GNU General Public License version 2 only, as aoqi@0: * published by the Free Software Foundation. Oracle designates this aoqi@0: * particular file as subject to the "Classpath" exception as provided aoqi@0: * by Oracle in the LICENSE file that accompanied this code. aoqi@0: * aoqi@0: * This code is distributed in the hope that it will be useful, but WITHOUT aoqi@0: * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or aoqi@0: * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License aoqi@0: * version 2 for more details (a copy is included in the LICENSE file that aoqi@0: * accompanied this code). aoqi@0: * aoqi@0: * You should have received a copy of the GNU General Public License version aoqi@0: * 2 along with this work; if not, write to the Free Software Foundation, aoqi@0: * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. aoqi@0: * aoqi@0: * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA aoqi@0: * or visit www.oracle.com if you need additional information or have any aoqi@0: * questions. aoqi@0: */ aoqi@0: aoqi@0: package javax.xml.bind.annotation; aoqi@0: aoqi@0: import org.w3c.dom.Element; aoqi@0: aoqi@0: import javax.xml.bind.JAXBContext; aoqi@0: import javax.xml.bind.JAXBElement; aoqi@0: import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter; aoqi@0: import java.lang.annotation.Retention; aoqi@0: import java.lang.annotation.Target; aoqi@0: import java.util.List; aoqi@0: aoqi@0: import static java.lang.annotation.ElementType.FIELD; aoqi@0: import static java.lang.annotation.ElementType.METHOD; aoqi@0: import static java.lang.annotation.RetentionPolicy.RUNTIME; aoqi@0: aoqi@0: /** aoqi@0: * Maps a JavaBean property to XML infoset representation and/or JAXB element. aoqi@0: * aoqi@0: *

aoqi@0: * This annotation serves as a "catch-all" property while unmarshalling aoqi@0: * xml content into a instance of a JAXB annotated class. It typically aoqi@0: * annotates a multi-valued JavaBean property, but it can occur on aoqi@0: * single value JavaBean property. During unmarshalling, each xml element aoqi@0: * that does not match a static @XmlElement or @XmlElementRef aoqi@0: * annotation for the other JavaBean properties on the class, is added to this aoqi@0: * "catch-all" property. aoqi@0: * aoqi@0: *

aoqi@0: *

Usages:

aoqi@0: *
aoqi@0:  * @XmlAnyElement
aoqi@0:  * public {@link Element}[] others;
aoqi@0:  *
aoqi@0:  * // Collection of {@link Element} or JAXB elements.
aoqi@0:  * @XmlAnyElement(lax="true")
aoqi@0:  * public {@link Object}[] others;
aoqi@0:  *
aoqi@0:  * @XmlAnyElement
aoqi@0:  * private List<{@link Element}> nodes;
aoqi@0:  *
aoqi@0:  * @XmlAnyElement
aoqi@0:  * private {@link Element} node;
aoqi@0:  * 
aoqi@0: * aoqi@0: *

Restriction usage constraints

aoqi@0: *

aoqi@0: * This annotation is mutually exclusive with aoqi@0: * {@link XmlElement}, {@link XmlAttribute}, {@link XmlValue}, aoqi@0: * {@link XmlElements}, {@link XmlID}, and {@link XmlIDREF}. aoqi@0: * aoqi@0: *

aoqi@0: * There can be only one {@link XmlAnyElement} annotated JavaBean property aoqi@0: * in a class and its super classes. aoqi@0: * aoqi@0: *

Relationship to other annotations

aoqi@0: *

aoqi@0: * This annotation can be used with {@link XmlJavaTypeAdapter}, so that users aoqi@0: * can map their own data structure to DOM, which in turn can be composed aoqi@0: * into XML. aoqi@0: * aoqi@0: *

aoqi@0: * This annotation can be used with {@link XmlMixed} like this: aoqi@0: *

aoqi@0:  * // List of java.lang.String or DOM nodes.
aoqi@0:  * @XmlAnyElement @XmlMixed
aoqi@0:  * List<Object> others;
aoqi@0:  * 
aoqi@0: * aoqi@0: * aoqi@0: *

Schema To Java example

aoqi@0: * aoqi@0: * The following schema would produce the following Java class: aoqi@0: *
aoqi@0:  * <xs:complexType name="foo">
aoqi@0:  *   <xs:sequence>
aoqi@0:  *     <xs:element name="a" type="xs:int" />
aoqi@0:  *     <xs:element name="b" type="xs:int" />
aoqi@0:  *     <xs:any namespace="##other" processContents="lax" minOccurs="0" maxOccurs="unbounded" />
aoqi@0:  *   </xs:sequence>
aoqi@0:  * </xs:complexType>
aoqi@0:  * 
aoqi@0: * aoqi@0: *
aoqi@0:  * class Foo {
aoqi@0:  *   int a;
aoqi@0:  *   int b;
aoqi@0:  *   @{@link XmlAnyElement}
aoqi@0:  *   List<Element> any;
aoqi@0:  * }
aoqi@0:  * 
aoqi@0: * aoqi@0: * It can unmarshal instances like aoqi@0: * aoqi@0: *
aoqi@0:  * <foo xmlns:e="extra">
aoqi@0:  *   <a>1
aoqi@0:  *   <e:other />  // this will be bound to DOM, because unmarshalling is orderless
aoqi@0:  *   <b>3
aoqi@0:  *   <e:other />
aoqi@0:  *   <c>5     // this will be bound to DOM, because the annotation doesn't remember namespaces.
aoqi@0:  * </foo>
aoqi@0:  * 
aoqi@0: * aoqi@0: * aoqi@0: * aoqi@0: * The following schema would produce the following Java class: aoqi@0: *
aoqi@0:  * <xs:complexType name="bar">
aoqi@0:  *   <xs:complexContent>
aoqi@0:  *   <xs:extension base="foo">
aoqi@0:  *     <xs:sequence>
aoqi@0:  *       <xs:element name="c" type="xs:int" />
aoqi@0:  *       <xs:any namespace="##other" processContents="lax" minOccurs="0" maxOccurs="unbounded" />
aoqi@0:  *     </xs:sequence>
aoqi@0:  *   </xs:extension>
aoqi@0:  * </xs:complexType>
aoqi@0:  * 
aoqi@0: * aoqi@0: *
aoqi@0:  * class Bar extends Foo {
aoqi@0:  *   int c;
aoqi@0:  *   // Foo.getAny() also represents wildcard content for type definition bar.
aoqi@0:  * }
aoqi@0:  * 
aoqi@0: * aoqi@0: * aoqi@0: * It can unmarshal instances like aoqi@0: * aoqi@0: *
aoqi@0:  * <bar xmlns:e="extra">
aoqi@0:  *   <a>1
aoqi@0:  *   <e:other />  // this will be bound to DOM, because unmarshalling is orderless
aoqi@0:  *   <b>3
aoqi@0:  *   <e:other />
aoqi@0:  *   <c>5     // this now goes to Bar.c
aoqi@0:  *   <e:other />  // this will go to Foo.any
aoqi@0:  * </bar>
aoqi@0:  * 
aoqi@0: * aoqi@0: * aoqi@0: * aoqi@0: * aoqi@0: *

Using {@link XmlAnyElement} with {@link XmlElementRef}

aoqi@0: *

aoqi@0: * The {@link XmlAnyElement} annotation can be used with {@link XmlElementRef}s to aoqi@0: * designate additional elements that can participate in the content tree. aoqi@0: * aoqi@0: *

aoqi@0: * The following schema would produce the following Java class: aoqi@0: *

aoqi@0:  * <xs:complexType name="foo">
aoqi@0:  *   <xs:choice maxOccurs="unbounded" minOccurs="0">
aoqi@0:  *     <xs:element name="a" type="xs:int" />
aoqi@0:  *     <xs:element name="b" type="xs:int" />
aoqi@0:  *     <xs:any namespace="##other" processContents="lax" />
aoqi@0:  *   </xs:choice>
aoqi@0:  * </xs:complexType>
aoqi@0:  * 
aoqi@0: * aoqi@0: *
aoqi@0:  * class Foo {
aoqi@0:  *   @{@link XmlAnyElement}(lax="true")
aoqi@0:  *   @{@link XmlElementRefs}({
aoqi@0:  *     @{@link XmlElementRef}(name="a", type="JAXBElement.class")
aoqi@0:  *     @{@link XmlElementRef}(name="b", type="JAXBElement.class")
aoqi@0:  *   })
aoqi@0:  *   {@link List}<{@link Object}> others;
aoqi@0:  * }
aoqi@0:  *
aoqi@0:  * @XmlRegistry
aoqi@0:  * class ObjectFactory {
aoqi@0:  *   ...
aoqi@0:  *   @XmlElementDecl(name = "a", namespace = "", scope = Foo.class)
aoqi@0:  *   {@link JAXBElement}<Integer> createFooA( Integer i ) { ... }
aoqi@0:  *
aoqi@0:  *   @XmlElementDecl(name = "b", namespace = "", scope = Foo.class)
aoqi@0:  *   {@link JAXBElement}<Integer> createFooB( Integer i ) { ... }
aoqi@0:  * 
aoqi@0: * aoqi@0: * It can unmarshal instances like aoqi@0: * aoqi@0: *
aoqi@0:  * <foo xmlns:e="extra">
aoqi@0:  *   <a>1     // this will unmarshal to a {@link JAXBElement} instance whose value is 1.
aoqi@0:  *   <e:other />  // this will unmarshal to a DOM {@link Element}.
aoqi@0:  *   <b>3     // this will unmarshal to a {@link JAXBElement} instance whose value is 1.
aoqi@0:  * </foo>
aoqi@0:  * 
aoqi@0: * aoqi@0: * aoqi@0: * aoqi@0: * aoqi@0: *

W3C XML Schema "lax" wildcard emulation

aoqi@0: * The lax element of the annotation enables the emulation of the "lax" wildcard semantics. aoqi@0: * For example, when the Java source code is annotated like this: aoqi@0: *
aoqi@0:  * @{@link XmlRootElement}
aoqi@0:  * class Foo {
aoqi@0:  *   @XmlAnyElement(lax=true)
aoqi@0:  *   public {@link Object}[] others;
aoqi@0:  * }
aoqi@0:  * 
aoqi@0: * then the following document will unmarshal like this: aoqi@0: *
aoqi@0:  * <foo>
aoqi@0:  *   <unknown />
aoqi@0:  *   <foo />
aoqi@0:  * </foo>
aoqi@0:  *
aoqi@0:  * Foo foo = unmarshal();
aoqi@0:  * // 1 for 'unknown', another for 'foo'
aoqi@0:  * assert foo.others.length==2;
aoqi@0:  * // 'unknown' unmarshals to a DOM element
aoqi@0:  * assert foo.others[0] instanceof Element;
aoqi@0:  * // because of lax=true, the 'foo' element eagerly
aoqi@0:  * // unmarshals to a Foo object.
aoqi@0:  * assert foo.others[1] instanceof Foo;
aoqi@0:  * 
aoqi@0: * aoqi@0: * @author Kohsuke Kawaguchi aoqi@0: * @since JAXB2.0 aoqi@0: */ aoqi@0: @Retention(RUNTIME) aoqi@0: @Target({FIELD,METHOD}) aoqi@0: public @interface XmlAnyElement { aoqi@0: aoqi@0: /** aoqi@0: * Controls the unmarshaller behavior when it sees elements aoqi@0: * known to the current {@link JAXBContext}. aoqi@0: * aoqi@0: *

When false

aoqi@0: *

aoqi@0: * If false, all the elements that match the property will be unmarshalled aoqi@0: * to DOM, and the property will only contain DOM elements. aoqi@0: * aoqi@0: *

When true

aoqi@0: *

aoqi@0: * If true, when an element matches a property marked with {@link XmlAnyElement} aoqi@0: * is known to {@link JAXBContext} (for example, there's a class with aoqi@0: * {@link XmlRootElement} that has the same tag name, or there's aoqi@0: * {@link XmlElementDecl} that has the same tag name), aoqi@0: * the unmarshaller will eagerly unmarshal this element to the JAXB object, aoqi@0: * instead of unmarshalling it to DOM. Additionally, if the element is aoqi@0: * unknown but it has a known xsi:type, the unmarshaller eagerly unmarshals aoqi@0: * the element to a {@link JAXBElement}, with the unknown element name and aoqi@0: * the JAXBElement value is set to an instance of the JAXB mapping of the aoqi@0: * known xsi:type. aoqi@0: * aoqi@0: *

aoqi@0: * As a result, after the unmarshalling, the property can become heterogeneous; aoqi@0: * it can have both DOM nodes and some JAXB objects at the same time. aoqi@0: * aoqi@0: *

aoqi@0: * This can be used to emulate the "lax" wildcard semantics of the W3C XML Schema. aoqi@0: */ aoqi@0: boolean lax() default false; aoqi@0: aoqi@0: /** aoqi@0: * Specifies the {@link DomHandler} which is responsible for actually aoqi@0: * converting XML from/to a DOM-like data structure. aoqi@0: */ aoqi@0: Class value() default W3CDomHandler.class; aoqi@0: }