1

我正在尝试序列化包含 HashMap 的对象,但出现以下异常。

com.fasterxml.jackson.dataformat.csv.CsvMappingException: Unrecognized column 'tags': known columns: ["_id","insertDate"] (through reference chain.

另外,我不明白为什么在序列化方面需要有一个模式。在我看来,没有办法拥有一个无法识别的字段,因为它都是在类中指定的。

因为我不太了解杰克逊,所以我搜索并尝试了这两个注释的各种组合。@JsonUnwrapped @JsonAnyGetter

class Product{
    public @Id String _id;

    @JsonUnwrapped
    private HashMap<String, String> tags = new HashMap<>();

    public String insertDate;

    @JsonAnyGetter
    public HashMap<String, String> getTags() {
        return tags;
    }
    @JsonAnySetter
    public void setTags(HashMap<String, String> tags) {
        this.tags = tags;
    }
}

用于序列化的代码

CsvSchema schema = csvMapper.schemaFor(Product.class).withHeader();
ObjectWriter myObjectWriter = csvMapper.writer(schema);
csvMapper.enable(CsvParser.Feature.IGNORE_TRAILING_UNMAPPABLE);
csvMapper.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);
string = myObjectWriter.writeValueAsString(someProduct);

尝试 NR 2

public class Product {

public @Id String _id;

public Map<String, String> tags = new HashMap<>();

public String insertDate;

@JsonAnyGetter
public Map<String, String> getTags() {
    return tags;
}
@JsonAnySetter
public void setTags(Map<String, String> tags) {
    this.tags = tags;
}

}

新错误

com.fasterxml.jackson.dataformat.csv.CsvMappingException: CSV generator does not support Object values for properties (nested Objects) (through reference chain: main.model.Product["tags"])
4

1 回答 1

1

使用字段类型Collection的实现类(而不仅仅是它的初始值类型)让杰克逊感到困惑。HashMap<String, String>

Jackson 检查接口java.util.Map以选择适当的序列化器,如构造函数中所证明的那样

com.fasterxml.jackson.databind.ser.std.MapSerializer

根据 Schema question,根据 jackson-dataformat-csv文档

需要注意的是,模式对象需要确保列的正确排序;

另请注意,虽然显式类型可以帮助提高效率,但通常不需要,因为 Jackson 数据绑定可以进行常见的转换/强制

我想ObjectWriter.writeValueAsString(Object)可以反身检查以推断序列化对象的类型。

由于 CSV 格式的表格性质,不能很好地支持深度嵌套的数据结构。

@JsonUnwrapped仅适用于(嵌套的)POJO-s。你想要的是使用@JsonAnyGetter. 它需要返回java.util.Map。JavaDocs:

注意注解方法的返回类型必须是 Map)。

如果您只是序列化,@JsonAnySetter则不需要。

我很好奇你为什么使用 Map 作为标签。也许List<String> tags就足够了,标签只有名称。

值得一试:https ://www.baeldung.com/jackson-mapping-dynamic-object

于 2019-07-24T07:21:39.127 回答