Reputation: 11
I've searched a lot in this forum and other websites, but I'm still stuck with my problem.
I'm actually using modelmapper to convert an entity to a DTO.
Here is the Entity :
@Entity
public class Candidate implements Serializable {
@Id
@GeneratedValue (strategy=GenerationType.IDENTITY)
@Column(name = "id")
private Long id;
@Column (name = "name")
private String lastname;
@Column (name = "firstname")
private String firstname;
@Column (name = "phone")
private String phoneNumber;
@Column (name = "mail")
private String email;
@Column (name = "title")
private int title;
@OneToMany (mappedBy = "candidateId")
private Collection<Candidature> Interviews;
Here is Candidature Entity (that you find in the first Entity's collection):
public class Candidature implements Serializable {
@Id
@NotBlank
@GeneratedValue(strategy=GenerationType.IDENTITY)
@Column(name="id")
private Long id;
@ManyToOne (fetch = FetchType.LAZY)
@JoinColumn (name = "candidat_id")
private Candidate candidateId;
@Column(name = "interview")
@Temporal (TemporalType.DATE)
private Date dateInterview;
@Column(name ="status")
private String status;
And here is the DTO :
public class CandidateDTO {
private Long id;
private String lastname;
private String firstname;
private String phoneNumber;
private String email;
private String title;
private String dateLastInterview;
As you can see, there are some differences.
The problem I face is that the last attribute of DTO (dateLastInterview
) comes from the Collection<Candidature>
and more precisely it must be the last dateInterview
converted into String.
Convert a Date into String is not a problem. Getting the last item of a Collection neither.
But I can't make it work with modelMapper. Here is a sample code I tried :
modelMapper = new ModelMapper();
Converter<Candidate, CandidateDTO> converter = new Converter<Candidate, CandidateDTO>()
{
@Override
public CandidateDTO convert(MappingContext<Candidate, CandidateDTO> mappingContext) {
Candidate candidate = mappingContext.getSource();
CandidateDTO cdto = new CandidateDTO();
List<Candidature> list = (List) candidate.getInterviews();
Date date = list.get(list.size()-1).getDateInterview();
DateFormat df = new SimpleDateFormat("yyyy-MM-dd");
String dateInterviewConverted = df.format(date);
mappingContext.getDestination().setTitle(mappingContext.getSource().getTitle());
mappingContext.getDestination().setDateLastInterview(dateInterviewConverted);
return cdto;
}
};
modelMapper.createTypeMap(Candidate.class, CandidateDTO.class).setConverter(converter);
(and I tried, instead of the last line above : modelMapper.addConverter(converter);
but same result)
But it doesn't work, I get all attributes at null.
I previously succeded using
map().setTitle(source.getTitle());
map().setDateLastInterview(dateInterviewConverted);
And then converting the Date to String in my DTO "set" method, but it seems that it shouldn't be here, but into the ModelMapper class or the class that is using it.
Do you have an idea ? I'm new with modelMapper, and I keep browsing google and I can't find (or maybe understand ?) any response that might help me.
Thanks
Upvotes: 0
Views: 4472
Reputation: 11
Ok I think I succeded. Using the converter was the right thing, but I wasn't using it correctly. For the converter, the two objets that you put inside <> are the ones of the attributes concerned by the converter.
For example, for the first converter, I wanted to parameter the conversion of the Collection (coming from an object Candidate) to become a String (to match the attribute of the DTO).
So then you only have to create a PropertyMap with the Class and ClassDTO, and in the configure() method you only mention the attributes that will use special parameters (the other ones are correct since they respect the standard mapping).
Converter<Collection<Candidature>, String> convertLastDateToString = new Converter<Collection<Candidature>, String>() {
public String convert(MappingContext<Collection<Candidature>, String> context) {
List<Candidature> candidatureList = (List)context.getSource();
String dateInterviewConverted = "";
if (candidatureList.size() > 0) {
Date lastInterview = candidatureList.get(0).getDateInterview();
for (int i = 0; i < candidatureList.size(); i++) {
if (candidatureList.get(i).getDateInterview().after(lastInterview)) {
lastInterview = candidatureList.get(i).getDateInterview();
}
}
// converts the Date to String
DateFormat df = new SimpleDateFormat(DATE_FORMAT);
dateInterviewConverted = df.format(lastInterview);
}
return dateInterviewConverted;
}
};
// allows custom conversion for Title attribute
// the source (Candidate) has a title attribute in int type
// the destination (CandidateDTO) has a title attributes in String type
Converter<Integer, String> convertTitleToString = new Converter<Integer, String>(){
public String convert(MappingContext<Integer, String> context){
return Title.values()[context.getSource()].toString();
}
};
// define explicit mappings between source and destination properties
// does only concernes the attributes that will need custom mapping
PropertyMap<Candidate, CandidateDTO> candidateMapping = new PropertyMap<Candidate, CandidateDTO>()
{
protected void configure()
{
// to map these two attributes, they will use the corresponding converters
using(convertTitleToString).map(source.getTitle()).setTitle(null);
using(convertLastDateToString).map(source.getCandidatures()).setDateLastInterview(null);
}
};
// add the mapping settings to the ModelMapper
modelMapper.addMappings(candidateMapping);
Upvotes: 1