实体类使用@Builder,导致@ConfigurationProperties注入属性失败问题

 更新时间:2023年12月15日 14:57:33   作者:搏·梦  
这篇文章主要介绍了实体类使用@Builder,导致@ConfigurationProperties注入属性失败问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教

1. 前言

这里只是列出,可能需要补一下的知识点:

具体的yml文件字符串、List、Map的书写方式并使用@ConfigurationProperties注入配置类.

使用@Builder导致的无法创建无参构造方法

2. 场景

@ConfigurationProperties注入属性,有两个很重要的条件:

  • 该类必须是bean对象,即加了@Component注解。
  • 该类必须得有set方法,即加@Setter注解。

偶然一次发现,当在该类加上@Builder注解,会直接导致无法属性注入。

重现

正常情况下:

@ToString
@Setter
@Component
@ConfigurationProperties(prefix = "failed.test")
public class demoFailedTest {

    private String username;
    private int age;
    private demoPerson demoPerson;
}

@Setter
@ToString
public class demoPerson {
    private String name;
    private String sex;
}
@Component("demoFailedTestRunner")
public class demoRunner implements ApplicationRunner {

    @Autowired
    demoFailedTest demoFailedTest;

    @Override
    public void run(ApplicationArguments args) throws Exception {
        System.out.println(demoFailedTest);
    }
}

failed:
  test:
    user-name: failedTest
    age: 19
    demo-person:
      name: person
      sex: boy

异常情况:当在demoPerson类上加上@Builder注解:

@Builder
@Setter
@ToString
public class demoPerson {
    private String name;
    private String sex;
}

一开始都惊了,本来就是符合条件的,demoPerson类上面有set方法,不应该注入不进来。

3. 解释

1.上面两张图片有个输出有个很细微的差异,一开始我也没有看出来,后来才反应过来了:

第一个:

demoFailedTest(username=failedTest, age=19, demoPerson=demoPerson(name=person, sex=boy))

第二个:

demoFailedTest(username=failedTest, age=19, demoPerson=null)

注: demoPerson类上 加了@ToString

讲道理,第二个报错不应该是:

demoFailedTest(username=failedTest, age=19, demoPerson=demoPerson(name=null, sex=null))

这样子才是真正注入不进来属性的结果。

那么现在直接 demoPerson=null 代表 该demoPerson根本没有被创建对象!!!

2.后来详细去了解了@Builder注解的作用:

详细:使用@Builder导致的无法创建无参构造方法

简单说一下:就是如果你只是使用了@Builder则会导致 该类的没有无参构造函数,会有全参构造函数

3.重点:spring属性注入的时候,为什么要有set方法,显示它是使用set方法注入的,它又不能直接使用对象.set方法(),想必是使用了反射,那就必须得有对象吧,可得 spring肯定是先反射创建对象,是的,没错,spring默认是使用无参构造函数创建对象,再调用反射的set方法。

4.因此,如果加上@Builder注解,会没有无参构造函数方法,当然是没有办法创建对象了,因此才会出现 demoPerson=null的结果

4. 解决方法

具体@Builder的解决方法,上面链接里面有三种,我演示其中一种,即在该类上加上@AllArgsConstructor@NoArgsConstructor。

@ToString
@Setter
@Builder
@AllArgsConstructor
@NoArgsConstructor
public class demoPerson {
    private String name;
    private String sex;

}

5. 思考

根据第四大点的解决方法,加上@AllArgsConstructor、@NoArgsConstructor即可,但有没有想过为什么要用@Builder方法

原因:

  • builder创建对象方式很优雅,写的很简洁。
  • 有没有一种可能,就是需求就是不想对外提供默认无参构造方法,或者全参构造方法,不想别人随便就可以new 对象出来了。

如果要满足第二点原因,显然现在是无法做到的,因为spring使用set方法注入,得有无参构造方法先创建对象,但是我们又不想提供无参构造方法,这不是矛盾吗?

再额外补充一个问题:如果这个Person类,我只想通过配置文件注入之后,永远不被修改,固然不能提供set方法,但是因为spring使用set方法注入属性,这不也是矛盾吗?

此时,突然脑子里面肯定会出现一个想法:为什么只会有set方法注入,不应该吧,set都可以,应该也可以有构造函数注入吧。

是的,下一篇文章:

spring的构造函数注入属性@ConstructorBinding 

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。

相关文章

  • 微信随机生成红包金额算法java版

    微信随机生成红包金额算法java版

    这篇文章主要为大家详细介绍了java和php版的微信随机生成红包金额算法,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2016-07-07
  • JAVA基于Slack实现异常日志报警详解

    JAVA基于Slack实现异常日志报警详解

    这篇文章主要为大家介绍了JAVA基于Slack实现异常日志报警详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-08-08
  • 关于SpringCloud整合RabbitMQ的实例

    关于SpringCloud整合RabbitMQ的实例

    这篇文章主要介绍了关于SpringCloud整合RabbitMQ的实例,消息队列是指利用高效可靠的消息传递机制进行与平台无关的数据交流,并基于数据通信来进行分布式系统的集成,是在消息的传输过程中保存消息的容器,需要的朋友可以参考下
    2023-07-07
  • ScrollView中嵌入ListView只显示一条的解决办法

    ScrollView中嵌入ListView只显示一条的解决办法

    在ScrollView添加一个ListView会导致listview控件显示不全,通常只会显示一条,究竟是什么原因呢?下面脚本之家小编给大家介绍ScrollView中嵌入ListView只显示一条的解决办法,感兴趣的朋友一起学习吧
    2016-05-05
  • GSON实现Java对象的JSON序列化与反序列化的实例教程

    GSON实现Java对象的JSON序列化与反序列化的实例教程

    GSON是Google开发并开源的一个Java的JSON转换库,这里我们将来讲解GSON实现Java对象的JSON序列化与反序列化的实例教程,需要的朋友可以参考下
    2016-06-06
  • springmvc如何使用map接收参数

    springmvc如何使用map接收参数

    这篇文章主要介绍了springmvc如何使用map接收参数的操作,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2021-10-10
  • 后端如何接收格式为x-www-form-urlencoded的数据

    后端如何接收格式为x-www-form-urlencoded的数据

    x-www-form-urlencoded格式是一种常见的HTTP请求数据格式,它将请求参数编码为键值对的形式,以便于传输和解析,下面这篇文章主要给大家介绍了关于后端如何接收格式为x-www-form-urlencoded的数据,需要的朋友可以参考下
    2023-05-05
  • Jmeter post上传文件实现过程详解

    Jmeter post上传文件实现过程详解

    这篇文章主要介绍了Jmeter post上传文件实现过程详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2020-08-08
  • 详解SpringCloud Finchley Gateway 统一异常处理

    详解SpringCloud Finchley Gateway 统一异常处理

    这篇文章主要介绍了详解SpringCloud Finchley Gateway 统一异常处理,非常具有实用价值,需要的朋友可以参考下
    2018-10-10
  • 自带IDEA插件的阿里开源诊断神器Arthas线上项目BUG调试

    自带IDEA插件的阿里开源诊断神器Arthas线上项目BUG调试

    这篇文章主要为大家介绍了自带IDEA插件阿里开源诊断神器Arthas线上项目BUG调试,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-06-06

最新评论