为什么@configurationproperties需要getter?

zbwhf8kr  于 2021-06-29  发布在  Java
关注(0)|答案(1)|浏览(454)

我在春靴里发现了一个奇怪的行为。
在yml文件中,我有以下配置:

main:
  record-id:
    start-position: 1
    value: 1
    enabled: true
  record-name:
    start-position: 2
    value: main
    enabled: true
  invented:
    start-position: 3
    value: 01012020
    enabled: false

下面是它的课程:

public class FieldType {
  private Integer startPosition;
  private String value;
  private Boolean enabled;
  getters/setters
}

@Component
@ConfigurationProperties(prefix = "main")
public class Main {
  private FieldType recordId;
  private FieldType recordName;
  private FieldType invented;
  getters/setters <-- sometimes without getters
}

如您所见,main类具有@configurationproperties注解,用于将属性从yml加载到该bean中。
我发现:
如果我没有为main类中的字段提供getter,那么有时main调用中的字段将保持为null,因此不会启动
如果我重新启动springboot,那么其他(1个或更多)字段将保持为空,因此不会启动
如果我重新启动springboot n次,那么,一次又一次,随机字段保持为空
如果我为主类中的字段提供getter,那么所有字段将始终从tye yml文件示例化,无论我重新启动springboot多少次
为什么会这样?为什么springboot需要表示yml中属性的字段的getter?

swvgeqrz

swvgeqrz1#

不需要getter来绑定属性,如果使用默认构造函数docs,则需要setter来绑定属性
如果初始化了嵌套的pojo属性(如前面示例中的安全字段),则不需要setter。如果希望绑定器使用其默认构造函数动态创建示例,则需要setter。
如果您正在初始化 FieldTypeMain 同学们,那么你们也不需要二传手了

@Component
@ConfigurationProperties(prefix = "main")
public class Main {
    private FieldType recordId = new FieldType();
    private FieldType recordName = new FieldType();
    private FieldType invented = new FieldType();

 }

还可以通过完全避免setter来使用构造函数绑定

public class FieldType {
   private Integer startPosition;
   private String value;
   private Boolean enabled;

   public FieldType(Integer startPosition, String value, Boolean enabled) {
         this.startPosition = startPosition;
         this.value = value;
         this.enabled = enabled

  }

  @ConstructorBinding
  @ConfigurationProperties(prefix = "main")
  public class Main {
       private FieldType recordId;
       private FieldType recordName;
       private FieldType invented;

  public Main(FieldType recordId,FieldType recordName,FieldType invented) {
       this.recordId = recordId;
       this.recordName = recordName;
       this.invented = invented;

  }

只是一个关于构造函数绑定的注解
若要使用构造函数绑定,必须使用@enableconfigurationproperties或配置属性扫描来启用该类。不能对由常规spring机制创建的bean(例如@component bean、通过@bean方法创建的bean或使用@import加载的bean)使用构造函数绑定

相关问题