incompletablefuture
incompletablefuture

Reputation: 124

Set the value of LocalDateTime.now() to two fields while mapping by ModelMapper

I have to map my DTO which I am getting from UI to my entity by ModelMapper.

Before using ModelMapper I had this method:

private Operation map(OperationForm src) {
    Operation operation = new Operation();
    LocalDateTime NOW = LocalDateTime.now();
    operation.setOperationKey(OperationKey.of(src.getLegalEntityId(), 
                             src.getEmployeeId(), 
                             NOW));  // here
    operation.setIndividualId(src.getIndividualId());
    operation.setKey(src.getLegalEntityId() + "_" 
                     + src.getEmployeeId() + "_" 
                     + NOW);         // and here

    return operation;
}

In this case I have to generate new LocalDateTime by LocalDateTime.now() and use it in two different fields.

So, I tried to configure ModelMapper like that:

public OperationFormMapper(ModelMapper modelMapper) {
    Converter<OperationForm, OperationKey> operationKeyConverter = (context) -> OperationKey.of(context.getSource().getLegalEntityId(), 
                context.getSource().getEmployeeId(), 
                LocalDateTime.now()); // generate new LocalDateTime to 
                                      // destination instance

    Converter<Operation, String> keyConverter = (context) -> {
        Operation src = context.getSource();
        return src.getOperationKey().getLegalEntityId() + "_" 
               + src.getOperationKey().getEmployeeId() + "_" 
               + src.getOperationKey().getOperationDate();
    }; // converter for my purpose
       // I am trying to get value not from source, 
       // but from destination instance, hoping that 
       // all needed fields are already mapped

    this.modelMapper = modelMapper;

    this.modelMapper.addMappings(new PropertyMap<OperationForm, Operation>() {

        @Override
        protected void configure() {
            using(operationKeyConverter).map(source, destination.getOperationKey());
            map().setIndividualId(source.getIndividualId());
            map().setOperationStatus(Operation.OperationStatus.CREATED);

            using(keyConverter).map(destination, destination.getKey()); 
            // trying to get all needed data from already mapped fields
        }
    });
}

It wasn't a surprise that it hadn't worked. I got NullPointerException. Apparently, fields are still not mapped in the moment I am trying to get their values for Key field.

So, does anybody know how to handle this moment and make ModelMapper work also for my case? Or maybe at least there are some ways to fully customize mapping process and create the whole method which will be used by ModelMapper for mapping(or make it use my existing one from above)?

UPDATED:

My entity:

public class Operation {
    private OperationKey operationKey;
    private Long individualId;
    private String operationStatus;
    private String operationResult;
    private String guardCardSeries;
    private String guardCardNumber;
    private LocalDateTime guardCardStartDate;
    private LocalDateTime guardCardEndDate;
    private String resultMessage;
    private String key;
}

My DTO from UI:

public class OperationForm implements Serializable {
    private Long legalEntityId;
    private Long employeeId;
    private Long individualId;
}

My composite key for Cassandra DB:

public class OperationKey {
    private final Long legalEntityId;
    private final Long employeeId;
    private final LocalDateTime operationDate;
}

I simplified them a little bit just by removing persistence annotations.

Upvotes: 0

Views: 731

Answers (1)

incompletablefuture
incompletablefuture

Reputation: 124

Seems like I found a solution for me.

My configuration for ModelMapper now.

public OperationFormMapper(ModelMapper modelMapper) {
        this.modelMapper = modelMapper;

        Converter<OperationForm, Operation> converter = context -> {
            OperationForm src = context.getSource();
            Operation dest = new Operation();

            final LocalDateTime NOW = LocalDateTime.now();
            dest.setOperationKey(OperationKey.of(src.getLegalEntityId(), src.getEmployeeId(), NOW));
            dest.setIndividualId(src.getIndividualId());
            dest.setKey(src.getLegalEntityId() + "_" + src.getEmployeeId() + "_" + NOW);

            return dest;
        };

        this.modelMapper.addConverter(converter);
    }

I created Converter and pushed my method into it. Now it works.

Upvotes: 1

Related Questions