Skip to content

Commit

Permalink
Fix #795
Browse files Browse the repository at this point in the history
  • Loading branch information
cowtowncoder committed May 18, 2015
1 parent f0efb09 commit ee1c51a
Show file tree
Hide file tree
Showing 7 changed files with 57 additions and 34 deletions.
2 changes: 2 additions & 0 deletions release-notes/VERSION
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,8 @@ Project: jackson-databind
configurable/external equality comparison
#794: Add `SerializationFeature.WRITE_DATES_WITH_ZONE_ID` to allow inclusion/exclusion of
timezone id for date/time values (as opposed to timezone offset)
#795: Converter annotation not honored for abstract types
(reported by myrosia@github)
- Remove old cglib compatibility tests; cause problems in Eclipse

2.5.4 (not yet released)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -411,7 +411,6 @@ public ValueInstantiator _valueInstantiatorInstance(DeserializationConfig config

// may need to keep track for [#725]
List<AnnotatedConstructor> implicitCtors = null;

for (AnnotatedConstructor ctor : beanDesc.getConstructors()) {
final boolean isCreator = intr.hasCreatorAnnotation(ctor);
BeanPropertyDefinition[] propDefs = creatorParams.get(ctor);
Expand Down Expand Up @@ -446,7 +445,7 @@ public ValueInstantiator _valueInstantiatorInstance(DeserializationConfig config
// 2 or more args; all params must have names or be injectable
// 14-Mar-2015, tatu (2.6): Or, as per [#725], implicit names will also
// do, with some constraints. But that will require bit post processing...

AnnotatedParameter nonAnnotatedParam = null;
CreatorProperty[] properties = new CreatorProperty[argCount];
int explicitNameCount = 0;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,8 @@ public class BeanDeserializer
{
/* TODOs for future versions:
*
* For 2.6?
*
* For 2.7?
*
* - New method in JsonDeserializer (deserializeNext()) to allow use of more
* efficient 'nextXxx()' method `JsonParser` provides.
*
Expand Down Expand Up @@ -429,7 +429,7 @@ protected Object _deserializeUsingPropertyBased(final JsonParser p, final Deseri
unknown.writeFieldName(propName);
unknown.copyCurrentStructure(p);
}

// We hit END_OBJECT, so:
Object bean;
try {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -407,11 +407,11 @@ public void resolve(DeserializationContext ctxt)
{
ExternalTypeHandler.Builder extTypes = null;
// if ValueInstantiator can use "creator" approach, need to resolve it here...
SettableBeanProperty[] creatorProps;
if (_valueInstantiator.canCreateFromObjectWith()) {
SettableBeanProperty[] creatorProps = _valueInstantiator.getFromObjectArguments(ctxt.getConfig());
_propertyBasedCreator = PropertyBasedCreator.construct(ctxt, _valueInstantiator, creatorProps);
creatorProps = _valueInstantiator.getFromObjectArguments(ctxt.getConfig());
// also: need to try to resolve 'external' type ids...
for (SettableBeanProperty prop : _propertyBasedCreator.properties()) {
for (SettableBeanProperty prop : creatorProps) {
if (prop.hasValueTypeDeserializer()) {
TypeDeserializer typeDeser = prop.getValueTypeDeserializer();
if (typeDeser.getTypeInclusion() == JsonTypeInfo.As.EXTERNAL_PROPERTY) {
Expand All @@ -422,12 +422,15 @@ public void resolve(DeserializationContext ctxt)
}
}
}
} else {
creatorProps = null;
}

UnwrappedPropertyHandler unwrapped = null;

for (SettableBeanProperty origProp : _beanProperties) {
SettableBeanProperty prop = origProp;

// May already have deserializer from annotations, if so, skip:
if (!prop.hasValueDeserializer()) {
// [Issue#125]: allow use of converters
Expand All @@ -447,6 +450,7 @@ public void resolve(DeserializationContext ctxt)
prop = prop.withValueDeserializer(cd);
}
}

// [JACKSON-235]: need to link managed references with matching back references
prop = _resolveManagedReferenceProperty(ctxt, prop);

Expand All @@ -472,11 +476,29 @@ public void resolve(DeserializationContext ctxt)
prop = _resolveInnerClassValuedProperty(ctxt, prop);
if (prop != origProp) {
_beanProperties.replace(prop);
// [databind#795]: Make sure PropertyBasedCreator's properties stay in sync
if (creatorProps != null) {
// 18-May-2015, tatu: _Should_ start with consistent set. But can we really
// fully count on this? May need to revisit in future; seems to hold for now.
for (int i = 0, len = creatorProps.length; i < len; ++i) {
if (creatorProps[i] == origProp) {
creatorProps[i] = prop;
break;
}
// ... as per above, it is possible we'd need to add this as fallback
// if (but only if) identity check fails?
/*
if (creatorProps[i].getName().equals(prop.getName())) {
creatorProps[i] = prop;
break;
}
*/
}
}
}

/* one more thing: if this property uses "external property" type inclusion
* (see [JACKSON-453]), it needs different handling altogether
*/
// one more thing: if this property uses "external property" type inclusion
// (see [JACKSON-453]), it needs different handling altogether
if (prop.hasValueTypeDeserializer()) {
TypeDeserializer typeDeser = prop.getValueTypeDeserializer();
if (typeDeser.getTypeInclusion() == JsonTypeInfo.As.EXTERNAL_PROPERTY) {
Expand Down Expand Up @@ -522,7 +544,12 @@ public void resolve(DeserializationContext ctxt)
}
_delegateDeserializer = dd;
}


// And now that we know CreatorProperty instances are also resolved can finally create the creator:
if (creatorProps != null) {
_propertyBasedCreator = PropertyBasedCreator.construct(ctxt, _valueInstantiator, creatorProps);
}

if (extTypes != null) {
_externalTypeIdHandler = extTypes.build();
// we consider this non-standard, to offline handling
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -534,13 +534,13 @@ protected void addBeanProps(DeserializationContext ctxt,
+name+"' (in class "+beanDesc.getBeanClass().getName()+")");
}
if (prop != null) {
cprop = cprop.withFallbackSetter(prop);
cprop.setFallbackSetter(prop);
}
prop = cprop;
builder.addCreatorProperty(cprop);
continue;
}

if (prop != null) {
Class<?>[] views = propDef.findViews();
if (views == null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.*;
import com.fasterxml.jackson.databind.introspect.AnnotatedMember;
import com.fasterxml.jackson.databind.introspect.AnnotatedParameter;
Expand Down Expand Up @@ -50,11 +49,14 @@ public class CreatorProperty
* In special cases, when implementing "updateValue", we can not use
* constructors or factory methods, but have to fall back on using a
* setter (or mutable field property). If so, this refers to that fallback
* accessor
* accessor.
*<p>
* Mutable only to allow setting after construction, but must be strictly
* set before any use.
*
* @since 2.3
*/
protected final SettableBeanProperty _fallbackSetter;
protected SettableBeanProperty _fallbackSetter;

/**
* @param name Name of the logical property
Expand Down Expand Up @@ -102,17 +104,6 @@ protected CreatorProperty(CreatorProperty src, JsonDeserializer<?> deser) {
_fallbackSetter = src._fallbackSetter;
}

/**
* @since 2.3
*/
protected CreatorProperty(CreatorProperty src, SettableBeanProperty fallbackSetter) {
super(src);
_annotated = src._annotated;
_creatorIndex = src._creatorIndex;
_injectableValueId = src._injectableValueId;
_fallbackSetter = fallbackSetter;
}

@Override
public CreatorProperty withName(PropertyName newName) {
return new CreatorProperty(this, newName);
Expand All @@ -123,10 +114,16 @@ public CreatorProperty withValueDeserializer(JsonDeserializer<?> deser) {
return new CreatorProperty(this, deser);
}

public CreatorProperty withFallbackSetter(SettableBeanProperty fallbackSetter) {
return new CreatorProperty(this, fallbackSetter);
/**
* NOTE: one exception to immutability, due to problems with CreatorProperty instances
* being shared between Bean, separate PropertyBasedCreator
*
* @since 2.6.0
*/
public void setFallbackSetter(SettableBeanProperty fallbackSetter) {
_fallbackSetter = fallbackSetter;
}

/**
* Method that can be called to locate value to be injected for this
* property, if it is configured for this.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package com.fasterxml.jackson.failing;
package com.fasterxml.jackson.databind.convert;

import com.fasterxml.jackson.annotation.*;
import com.fasterxml.jackson.databind.*;
Expand Down Expand Up @@ -47,7 +47,6 @@ public NonAbstractCustomType(String v) {
}
}


public static class NonAbstractCustomTypeDeserializationConverter extends StdConverter<String, NonAbstractCustomType>{

@Override
Expand All @@ -56,7 +55,6 @@ public NonAbstractCustomType convert(String arg) {
}
}


public static class NonAbstractCustomTypeUser {
@JsonProperty
@JsonDeserialize(converter = NonAbstractCustomTypeDeserializationConverter.class)
Expand Down

0 comments on commit ee1c51a

Please sign in to comment.