Мне нужно проанализировать огромный xml, используя SAX, и демонтировать отдельные известные элементы, используя jaxb.Если я отменяю маршализацию корневого компонента, имеющего List
с @XmlAnyElement(lax=true)
, все в порядке: известные теги преобразуются в классы, известные JAXBContext, а неизвестные теги становятся экземплярами DOM Element
.
Однако, если япропустите корневой элемент и удалите отдельные объекты, первый неизвестный тег вызывает исключение unexpected element
.Если я вызываю unmarshal()
с явным Object.class
, то даже известные теги становятся JAXBElement
.
Вывод:
<Root>
<Header/>
<Product/>
<Product/>
<Product/>
<Product/>
<Product/>
<Unknown/>
</Root>
class com.common.config.Problem$Header
class com.common.config.Problem$Product
class com.common.config.Problem$Product
class com.common.config.Problem$Product
class com.common.config.Problem$Product
class com.common.config.Problem$Product
Exception in thread "main" javax.xml.bind.UnmarshalException
- with linked exception:
[com.sun.istack.internal.SAXParseException2; lineNumber: 8; columnNumber: 15; unexpected element (uri:"", local:"Unknown"). Expected elements are <{}Header>,<{}Product>]
Я хочу, чтобы он откатился до JAXBElement
или Element
.Является ли это возможным?код:
import java.io.StringReader;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.Unmarshaller;
import javax.xml.bind.annotation.XmlRootElement;
import javax.xml.stream.XMLInputFactory;
import javax.xml.stream.XMLStreamReader;
//@XmlRootElement(name = "Root")
//@XmlAccessorType(XmlAccessType.FIELD)
public class Problem {
//@XmlAnyElement(lax = true)
//protected final List<Object> accounts = new ArrayList<Object>();
public static void main(final String[] args) throws Exception {
System.err.println(XML);
final JAXBContext jaxbContext = JAXBContext.newInstance(Header.class, Product.class);
final Unmarshaller unm = jaxbContext.createUnmarshaller();
XMLStreamReader reader = XMLInputFactory.newInstance().createXMLStreamReader(new StringReader(XML));
boolean skipNext = false;
int event = 0;
boolean rootElSkipped = false;
while (reader.hasNext()) {
if (!skipNext) {
event = reader.next();
}
if (event == XMLStreamReader.START_ELEMENT) {
if (rootElSkipped) {
Object obj = unm.unmarshal(reader);
System.err.println(obj.getClass());
} else {
}
rootElSkipped = true;
}
}
}
static final String XML = "<Root>\r\n" + " <Header/>\r\n" + " <Product/>\r\n" + " <Product/>\r\n"
+ " <Product/>\r\n" + " <Product/>\r\n" + " <Product/>\r\n" + " <Unknown/>\r\n" + "</Root>\r\n"
+ "\r\n" + "";
@XmlRootElement(name = "Header")
public static class Header {
}
@XmlRootElement(name = "Product")
public static class Product {
}
}