【问题标题】:@Validated annotation makes field of @ConfigurationProperties class to be null@Validated 注解使@ConfigurationProperties 类的字段为空
【发布时间】:2020-08-21 10:08:33
【问题描述】:

我有以下两个类和yaml-config:

第 1 类:

 @ConfigurationProperties
 @Validated     ֎ 1 ֎
 public class SplitterProps {

    @Valid
    public final ConnectionParams connectionParams;
 //   @Valid
 //   @NotNull
    public final Subscriber subscriber;
    public final List<@NotNull @Valid Converter> converters;

    @ConstructorBinding
    public SplitterProps(ConnectionParams connectionParams,
                                Map<String, Subscriber> subscribersList,
                                List<Converter> converters) {
        this.connectionParams = connectionParams;
        this.subscriber = subscribersList.isEmpty() ? 
                          null : 
                          subscribersList.values().iterator().next();
        this.converters = converters;
    }
 ...
 }

YAML 配置:

...
subscribersList:
  sub1:
    kafkaBroker: xxx:9092
    topicName: saveTopic
    healthCheckTimeout: 10
    producerTimeout: 10
...

第 2 类:

@Configuration(proxyBeanMethods = false)
public class KafkaConfig {

    private final Subscriber subscriberProps;
    private final Map<String, Object> producerProps;

    public KafkaConfig(KafkaProperties kafkaProps,
                       SplitterProps appProps) {
        this.subscriberProps = appProps.subscriber;      ֎ 2 ֎
        this.producerProps = getProducerProperties(kafkaProps, subscriberProps);
    }
...
}

如果第 1 行有 @Validated 注释 ֎

然后 appProps.subscriber == null 在第 ֎ 2 ֎ 行。 (出现NPE)

如果第 1 行没有 @Validated 注释 ֎

然后 appProps.subscriber != null 在第 ֎ 2 ֎ 行。 (按预期工作)

为什么会这样以及如何避免?

【问题讨论】:

    标签: java spring validation initialization configurationproperties


    【解决方案1】:

    解决方法如下:

    • 当@ConfigurationProperties 类上有no @Validate 注解时 然后调用 appProps.subscriber 指的是 SplitterProps 类的实例
    • 当@ConfigurationProperties 类上有 @Validate 注释时 然后 SplitterProps 包装到 Spring 代理中,因此调用 appProps.subscriber 指代代理成员

    为了处理这种行为,我应该通过 getter 执行字段访问。

    所以我已将 @Getter 添加到 SplitterProps 类,现在 appProps.getSubscriber() != null。

    【讨论】:

      猜你喜欢
      • 2017-11-14
      • 1970-01-01
      • 2016-03-16
      • 2014-08-12
      • 2021-01-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-06-09
      相关资源
      最近更新 更多