Spring Boot bind @Value to Enum case insensitive

帅比萌擦擦* 提交于 2019-12-05 01:14:54

@Value and @ConfigurationProperties features do not match. I couldn't stress enough how @ConfigurationProperties is superior.

First, you get to design your configuration in a simple POJO that you can inject wherever you want (rather than having expressions in annotation that you can easily break with a typo). Second, the meta-data support means that you can very easily get auto-completion in your IDE for your own keys.

And finally, the relaxed binding described in the doc only applies to @ConfigurationProperties. @Value is a Spring Framework feature and is unaware of relaxed binding. We intend to make that more clear in the doc.

TL;DR abc works with @ConfigurationProperties but won't with @Value.

The values are case-sensitive (consider keys or passwords injected from the environment), and the relaxed binding applies only to the keys. Java enum names are also case-sensitive (A and a are distinct values), and you wouldn't want to squash case.

Just use the correct case in your configuration properties.

A problem with ConfigurationPropertis (afaik) is that you cannot use constructor injection, and your class has to be mutable.

A workaround (or hack if you like) would be to use SpEL to uppercase the property before looking it up, like this:

@Value("#{'${custom.property}'.toUpperCase()}") Property property

This should work since enums instances are constants, and should always be defined in uppercase: https://docs.oracle.com/javase/tutorial/java/javaOO/enum.html

In a practical world, this works....

public enum Property {
    A, a
    AB, ab,
    ABC, abc,
    ABCD, abcd,
    ABCDE, abcde; 

    public boolean isA() {
        return this.equals(A) || this.equals(a);
    }

    public boolean isAB() {
        return this.equals(AB) || this.equals(ab);
    }

    ...etc...

}

..although this does break the principle of the enum!

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!