Jackson 数据绑定枚举不区分大小写 [英] Jackson databind enum case insensitive

查看:41
本文介绍了Jackson 数据绑定枚举不区分大小写的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如何反序列化包含不区分大小写的枚举值的 JSON 字符串?(使用杰克逊数据绑定)

How can I deserialize JSON string that contains enum values that are case insensitive? (using Jackson Databind)

JSON 字符串:

[{"url": "foo", "type": "json"}]

和我的 Java POJO:

and my Java POJO:

public static class Endpoint {

    public enum DataType {
        JSON, HTML
    }

    public String url;
    public DataType type;

    public Endpoint() {

    }

}

在这种情况下,使用 "type":"json" 反序列化 JSON 会失败,而 "type":"JSON" 会起作用.但出于命名约定的原因,我希望 "json" 也能正常工作.

in this case,deserializing the JSON with "type":"json" would fail where as "type":"JSON" would work. But I want "json" to work as well for naming convention reasons.

序列化 POJO 也会导致大写 "type":"JSON"

Serializing the POJO also results in upper case "type":"JSON"

我想到了使用 @JsonCreator 和 @JsonGetter:

I thought of using @JsonCreator and @JsonGetter:

    @JsonCreator
    private Endpoint(@JsonProperty("name") String url, @JsonProperty("type") String type) {
        this.url = url;
        this.type = DataType.valueOf(type.toUpperCase());
    }

    //....
    @JsonGetter
    private String getType() {
        return type.name().toLowerCase();
    }

它奏效了.但我想知道是否有更好的解决方案,因为这对我来说看起来像是一个黑客.

And it worked. But I was wondering whether there's a better solutuon because this looks like a hack to me.

我也可以编写自定义反序列化器,但我有许多使用枚举的不同 POJO,而且很难维护.

I can also write a custom deserializer but I got many different POJOs that use enums and it would be hard to maintain.

谁能提出一种更好的方法来序列化和反序列化具有适当命名约定的枚举?

Can anyone suggest a better way to serialize and deserialize enums with proper naming convention?

我不希望 java 中的枚举为小写!

这是我使用的一些测试代码:

Here is some test code that I used:

    String data = "[{"url":"foo", "type":"json"}]";
    Endpoint[] arr = new ObjectMapper().readValue(data, Endpoint[].class);
        System.out.println("POJO[]->" + Arrays.toString(arr));
        System.out.println("JSON ->" + new ObjectMapper().writeValueAsString(arr));

推荐答案

Jackson 2.9

现在这个很简单,使用jackson-databind 2.9.0 及以上

ObjectMapper objectMapper = new ObjectMapper();
objectMapper.enable(MapperFeature.ACCEPT_CASE_INSENSITIVE_ENUMS);

// objectMapper now deserializes enums in a case-insensitive manner


带有测试的完整示例

import com.fasterxml.jackson.databind.MapperFeature;
import com.fasterxml.jackson.databind.ObjectMapper;

public class Main {

  private enum TestEnum { ONE }
  private static class TestObject { public TestEnum testEnum; }

  public static void main (String[] args) {
    ObjectMapper objectMapper = new ObjectMapper();
    objectMapper.enable(MapperFeature.ACCEPT_CASE_INSENSITIVE_ENUMS);

    try {
      TestObject uppercase = 
        objectMapper.readValue("{ "testEnum": "ONE" }", TestObject.class);
      TestObject lowercase = 
        objectMapper.readValue("{ "testEnum": "one" }", TestObject.class);
      TestObject mixedcase = 
        objectMapper.readValue("{ "testEnum": "oNe" }", TestObject.class);

      if (uppercase.testEnum != TestEnum.ONE) throw new Exception("cannot deserialize uppercase value");
      if (lowercase.testEnum != TestEnum.ONE) throw new Exception("cannot deserialize lowercase value");
      if (mixedcase.testEnum != TestEnum.ONE) throw new Exception("cannot deserialize mixedcase value");

      System.out.println("Success: all deserializations worked");
    } catch (Exception e) {
      e.printStackTrace();
    }
  }
}

这篇关于Jackson 数据绑定枚举不区分大小写的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆