12
12
import com .fasterxml .jackson .databind .introspect .*;
13
13
import com .fasterxml .jackson .databind .jsontype .TypeDeserializer ;
14
14
import com .fasterxml .jackson .databind .jsontype .impl .SubTypeValidator ;
15
+ import com .fasterxml .jackson .databind .node .ObjectNode ;
15
16
import com .fasterxml .jackson .databind .util .BeanUtil ;
16
17
import com .fasterxml .jackson .databind .util .ClassUtil ;
17
18
import com .fasterxml .jackson .databind .util .IgnorePropertiesUtil ;
@@ -806,6 +807,7 @@ protected SettableAnyProperty constructAnySetter(DeserializationContext ctxt,
806
807
BeanProperty prop ;
807
808
JavaType keyType ;
808
809
JavaType valueType ;
810
+ final boolean isField = mutator instanceof AnnotatedField ;
809
811
810
812
if (mutator instanceof AnnotatedMethod ) {
811
813
// we know it's a 2-arg method, second arg is the value
@@ -817,18 +819,39 @@ protected SettableAnyProperty constructAnySetter(DeserializationContext ctxt,
817
819
valueType , null , mutator ,
818
820
PropertyMetadata .STD_OPTIONAL );
819
821
820
- } else if (mutator instanceof AnnotatedField ) {
822
+ } else if (isField ) {
821
823
AnnotatedField af = (AnnotatedField ) mutator ;
822
824
// get the type from the content type of the map object
823
- JavaType mapType = af .getType ();
824
- mapType = resolveMemberAndTypeAnnotations (ctxt , mutator , mapType );
825
- keyType = mapType .getKeyType ();
826
- valueType = mapType .getContentType ();
827
- prop = new BeanProperty .Std (PropertyName .construct (mutator .getName ()),
828
- mapType , null , mutator , PropertyMetadata .STD_OPTIONAL );
825
+ JavaType fieldType = af .getType ();
826
+ // 31-Jul-2022, tatu: Not just Maps any more but also JsonNode, so:
827
+ if (fieldType .isMapLikeType ()) {
828
+ fieldType = resolveMemberAndTypeAnnotations (ctxt , mutator , fieldType );
829
+ keyType = fieldType .getKeyType ();
830
+ valueType = fieldType .getContentType ();
831
+ prop = new BeanProperty .Std (PropertyName .construct (mutator .getName ()),
832
+ fieldType , null , mutator , PropertyMetadata .STD_OPTIONAL );
833
+ } else if (fieldType .hasRawClass (JsonNode .class )
834
+ || fieldType .hasRawClass (ObjectNode .class )) {
835
+ fieldType = resolveMemberAndTypeAnnotations (ctxt , mutator , fieldType );
836
+ // Deserialize is individual values of ObjectNode, not full ObjectNode, so:
837
+ valueType = ctxt .constructType (JsonNode .class );
838
+ prop = new BeanProperty .Std (PropertyName .construct (mutator .getName ()),
839
+ fieldType , null , mutator , PropertyMetadata .STD_OPTIONAL );
840
+
841
+ // Unlike with more complicated types, here we do not allow any annotation
842
+ // overrides etc but instead short-cut handling:
843
+ return SettableAnyProperty .constructForJsonNodeField (ctxt ,
844
+ prop , mutator , valueType ,
845
+ ctxt .findRootValueDeserializer (valueType ));
846
+ } else {
847
+ return ctxt .reportBadDefinition (beanDesc .getType (), String .format (
848
+ "Unsupported type for any-setter: %s -- only support `Map`s, `JsonNode` and `ObjectNode` " ,
849
+ ClassUtil .getTypeDescription (fieldType )));
850
+ }
829
851
} else {
830
852
return ctxt .reportBadDefinition (beanDesc .getType (), String .format (
831
- "Unrecognized mutator type for any setter: %s" , mutator .getClass ()));
853
+ "Unrecognized mutator type for any-setter: %s" ,
854
+ ClassUtil .nameOf (mutator .getClass ())));
832
855
}
833
856
// First: see if there are explicitly specified
834
857
// and then possible direct deserializer override on accessor
@@ -853,8 +876,12 @@ protected SettableAnyProperty constructAnySetter(DeserializationContext ctxt,
853
876
deser = (JsonDeserializer <Object >) ctxt .handlePrimaryContextualization (deser , prop , valueType );
854
877
}
855
878
TypeDeserializer typeDeser = valueType .getTypeHandler ();
856
- return new SettableAnyProperty (prop , mutator , valueType ,
857
- keyDeser , deser , typeDeser );
879
+ if (isField ) {
880
+ return SettableAnyProperty .constructForMapField (ctxt ,
881
+ prop , mutator , valueType , keyDeser , deser , typeDeser );
882
+ }
883
+ return SettableAnyProperty .constructForMethod (ctxt ,
884
+ prop , mutator , valueType , keyDeser , deser , typeDeser );
858
885
}
859
886
860
887
/**
0 commit comments