【问题标题】:Easy way to serialize/deserialize public enums?序列化/反序列化公共枚举的简单方法?
【发布时间】:2016-04-29 16:52:04
【问题描述】:

我在尝试用 Java 序列化/反序列化一些 enum 时遇到了一些麻烦。这是我的枚举类:

FrequencyType.java:

@JsonInclude(Include.NON_NULL)
@JsonIgnoreProperties(ignoreUnknown = true)
public enum FrequencyType {
    NONE,
    HOURLY,
    DAILY,
    WEEKLY,
    MONTHLY;
}

Controller.java

@RequestMapping(method = RequestMethod.POST)
public Object createFrequency(@RequestBody FrequencyType frequencyType) throws Exception {
    ...
    frequencyManager.createFrequency(frequencyType);
    ...
}

我正在尝试使用createFrequency 方法将FrequencyType 作为json 输入。这是我的输入示例:

{
    "frequencyType": "HOURLY"
}

但是,每当我尝试通过我的 REST API 调用此方法时,我都会收到一条错误消息:

"无法读取 JSON:无法反序列化 com.zuora.cds.api.schedule.FrequencyType 超出 START_OBJECT 令牌\n 在 [来源:java.io.PushbackInputStream@225337f8;行:1,列:1]; 嵌套异常是 com.fasterxml.jackson.databind.JsonMappingException:不能 反序列化 com.zuora.cds.api.schedule.FrequencyType 的实例 START_OBJECT 令牌\n 在 [Source: java.io.PushbackInputStream@225337f8;行:1,列:1]",

我尝试在上面添加JsonIncludeJsonIgnoreProperties 注释,但这似乎没有帮助。我还尝试像这样添加getterssetters

FrequencyType getNone() {
    return FrequencyType.NONE;
}
FrequencyType getHourly() {
    return FrequencyType.HOURLY;
}
FrequencyType getDaily() {
    return FrequencyType.DAILY;
}
FrequencyType getWeekly() {
    return FrequencyType.WEEKLY;
}
FrequencyType getMonthly() {
    return FrequencyType.MONTHLY;
}
void setNone(FrequencyType frequencyType) {
    this.equals(frequencyType);
}
void setHourly(FrequencyType frequencyType) {
    this.equals(frequencyType);
}
void setDaily(FrequencyType frequencyType) {
    this.equals(frequencyType);
}
void setWeekly(FrequencyType frequencyType) {
    this.equals(frequencyType);
}
void setMonthly(FrequencyType frequencyType) {
    this.equals(frequencyType);
}

因此 POJO 表示有望将 JSON 转换为 FrequencyType 但我最终得到了同样的错误。任何帮助,将不胜感激。谢谢!

【问题讨论】:

  • 试试{"frequencyType": 1},如果这不起作用SerializeFrequencyType,看看你的图书馆期望什么。
  • @ElliottFrisch 您能否详细说明您对SerializeFrequencyType 工作的意义?第一种方法无效。

标签: java json spring serialization enums


【解决方案1】:

Jackson 中的枚举类型通常被序列化和反序列化为 JSON 字符串

您正在尝试将 JSON object 反序列化为枚举

{
    "frequencyType": "HOURLY"
}

这是一个 JSON 对象,它有一个名为 frequencyType 的名称-值对和一个 JSON 字符串值。

你需要创建一个 POJO 来包装这个对象

class FrequencyTypeWrapper {
    private FrequencyType frequencyType;

    // getters and setters
}

Jackson will eventually support a @JsonWrapped annotation 您可能可以将其添加到您的枚举类型中,表明您希望在根对象中使用某个名称包装它。

另一种方法是为进行适当转换的枚举类型编写和注册自己的JsonDeserializer,即。解析 JSON 对象,提取名称-值对,并将 String 值转换为枚举值。


如果您没有在代码中将任何其他内容反序列化为 JSON,则可以配置您的 ObjectMapper 以解开根值。

mapper.configure(DeserializationFeature.UNWRAP_ROOT_VALUE, true);

您还必须为您的 enum 类型配置根名称

@JsonRootName("frequencyType")
enum FrequencyType {
    HOURLY /* more */;
}

【讨论】:

  • 啊,我明白你在说什么。那么我会做一些像这样的课程:public class FrequencyTypeWrapper { private FrequencyType frequencyType; public FrequencyType getFrequencyType() { return frequencyType; } public void setFrequencyType(String frequencyType) { String result = frequencyType; //Parse frequencyType... this.frequencyType = result; } }
  • @user1871869 是的,您将使用该类型作为处理程序方法的参数。还有其他选项(但它们可能并非在所有情况下都有用),请参阅我的编辑。
【解决方案2】:

你可以简单地:

添加以下注释:

-1.

 @JsonFormat(shape = JsonFormat.Shape.OBJECT)
    public enum FrequencyType {

-2。在 setter 中添加以下注解:

@JsonDeserialize(using = EnumDeserializer.class)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-11-30
    • 2012-10-24
    • 2014-08-10
    • 2019-05-31
    • 2015-07-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多