Mapstruct:对所有枚举使用相同的映射器
Mapstruct: Using same mapper for all enums
我试图将所有 enums
映射到同一个 DTO class,我想避免为每个 enum
类型声明一种方法,或使用 @Mapping
对于每个枚举字段。
@Mapper
public interface EnumDtoMapper
{
// approach one
default <E extends Enum<E>> EnumDTO enumToEnumDTO(Enum<E> e)
{
if (e == null)
{
return null;
}
EnumDTO enumDTO = new EnumDTO();
enumDTO.setName(e.name());
return enumDTO;
}
//approach two: enum -> String -> EnumDTO
default <E extends Enum<E>> String enumToString(Enum<E> e)
{
return e.name();
}
default EnumDTO stringToEumDTO(String name)
{
EnumDTO enumDTO = new EnumDTO();
enumDTO.setName(name);
return enumDTO;
}
}
然后在我的其他 Mappers 上
@Mapper(componentModel = "cdi", injectionStrategy = InjectionStrategy.CONSTRUCTOR, uses = {
EnumDtoMapper.class
})
但是 MapStruct 仍在为每个枚举类型生成新的映射方法,实现不符合我的需要。
有没有办法用 MapStruct 做到这一点?还是魔法太多了? :D
做了一些测试,没有将 componentModel 设置为 cdi
你所拥有的会产生你所期望的。
但是有了它,你需要通配输入的通用类型enum
,之后它应该可以工作。
例子
如果 EnumUtil 看起来像这样:
class EnumUtil {
static EnumDto enumToEnumDTO(Enum<?> e) {
if ( e == null ) {
return null;
}
EnumDto enumDTO = new EnumDto( e.name() );
return enumDTO;
}
// approach two: enum -> String -> EnumDTO
static String enumToString(Enum<?> e) {
return e.name();
}
static EnumDto stringToEumDTO(String name) {
return new EnumDto( name );
}
}
使用以下映射器和 类:
@Mapper( componentModel = ComponentModel.CDI,
injectionStrategy = InjectionStrategy.CONSTRUCTOR,
uses = {
EnumUtil.class
} )
public interface EnumMapper {
@Mapping( target = "value", source = "enumValue" )
DtoWithEnumDto map(SourceWithEnum source);
}
class SourceWithEnum {
private MyEnum enumValue;
// getter & setter
}
enum MyEnum {
SOMETHING, ELSE
}
class EnumDto {
private final String name;
// constructor and getter
}
class DtoWithEnumDto {
private EnumDto value;
// constructor, getter and setter
}
您将获得以下生成的映射器:
@Generated(
value = "org.mapstruct.ap.MappingProcessor",
date = "2022-02-21T16:59:06+0100",
comments = "version: 1.4.2.Final, compiler: Eclipse JDT (IDE) 1.4.50.v20210914-1429, environment: Java 17.0.1 (Azul Systems, Inc.)"
)
@ApplicationScoped
public class EnumMapperImpl implements EnumMapper {
@Override
public DtoWithEnumDto map(SourceWithEnum source) {
if ( source == null ) {
return null;
}
EnumDto value = null;
value = EnumUtil.enumToEnumDTO( source.getEnumValue() );
DtoWithEnumDto dtoWithEnumDto = new DtoWithEnumDto( value );
return dtoWithEnumDto;
}
}
我试图将所有 enums
映射到同一个 DTO class,我想避免为每个 enum
类型声明一种方法,或使用 @Mapping
对于每个枚举字段。
@Mapper
public interface EnumDtoMapper
{
// approach one
default <E extends Enum<E>> EnumDTO enumToEnumDTO(Enum<E> e)
{
if (e == null)
{
return null;
}
EnumDTO enumDTO = new EnumDTO();
enumDTO.setName(e.name());
return enumDTO;
}
//approach two: enum -> String -> EnumDTO
default <E extends Enum<E>> String enumToString(Enum<E> e)
{
return e.name();
}
default EnumDTO stringToEumDTO(String name)
{
EnumDTO enumDTO = new EnumDTO();
enumDTO.setName(name);
return enumDTO;
}
}
然后在我的其他 Mappers 上
@Mapper(componentModel = "cdi", injectionStrategy = InjectionStrategy.CONSTRUCTOR, uses = {
EnumDtoMapper.class
})
但是 MapStruct 仍在为每个枚举类型生成新的映射方法,实现不符合我的需要。
有没有办法用 MapStruct 做到这一点?还是魔法太多了? :D
做了一些测试,没有将 componentModel 设置为 cdi
你所拥有的会产生你所期望的。
但是有了它,你需要通配输入的通用类型enum
,之后它应该可以工作。
例子
如果 EnumUtil 看起来像这样:
class EnumUtil {
static EnumDto enumToEnumDTO(Enum<?> e) {
if ( e == null ) {
return null;
}
EnumDto enumDTO = new EnumDto( e.name() );
return enumDTO;
}
// approach two: enum -> String -> EnumDTO
static String enumToString(Enum<?> e) {
return e.name();
}
static EnumDto stringToEumDTO(String name) {
return new EnumDto( name );
}
}
使用以下映射器和 类:
@Mapper( componentModel = ComponentModel.CDI,
injectionStrategy = InjectionStrategy.CONSTRUCTOR,
uses = {
EnumUtil.class
} )
public interface EnumMapper {
@Mapping( target = "value", source = "enumValue" )
DtoWithEnumDto map(SourceWithEnum source);
}
class SourceWithEnum {
private MyEnum enumValue;
// getter & setter
}
enum MyEnum {
SOMETHING, ELSE
}
class EnumDto {
private final String name;
// constructor and getter
}
class DtoWithEnumDto {
private EnumDto value;
// constructor, getter and setter
}
您将获得以下生成的映射器:
@Generated(
value = "org.mapstruct.ap.MappingProcessor",
date = "2022-02-21T16:59:06+0100",
comments = "version: 1.4.2.Final, compiler: Eclipse JDT (IDE) 1.4.50.v20210914-1429, environment: Java 17.0.1 (Azul Systems, Inc.)"
)
@ApplicationScoped
public class EnumMapperImpl implements EnumMapper {
@Override
public DtoWithEnumDto map(SourceWithEnum source) {
if ( source == null ) {
return null;
}
EnumDto value = null;
value = EnumUtil.enumToEnumDTO( source.getEnumValue() );
DtoWithEnumDto dtoWithEnumDto = new DtoWithEnumDto( value );
return dtoWithEnumDto;
}
}