En general, a Dozer le gusta mapear, especialmente en cuanto a las estructuras de datos. Esto hace que tu problema sea complicado.
Sin duda ha leído sobre la asignación de java.util.Map a java.util.Map. Eso funciona muy bien si tienes Maps en ambos extremos. Desafortunadamente, no todos los reyes, todos los reyes, ni todos los reyes, te ayudarán con la conversión de java.util.Map a java.util.List. Dozer quiere Map.get (clave) desde el origen y Map.put (clave, valor) en el destino. Dado que List no juega en el juego de poner, estás atorado (no pude falsificarlo con un 'add()' ... ¿tal vez hay una manera?).
En la parte inferior de http://dozer.sourceforge.net/documentation/customconverter.html hay una sección sobre "Conversiones de estructura de datos", que parece parecerse a su problema. Cuando la respuesta es "escribir un mapa personalizado", probablemente no estoy siendo de gran ayuda, pero conseguí que tu código funcione con la siguiente configuración.
¿Has tenido un poco de suerte al hacer esto todo en dozer xml?
<mapping>
<class-a>Source</class-a>
<class-b>Destination</class-b>
<field custom-converter="HashMapToListConverter">
<a>dtos</a> <!-- This is a Map<String,DTO> -->
<b>dtos</b> <!-- This is a List<DTOPrime> -->
<a-hint>java.util.LinkedHashMap</a-hint>
<b-hint>java.util.ArrayList</b-hint>
</field>
</mapping>
import org.dozer.*;
import java.util.*;
public class HashMapToListConverter extends DozerConverter<Map, List> implements MapperAware {
private Mapper mapper;
public HashMapToListConverter() {
super(Map.class, List.class);
}
public List convertTo(Map source, List destination) {
List<DTOPrime> convertedList = new ArrayList<DTOPrime>();
for (Object object : source.values()) {
DTO item = (DTO)object;
DTOPrime mappedItem = mapper.map(item, DTOPrime.class);
convertedList.add(mappedItem);
}
return convertedList;
}
public Map convertFrom(List source, Map destination) {
Map<String, DTO> originalToMapped = new LinkedHashMap<String, DTO>();
for (Object object : source) {
DTOPrime item = (DTOPrime)object;
DTO mappedItem = mapper.map(item, DTO.class);
originalToMapped.put(mappedItem.getData(), mappedItem); // FIXME: Since the mapping is lossy, you can decide what the keys of your map are for the reverse mapping...
}
return originalToMapped;
}
public void setMapper(Mapper mapper) {
this.mapper = mapper;
}
}
Una respuesta melancolía; Esperaba que hubiera una manera más simple, pero eso es exactamente lo que terminé haciendo. Me pregunto cuántos otros han hecho lo mismo. – Idcmp