springboot 注解属性转换字典

1.注解相关功能实现

  1. 定义属性注解

import com.fasterxml.jackson.annotation.JacksonAnnotationsInside;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.vehicle.manager.core.serializer.DicSerializer;


import java.lang.annotation.*;

/**
 * @author zr 2024/2/28
 */
@JacksonAnnotationsInside
@JsonSerialize(
        using = DicSerializer.class
)
@Target({ElementType.METHOD, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Dic {
    String code();
    String fieldName()default "";
}
  1. 定义字典序列化器

import com.fasterxml.jackson.databind.ser.ContextualSerializer;
import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.BeanProperty;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.vehicle.manager.core.annotation.Dic;
import org.springframework.util.StringUtils;

import java.io.IOException;
import java.util.Objects;

/**
 * @author zr 2024/2/28
 */

public class DicSerializer extends JsonSerializer<String> implements ContextualSerializer {

    private String code;
    private String fieldName;


    public DicSerializer(String code, String fieldName) {
        this.code = code;
        this.fieldName = fieldName;
    }

    public DicSerializer() {
    }

    @Override
    public void serialize(String s, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) throws IOException {
        jsonGenerator.writeString(s);
        jsonGenerator.writeFieldName(fieldName);
        //这一步是通过code(字典类型code)和value(字段转换前的值)获取name(字段转换后的值),
        String name = DicData.getNameByCodeAndValue(this.code,s);
        jsonGenerator.writeString(name);
    }

    @Override
    public JsonSerializer<?> createContextual(SerializerProvider serializerProvider, BeanProperty beanProperty) throws JsonMappingException {
        if(beanProperty !=null){
            if(Objects.equals (beanProperty.getType ().getRawClass (), String.class)){
                Dic t =beanProperty.getAnnotation (Dic.class);
                if(t !=null){
                    String beanFieldName = beanProperty.getName();
                    if(StringUtils.hasText(t.fieldName())){
                        beanFieldName = t.fieldName();
                    }
                    return new DicSerializer(t.code(),beanFieldName+"Text");
                }
            }
            return serializerProvider.findValueSerializer (beanProperty.getType (), beanProperty);
        }
        return serializerProvider.findNullValueSerializer (beanProperty);
    }
}
  1. 虚假的字典数据类


import java.util.HashMap;
import java.util.Map;

/**
 * 字典数据
 */
public class DicData {

    public static final Map<String, Map<Object,String>> dicData = new HashMap<>();
    static {
        //        todo 目前写死,可存入数据库或缓存
        //        车辆状态
        Map<Object,String> m1 = new HashMap();
        m1.put("0","初始化");
        dicData.put("carStatus",m1);
    }


    public static String  getNameByCodeAndValue(String code,String value){
        return dicData.get(code).get(value);
    }

}

2.功能测试

测试场景:

  1. 使用mybatis plus查询数据库car表,将数据封装到CarDO(Car)
  2. 在service层将CarDO转换为CarVo,同时将CarDO的status字段通过注解转换并生成一个新的字段statusText
  1. CarDO
import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.annotation.IdType;

import java.time.LocalDate;

import com.baomidou.mybatisplus.annotation.TableId;

import java.time.LocalDateTime;

import com.baomidou.mybatisplus.annotation.TableField;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.vehicle.manager.core.annotation.Dic;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.Accessors;

import java.io.Serializable;

/**
 * <p>
 * 车辆信息
 * </p>
 *
 * @author MybatisGenerator
 * @since 2024-02-21
 */
@TableName("car")
@ApiModel("车辆实体类")
@Data
//@Accessors(chain = true)
public class Car extends BaseEntity implements Serializable {
    private static final long serialVersionUID = 2781951723978392659L;

    /**
     * 自增id
     */
    @TableId(value = "id", type = IdType.AUTO)
    private Long id;
    
    // *****其他属性省略*****

    /**
     * 车辆状态
     */
    @TableField("status")
    private String status;
}

  1. CarVo

此处Vo属性上加上自定义注解@Dic

import com.fasterxml.jackson.annotation.JsonFormat;
import com.vehicle.manager.core.annotation.Dic;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.experimental.Accessors;

import java.io.Serializable;
import java.time.LocalDate;

/**
 * <p>
 * 车辆信息
 * </p>
 *
 * @author MybatisGenerator
 * @since 2024-02-21
 */
@ApiModel("车辆实体类")
@Data
@Accessors(chain = true)
public class CarVo extends BaseVo implements Serializable {
    private static final long serialVersionUID = 2781951723978392659L;

    /**
     * 自增id
     */
    @ApiModelProperty("自增id")
    private Long id;

   // *****其他属性省略*****

    /**
     * 车辆状态
     */
    @ApiModelProperty("车辆状态")
    @Dic(code = "carStatus")
    private String status;

}

  1. 相关service实现类(service接口我就不写了)
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.vehicle.manager.core.mapper.CarMapper;
import com.vehicle.manager.core.model.Result;
import com.vehicle.manager.core.model.dto.CarQueryDto;
import com.vehicle.manager.core.model.entity.Car;
import com.vehicle.manager.core.model.enumeration.CommonResultStatus;
import com.vehicle.manager.core.model.vo.CarVo;
import com.vehicle.manager.core.service.CarService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

/**
 * @author zr 2024/2/26
 */
@Service
public class CarServiceImpl implements CarService {
    @Autowired
    private CarMapper carMapper;
    
    @Override
    public Result page(CarQueryDto carQueryDto) {
        Page<Car> rowPage = new Page(carQueryDto.getPageNum(),carQueryDto.getPageSize());
        LambdaQueryWrapper<Car> queryWrapper = new LambdaQueryWrapper<>();
        Page<Car> carPage = carMapper.selectPage(rowPage, queryWrapper);
        IPage<CarVo> carVoIPage = carPage.convert(res -> getCarVo(res));
        return Result.success(carVoIPage);
    }
    
    /**
     * carDo 转 carVo
     * @param res
     * @return
     */
    private static CarVo getCarVo(Car res) {
        CarVo carVo = new CarVo();
        BeanUtils.copyProperties(res, carVo);
        return carVo;
    }
    /**
     * 通过id查询数据,并封装到carDo中
     */
    @Override
    public Result getById(Integer carId) {
        Car car = carMapper.selectById(carId);
        CarVo carVo = getCarVo(car);
        return Result.success(carVo);
    }

}

  1. 在48行打上断点debug

image.png

  1. 返回给前端的vo数据

可以看到通过注解生成了一个statusText字段,并且为字段中配置的转换后的值

image.png

  • 8
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Spring Boot中,我们经常使用注解来配置应用程序的各种属性。如果一个注解有一个boolean类型的属性,我们可以使用以下两种方法动态地指定该属性的值: 1. 使用SpEL表达式:在注解中使用SpEL表达式,这样属性的值将在应用程序启动时动态计算。例如: ```java @Autowired @Value("#{systemProperties['myBooleanProperty'] ?: true}") private boolean myBooleanProperty; ``` 上述代码中,@Value注解使用了SpEL表达式来设置myBooleanProperty属性的值。表达式中使用了systemProperties对象,该对象代表了系统属性。如果系统属性myBooleanProperty存在,则使用该属性值。否则,使用默认值true。 2. 使用@ConfigurationProperties注解:如果一个注解有多个boolean类型的属性,或者我们想将多个属性组合在一起,可以使用@ConfigurationProperties注解。该注解注解中的所有属性映射到一个JavaBean中。然后,我们可以在应用程序启动时从属性文件或环境变量中加载该JavaBean,并使用其中的属性。例如: ```java @Component @ConfigurationProperties(prefix = "myProperties") public class MyProperties { private boolean myBooleanProperty; public boolean isMyBooleanProperty() { return myBooleanProperty; } public void setMyBooleanProperty(boolean myBooleanProperty) { this.myBooleanProperty = myBooleanProperty; } } ``` 上述代码中,@ConfigurationProperties注解将myProperties前缀的属性映射到MyProperties类中。我们可以将该类注入到其他类中,并使用其中的属性。例如: ```java @Autowired private MyProperties myProperties; public void doSomething() { boolean myBooleanProperty = myProperties.isMyBooleanProperty(); // ... } ``` 在上述代码中,我们使用@Autowired注解将MyProperties类注入到当前类中,并使用其中的属性

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值