如何在春季反序列化WWW表单字段枚举?

时间:2018-11-07 03:43:12

标签: spring-boot kotlin enums spring-restcontroller

在Kotlin的Spring应用程序中,尝试反序列化从WWW表单输入到枚举类的输入时遇到问题。

我的DTO和枚举类:

enum class Status(@get:JsonValue val value: Int) {
    NORMAL(0),
    ERROR(1);

    companion object {
        @JvmStatic
        @JsonCreator
        fun of(number: Int?): Status? {
            return values().find { it.value == number }
        }
    }
}

data class RequestData(val status: Status?)

控制器的POST请求接收器方法:

@PostMapping("/post")
fun register(@Valid data: RequestData, error: Errors) {}

当我使用邮递员用status = 0发出POST请求时,请求失败,并出现以下异常。

java.lang.IllegalArgumentException: Parameter specified as non-null is null: method com.example.Controller.post, parameter data

当我用status = NORMAL发出请求时,没有例外,但这是我所不想要的。 我在POST请求中使用了application/x-www-form-urlencoded内容类型。 请让我知道我在哪里做错了。

3 个答案:

答案 0 :(得分:0)

您只需使用名称即可。

ex)状态=正常

value重要吗?您可以使用序数

enum class Status{
    NORMAL,
    ERROR,
}

println(NORMAL.ordinal)
//result:0

这是个玩笑,但是如果您需要

enum class Status(val value:String){
    `0`("NORMAL"),`1`("ERROR")
}

println(data.status.value)

答案 1 :(得分:0)

您可以使用Converter类。请注意,对于您来说,请求参数看起来像一个数字,但实际上它们是字符串。这就是下面的转换器接受String?并返回Status?的原因。这意味着,如果您的enum也接受它,将会为您带来方便。例如:NORMAL("0"), ERROR("1")

class ConvStringToStatus : Converter<String?, Status?> {
    override fun convert(source: String?) = Status.of(source)
}

要使其正常工作,必须按以下方式注册转换器。

@Configuration
class WebConfig : WebMvcConfigurer {
    override fun addFormatters(registry: FormatterRegistry) {
        registry.addConverter(ConvStringToStatus())
    }
}

答案 2 :(得分:0)

对于仍在寻找和发现此内容的任何人。如果添加non-null field is null依赖项,示例代码将起作用,并且不会引发jackson-module-kotlin异常。它应该符合您的com.fasterxml.jackson.core版本

<dependency>
    <groupId>com.fasterxml.jackson.module</groupId>
    <artifactId>jackson-module-kotlin</artifactId>
    <version>2.9.8</version>
</dependency>