杰克逊不会映射到自定义的侦听器映射对象?



所以我一直在开发一个小型的LinkedHashMap扩展类,用于我的一个项目,在那里我编辑了它,使其在put方法中具有值更改侦听器。这是我的map类:

static class MapWithListeners<K, V> extends LinkedHashMap<K, V> {
private final LinkedHashMap<K, V> delegate;
public static final String UPDATE_EVT = "update";
public MapWithListeners() {
this.delegate = new LinkedHashMap<>();
}
public MapWithListeners(LinkedHashMap<K, V> delegate) {
this.delegate = delegate;
}
private final PropertyChangeSupport changeSupport = new PropertyChangeSupport(this);
public void addPropertyChangeListener(PropertyChangeListener listener) {
changeSupport.addPropertyChangeListener(listener);
}
public void removePropertyChangeListener(PropertyChangeListener listener) {
changeSupport.removePropertyChangeListener(listener);
}
protected void firePropertyChange(String propertyName, Object oldValue, Object newValue) {
changeSupport.firePropertyChange(propertyName, oldValue, newValue);
}
@Override
public V put(K var1, V var2) {
V oldValue = delegate.put(var1, var2);
firePropertyChange(UPDATE_EVT, oldValue == null ? null : new AbstractMap.SimpleEntry<>(var1, oldValue),
new AbstractMap.SimpleEntry<>(var1, var2));
return oldValue;
}
}

问题是,我试图映射一个对象到这个映射类的实例:

ObjectMapper mapper = new ObjectMapper();
MapWithListeners<String, Object> map = mapper.convertValue(mainObj, new TypeReference<MapWithListeners<String, Object>>() {
});

,结果是一个空映射。我已经尝试过用普通的LinkedHashMap这样做,它基本上按照我需要的方式工作,但是它丧失了我也需要的值更改侦听器。我假设我在MapWithListeners类中做错了什么,但不能弄清楚那是什么。提前感谢任何帮助与此!

编辑:我发现有必要将我的静态类更改为抽象类,基本上像:abstract class MapWithListeners<K,V> extends LinkedHashMap<K,V> implements Map<K,V>

然后用抽象类型映射模块配置我的映射器,如:

SimpleModule module = new SimpleModule().addAbstractTypeMapping(Map.class, MapWithListeners.class);
mapper.registerModule(module);

然而,到目前为止,在convertValue行返回了一个错误,它说:

java.lang.IllegalArgumentException: Cannot find a deserializer for non-concrete Map type [map type; class com.invoiceeditor.POJOEditor$MapWithListeners, [simple type, class java.lang.String] -> [simple type, class java.lang.Object]]

任何想法吗?

请尝试以下操作:通过构造自定义MapType为Jackson映射器提供更多的类型支持。此后,您可以使用它进行转换。

我已经实现了以下,它的技巧和IllegalArgumentException在你的帖子中提到的消失了:

MapType javaType = mapper.getTypeFactory().constructMapType(MapWithListeners.class, String.class, Object.class);
MapWithListeners<String, Object> map = mapper.convertValue(mainObj, javaType);

最新更新