Как сопоставить свойство с Integer Mapstruct в Java - PullRequest
0 голосов
/ 17 октября 2019

У меня проблема с картографом mapstruct. При запуске mvn clean install (или mvn clean compile) я получаю следующие ошибки:

[ERROR] /mapper/EntityMapper.java:[28,7] Can't map property "java.util.List<com.socomec.tseselector.model.Source> architecture.sources
" to "java.lang.Integer architecture.sources". Consider to declare/implement a mapping method: "java.lang.Integer map(java.util.List<com.socomec.tseselector.model.Source> value)".
[ERROR] /mapper/command/TSEProjectCommandMapper.java:[21,16] Can't map property "java.lang.Integer architecture.loads" to "java.util.List<com.socomec.tseselector.model.Load> architecture.loads". Consider to declare/implement a mapping method: "java.util.List<com.socomec.tseselector.model.Load> map(java.lang.Integer value)".

Проблема в том, что я понятия не имею, откуда mapstruct получает этот "java.lang.Integer Architecture.loads" из,Я не понимаю, откуда исходит это Integer, как вы можете видеть, в моем коде нет Integer. Также до сих пор я никогда не сталкивался с этой ошибкой при использовании аналогичного маппера.

Вот моя сущность Архитектура:

public class Architecture {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;
    private String imagePath;

    @ManyToMany(cascade = CascadeType.ALL)
    @JoinTable(name="tse_architectures_loads",
            joinColumns = {@JoinColumn(table = "tse_architecture", name = "architecture_id")},
            inverseJoinColumns = {@JoinColumn(table = "tse_load", name = "load_id")}
    )
    private List<Load> loads;

    @ManyToMany(cascade = CascadeType.ALL)
    @JoinTable(name="tse_architectures_sources",
            joinColumns = {@JoinColumn(table = "tse_architecture", name = "architecture_id")},
            inverseJoinColumns = {@JoinColumn(table = "tse_source", name = "source_id")}
    )
    private List<Source> sources;

    private String techno;

    public Architecture() {
        this.loads = new ArrayList<>();
        this.sources = new ArrayList<>();
    }

DTO

public class ArchitectureDto {
    private Long id;
    private String name;
    private String imagePath;
    private List<LoadDto> loadDtos;
    private List<SourceDto> sourceDtos;
    private String techno;

    public ArchitectureDto() {
        this.loadDtos = new ArrayList<>();
        this.sourceDtos = new ArrayList<>();
    }
}

Мой маппер:

@Mapper(componentModel = "spring")
public interface ArchitectureMapper extends EntityMapper<ArchitectureDto, Architecture> {

    @Mapping(source = "loads", target = "loadDtos")
    @Mapping(source = "sources", target = "sourceDtos")
    ArchitectureDto toDto(Architecture architecture);
}

Entity Mapper:

public interface EntityMapper<D, E> {

    /**
     * Map a DTO to an Entity
     *
     * @param dto the dto to map
     * @return an Entity
     */
    E toEntity(D dto);

    /**
     * Map an Entity to a DTO
     *
     * @param entity to map to a DTO
     * @return a DTO
     */
    D toDto(E entity);

    /**
     * Map a List of DTOs to a List of Entities
     *
     * @param dtoList the list to map
     * @return a list of Entities
     */
    List<E> toEntity(List<D> dtoList);

    /**
     * Map a list of Entities to a list of DTOs
     *
     * @param entityList the list to map
     * @return a list of DTOs
     */
    List<D> toDto(List<E> entityList);
}

Просматривая документацию и другие вопросы о mapstruct здесь, я пока не смог найти решение.

Я добавляю свои загрузки и исходные классы. Загрузка:

public class Load {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    private String name;
    private String type;
    private String unity;
    private Long sourcePriority1;
    private Long SourcePriority2;
    private Long SourcePriority3;
    private Long kvaValue;
    private Long kwValue;
    private Long pfValue;
    private Long aValue;
    private Long iccValue;

    @JsonIgnore
    @ManyToMany(mappedBy = "loads")
    private List<TSEProject> tseProjects;

    @JsonIgnore
    @ManyToMany(mappedBy = "loadList")
    private List<Architecture> architectures;

    public Load() {
        this.architectures = new ArrayList<>();
        this.tseProjects = new ArrayList<>();
    }

Источник:

public class Source {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    private String name;
    private String type;
    private String unity;
    private Long quantity;
    private Long kvaValue;
    private Long kwValue;
    private Long pfValue;
    private Long aValue;

    @JsonIgnore
    @ManyToMany(mappedBy = "sources")
    private List<TSEProject> tseProjects;

    @JsonIgnore
    @ManyToMany(mappedBy = "sourceList")
    private List<Architecture> architectures;

    public Source() {
        this.architectures = new ArrayList<>();
        this.tseProjects = new ArrayList<>();
    }

}

и DTO

@Data
public class LoadDto {
    private Long id;
    private String name;
    private String type;
    private String unity;
    private Long sourcePriority1;
    private Long SourcePriority2;
    private Long SourcePriority3;
    private Long kvaValue;
    private Long kwValue;
    private Long pfValue;
    private Long aValue;
    private Long iccValue;
    private List<Long> tseProjectsId;

    public LoadDto() {
        this.tseProjectsId = new ArrayList<>();
    }

}
@Data
public class SourceDto {

    private Long id;
    private String name;
    private String type;
    private String unity;
    private Long quantity;
    private Long kvaValue;
    private Long kwValue;
    private Long pfValue;
    private Long aValue;

}

1 Ответ

0 голосов
/ 10 ноября 2019

Полагаю, вам нужно еще немного устранить неполадки. Попробуйте помочь MapStruct и определите дополнительный метод отображения следующим образом:

Mapper(componentModel = "spring")
public interface ArchitectureMapper extends EntityMapper<ArchitectureDto, Architecture> {

    @Mapping(source = "loads", target = "loadDtos")
    @Mapping(source = "sources", target = "sourceDtos")
    ArchitectureDto toDto(Architecture architecture);

    // first try with all properties ignored
    // @Mapping( target = "id", ignore = true ) etc.
    SourceDto toDto(Source source);

    // first try with all properties ignored
    // @Mapping( target = "id", ignore = true ) etc.
    LoadDto toDto(Load load);

}

Проблема заключается в том, что MapStruct пытается сопоставить эти объекты автоматически на основе свойства. имена. Если он где-то обнаруживает то же имя, он пытается выполнить преобразование типа или использовать существующие методы отображения для выполнения своей работы. Он даже пытается выполнить 2 шага (то есть преобразование, а затем метод), что иногда приводит к этим результатам.

Вы можете предоставить некоторые сопоставления, которые MapStruct пытается сгенерировать сам, а затем снова игнорировать все свойства, как указано в примере. выше. Один за другим удалите строки игнорирования и посмотрите, когда MapStruct начнет жаловаться.

Если это снова граф объектов, вы можете применить похожую стратегию.

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

...