2013-07-15 3 views
1

У меня есть ситуация, когда у меня есть 2 структурно разных XML-файла, мне нужно извлечь данные из них (в то время как только XML нужно разобрать) и отправить его на некоторую логику, а затем заполнить общий формат.mapping structurally differnt xml to to common java object

<xml1> 
    <a>hello</a> 
    <b>shreyas</b> 
    <c>123</c> 
</xml1> 

и

<xml2> 
    <d> 
     <name> 
      <my>hello</my> 
     </name> 
    </d> 
    <e>shreyas</e> 
    <f>124</f> 
</xml2> 

и общий объект для заполнения

public class Gobj { 

    String fName; 
    String lName; 
    String id; 
} 

я искал какое-то время выполнения аннотаций распознавателя. Я попытался с JaxbIntros, реализованным Jboss поверх Jaxb, но я не смог найти поддержку xpath для него.

Также эта проблема может быть решена с использованием базового анализатора SAX, но мне нужен какой-то метод, например, jaxb и т. Д.. где читаемость кода может быть легкой.

-Спасибо Shreyas

ответ

1

Примечание: Я EclipseLink JAXB (MOXy) свинца и член группы экспертов JAXB (JSR-222).

Ниже приведен пример того, как вы могли бы поддержать этот прецедент, используя расширение внешнего файла MOXy.

Метаданные для XML 1

Мы будем использовать стандартные аннотации JAXB для отображения Gobj класса первого представления XML.

package forum17652921; 

import javax.xml.bind.annotation.*; 

@XmlRootElement(name="xml1") 
@XmlAccessorType(XmlAccessType.FIELD) 
public class Gobj { 

    @XmlElement(name="a") 
    String fName; 

    @XmlElement(name="b") 
    String lName; 

    @XmlElement(name="c") 
    String id; 

} 

Метаданные XML 2

Мы будем использовать внешнее отображение документа Moxy на карту того же класса на втором представлении XML. По умолчанию документ сопоставления используется для увеличения метаданных, предоставленных аннотациями. Если мы установим флаг xml-metadata-complete в значение true, вы можете полностью заменить эти метаданные.

<?xml version="1.0"?> 
<xml-bindings 
    xmlns="http://www.eclipse.org/eclipselink/xsds/persistence/oxm" 
    package-name="forum17652921" 
    xml-accessor-type="FIELD" 
    xml-mapping-metadata-complete="true"> 
    <java-types> 
     <java-type name="Gobj"> 
      <xml-root-element name="xml2"/> 
      <java-attributes> 
       <xml-element java-attribute="fName" xml-path="d/name/my/text()"/> 
       <xml-element java-attribute="lName" name="e"/> 
       <xml-element java-attribute="id" name="f"/> 
      </java-attributes> 
     </java-type> 
    </java-types> 
</xml-bindings> 

Demo

В демо-коде ниже есть два экземпляра JAXBContext. Мы будем использовать первое, чтобы прочитать XML-представление 1, к экземпляру Gobj. Затем мы будем использовать второй JAXBContext для маршалирования того же экземпляра Gobj ко второму представлению XML.

package forum17652921; 

import java.io.File; 
import java.util.*; 
import javax.xml.bind.*; 
import org.eclipse.persistence.jaxb.JAXBContextProperties; 

public class Demo { 

    public static void main(String[] args) throws Exception { 
     JAXBContext jc1 = JAXBContext.newInstance(Gobj.class); 

     Unmarshaller unmarshaller = jc1.createUnmarshaller(); 
     File xml = new File("src/forum17652921/xml1.xml"); 
     Gobj gobj = (Gobj) unmarshaller.unmarshal(xml); 

     Map<String, Object> properties = new HashMap<String, Object>(1); 
     properties.put(JAXBContextProperties.OXM_METADATA_SOURCE, "forum17652921/oxm.xml"); 
     JAXBContext jc2 = JAXBContext.newInstance(new Class[] {Gobj.class}, properties); 

     Marshaller marshaller = jc2.createMarshaller(); 
     marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); 
     marshaller.marshal(gobj, System.out); 
    } 

} 

xml1.XML

<xml1> 
    <a>hello</a> 
    <b>shreyas</b> 
    <c>123</c> 
</xml1> 

Выход

<?xml version="1.0" encoding="UTF-8"?> 
<xml2> 
    <d> 
     <name> 
     <my>hello</my> 
     </name> 
    </d> 
    <e>shreyas</e> 
    <f>123</f> 
</xml2> 

Для получения более подробной информации

+1

Чрезвычайно много блейза, это именно то, что мне нужно –

+0

Чрезвычайно много блейза, я пробовал то же самое в своей среде, но я получаю «javax.xml.bind.JAXBException: свойство» eclipselink.oxm.metadata-source «не поддерживается». –

+0

Я создал jaxb.properties и разместил его по моим классам моделей, я думаю, он не подбирается. я все равно получаю то же самое не поддерживаемое исключение. –