2014-12-22 2 views
1

У меня есть проблема понимания Xstream-конвертера.xstream unserialize complex XML для упрощения java с конвертером

У меня довольно сложный XML, исходящий из старого приложения для бэк-офиса и просто хочу преобразовать его в более простой класс Java или карту с конвертером.

  1. Я не хочу, чтобы мобилизовывать в XML, просто распаковать
  2. Я не хочу использовать аннотацию, просто ПОЦЕЛУЙ

Мой XML похож

<root> 
    <agent> 
     <id>123456789</id> 
     <name>GABIN</name> 
     <forname>Jean</forname> 
     <unit> 
      <legacyReference>AA</legacyReference> 
      <name>SAN ANTONIO</name> 
      <legacyName>SA</legacyName> 
      <address> 
       <number>1</number> 
       <street>Sesam street</street> 
       <city>NoWhere</city> 
       <legacyID>AAZE-56</legacyID> 
      </address> 
      <legacyStructurBlablabla> 
       <type>OFFICE</type> 
       <data> 
        <foo>BAR</foo> 
       </data> 
      </legacyStructurBlablabla> 
      <...> 
     </unit> 
     <...> 
    </agent> 
</root> 

Мой пункт назначения очень прост

class Agent { 
    String id; 
    String name; 
    String forname; 
    String unitName; 
    String unitType; 
    <...> 

} 

Мой главный метод выглядит

xStream = new XStream(new DomDriver()); 
stream = this.getClass().getClassLoader().getResourceAsStream("data/agent.xml") ; 
xStream.alias("root", Map.class); 
xStream.alias("agent", Agent.class); 
xStream.registerConverter(new ResultConverter()); 
xStream.registerConverter(new AgentConverter()); 
xStream.ignoreUnknownElements(); 

Object obj = xStream.fromXML(stream); 

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

public class ResultConverter implements Converter { 

... 


public Object unmarshal(HierarchicalStreamReader reader, 
     UnmarshallingContext context) { 
    Map<String, Object> agents = new HashMap<String, Object>(); 
    while(reader.hasMoreChildren()) { 
     reader.moveDown(); 
     // HOW I DO TO STEP DOWN IN FAVOR OF Agent CONVERTER ? 
     reader.moveUp(); 
    } 
    return agents; 
} 

Я не видел, чтобы Xstream прокручивал иерархию, чтобы активировать мой AgentConverter.

Я, конечно, не хватает точки

EDIT

Xstream может быть не Чет правильный инструмент для этого. Я бы использовал xmlbeam, в соответствии с рекомендациями Cfx. XMLBeam проектов XML-класс Java в соответствии с отображением XPATH.

ответ

1

Кажется, вы хотите, чтобы структура xml не отражалась в вашем классе Java. Если вы придерживаетесь XStream, у меня нет решения. Но есть alternative framework, который был создан для решения именно этой проблемы. Он использует аннотации, но IMHO не нарушает принцип KISS. Вот пример:

public interface Agent { 

@XBRead("/root/agent/id") 
String getId(); 

@XBRead("/root/agent/name") 
String getName(); 

@XBRead("/root/agent/forename") 
String getForname(); 

@XBRead("/root/agent/unit/name") 
String getUnitName(); 

@XBRead("/root/agent/unit/legacyStructurBlablabla/type") 
String getUnitType(); 

}

Вы будете определять интерфейсы вместо классов, но экземпляры этих интерфейсов полезные так же, как POJOs. (с toString(), equals(), hashCode, ...). Создание экземпляров этих интерфейсов выглядит так:

Agent agent = new XBProjector().io().stream(stream).read(Agent.class); 
+0

Хороший ответ. Вы правы, это может быть правильным решением для моей проблемы. Я попробую http://xmlbeam.org/. Спасибо – MarcDeXeT

+0

Я пробовал, и мне это нравится. – MarcDeXeT

+0

Но должен ли я использовать промежуточный интерфейс для поддержки списка элементов? как открытый интерфейс AgentList { @XBRead ("/ root/agent") public List getAgents(); } – MarcDeXeT