diff --git a/src/main/java/com/fasterxml/jackson/databind/ser/BeanSerializerFactory.java.orig b/src/main/java/com/fasterxml/jackson/databind/ser/BeanSerializerFactory.java.orig deleted file mode 100644 index 1712a1a78a..0000000000 --- a/src/main/java/com/fasterxml/jackson/databind/ser/BeanSerializerFactory.java.orig +++ /dev/null @@ -1,735 +0,0 @@ -package com.fasterxml.jackson.databind.ser; - -import java.util.*; - -import com.fasterxml.jackson.annotation.ObjectIdGenerator; -import com.fasterxml.jackson.annotation.ObjectIdGenerators; -import com.fasterxml.jackson.databind.*; -import com.fasterxml.jackson.databind.cfg.SerializerFactoryConfig; -import com.fasterxml.jackson.databind.introspect.*; -import com.fasterxml.jackson.databind.jsontype.NamedType; -import com.fasterxml.jackson.databind.jsontype.TypeResolverBuilder; -import com.fasterxml.jackson.databind.jsontype.TypeSerializer; -import com.fasterxml.jackson.databind.ser.impl.FilteredBeanPropertyWriter; -import com.fasterxml.jackson.databind.ser.impl.ObjectIdWriter; -import com.fasterxml.jackson.databind.ser.impl.PropertyBasedObjectIdGenerator; -import com.fasterxml.jackson.databind.ser.std.MapSerializer; -import com.fasterxml.jackson.databind.ser.std.StdDelegatingSerializer; -import com.fasterxml.jackson.databind.type.*; -import com.fasterxml.jackson.databind.util.ArrayBuilders; -import com.fasterxml.jackson.databind.util.ClassUtil; -import com.fasterxml.jackson.databind.util.Converter; - -/** - * Factory class that can provide serializers for any regular Java beans - * (as defined by "having at least one get method recognizable as bean - * accessor" -- where {@link Object#getClass} does not count); - * as well as for "standard" JDK types. Latter is achieved - * by delegating calls to {@link BasicSerializerFactory} - * to find serializers both for "standard" JDK types (and in some cases, - * sub-classes as is the case for collection classes like - * {@link java.util.List}s and {@link java.util.Map}s) and bean (value) - * classes. - *

- * Note about delegating calls to {@link BasicSerializerFactory}: - * although it would be nicer to use linear delegation - * for construction (to essentially dispatch all calls first to the - * underlying {@link BasicSerializerFactory}; or alternatively after - * failing to provide bean-based serializer}, there is a problem: - * priority levels for detecting standard types are mixed. That is, - * we want to check if a type is a bean after some of "standard" JDK - * types, but before the rest. - * As a result, "mixed" delegation used, and calls are NOT done using - * regular {@link SerializerFactory} interface but rather via - * direct calls to {@link BasicSerializerFactory}. - *

- * Finally, since all caching is handled by the serializer provider - * (not factory) and there is no configurability, this - * factory is stateless. - * This means that a global singleton instance can be used. - */ -public class BeanSerializerFactory - extends BasicSerializerFactory - implements java.io.Serializable // since 2.1 -{ - private static final long serialVersionUID = 1; - - /** - * Like {@link BasicSerializerFactory}, this factory is stateless, and - * thus a single shared global (== singleton) instance can be used - * without thread-safety issues. - */ - public final static BeanSerializerFactory instance = new BeanSerializerFactory(null); - - /* - /********************************************************** - /* Life-cycle: creation, configuration - /********************************************************** - */ - - /** - * Constructor for creating instances with specified configuration. - */ - protected BeanSerializerFactory(SerializerFactoryConfig config) - { - super(config); - } - - /** - * Method used by module registration functionality, to attach additional - * serializer providers into this serializer factory. This is typically - * handled by constructing a new instance with additional serializers, - * to ensure thread-safe access. - */ - @Override - public SerializerFactory withConfig(SerializerFactoryConfig config) - { - if (_factoryConfig == config) { - return this; - } - /* 22-Nov-2010, tatu: Handling of subtypes is tricky if we do immutable-with-copy-ctor; - * and we pretty much have to here either choose between losing subtype instance - * when registering additional serializers, or losing serializers. - * Instead, let's actually just throw an error if this method is called when subtype - * has not properly overridden this method; this to indicate problem as soon as possible. - */ - if (getClass() != BeanSerializerFactory.class) { - throw new IllegalStateException("Subtype of BeanSerializerFactory ("+getClass().getName() - +") has not properly overridden method 'withAdditionalSerializers': can not instantiate subtype with " - +"additional serializer definitions"); - } - return new BeanSerializerFactory(config); - } - - @Override - protected Iterable customSerializers() { - return _factoryConfig.serializers(); - } - - /* - /********************************************************** - /* SerializerFactory impl - /********************************************************** - */ - - /** - * Main serializer constructor method. We will have to be careful - * with respect to ordering of various method calls: essentially - * we want to reliably figure out which classes are standard types, - * and which are beans. The problem is that some bean Classes may - * implement standard interfaces (say, {@link java.lang.Iterable}. - *

- * Note: sub-classes may choose to complete replace implementation, - * if they want to alter priority of serializer lookups. - */ - @Override - @SuppressWarnings("unchecked") - public JsonSerializer createSerializer(SerializerProvider prov, - JavaType origType) - throws JsonMappingException - { - // Very first thing, let's check if there is explicit serializer annotation: - final SerializationConfig config = prov.getConfig(); - BeanDescription beanDesc = config.introspect(origType); - JsonSerializer ser = findSerializerFromAnnotation(prov, beanDesc.getClassInfo()); - if (ser != null) { - return (JsonSerializer) ser; - } - boolean staticTyping; - // Next: we may have annotations that further define types to use... - JavaType type = modifyTypeByAnnotation(config, beanDesc.getClassInfo(), origType); - if (type == origType) { // no changes, won't force static typing - staticTyping = false; - } else { // changes; assume static typing; plus, need to re-introspect if class differs - staticTyping = true; - if (!type.hasRawClass(origType.getRawClass())) { - beanDesc = config.introspect(type); - } - } - // Slight detour: do we have a Converter to consider? - Converter conv = beanDesc.findSerializationConverter(); - if (conv == null) { // no, simple - return (JsonSerializer) _createSerializer2(prov, type, beanDesc, staticTyping); - } - JavaType delegateType = conv.getOutputType(prov.getTypeFactory()); - - // One more twist, as per [Issue#288]; probably need to get new BeanDesc - if (!delegateType.hasRawClass(type.getRawClass())) { - beanDesc = config.introspect(delegateType); - // [#359]: explicitly check (again) for @JsonSerializer... - ser = findSerializerFromAnnotation(prov, beanDesc.getClassInfo()); - } - if (ser == null) { - ser = _createSerializer2(prov, delegateType, beanDesc, true); - } - return new StdDelegatingSerializer(conv, delegateType, ser); - } - - protected JsonSerializer _createSerializer2(SerializerProvider prov, - JavaType type, BeanDescription beanDesc, boolean staticTyping) - throws JsonMappingException - { - // Then JsonSerializable, @JsonValue etc: - JsonSerializer ser = findSerializerByAnnotations(prov, type, beanDesc); - if (ser != null) { - return ser; - } - final SerializationConfig config = prov.getConfig(); - - // Container types differ from non-container types - // (note: called method checks for module-provided serializers) - if (type.isContainerType()) { - if (!staticTyping) { - staticTyping = usesStaticTyping(config, beanDesc, null); - // [Issue#23]: Need to figure out how to force passed parameterization - // to stick... - /* - if (property == null) { - JavaType t = origType.getContentType(); - if (t != null && !t.hasRawClass(Object.class)) { - staticTyping = true; - } - } - */ - } - // 03-Aug-2012, tatu: As per [Issue#40], may require POJO serializer... - ser = buildContainerSerializer(prov, type, beanDesc, staticTyping); - // Will return right away, since called method does post-processing: - if (ser != null) { - return ser; - } - } else { - // Modules may provide serializers of POJO types: - for (Serializers serializers : customSerializers()) { - ser = serializers.findSerializer(config, type, beanDesc); - if (ser != null) { - break; - } - } - } - - // Otherwise, we will check "primary types"; both marker types that - // indicate specific handling (JsonSerializable), or main types that have - // precedence over container types - if (ser == null) { - ser = findSerializerByLookup(type, config, beanDesc, staticTyping); - if (ser == null) { - ser = findSerializerByPrimaryType(prov, type, beanDesc, staticTyping); - if (ser == null) { - // And this is where this class comes in: if type is not a - // known "primary JDK type", perhaps it's a bean? We can still - // get a null, if we can't find a single suitable bean property. - ser = findBeanSerializer(prov, type, beanDesc); - // Finally: maybe we can still deal with it as an implementation of some basic JDK interface? - if (ser == null) { - ser = findSerializerByAddonType(config, type, beanDesc, staticTyping); - // 18-Sep-2014, tatu: Actually, as per [jackson-databind#539], need to get - // 'unknown' serializer assigned earlier, here, so that it gets properly - // post-processed - if (ser == null) { - ser = prov.getUnknownTypeSerializer(beanDesc.getBeanClass()); - } - } - } - } - } - if (ser != null) { - // [Issue#120]: Allow post-processing - if (_factoryConfig.hasSerializerModifiers()) { - for (BeanSerializerModifier mod : _factoryConfig.serializerModifiers()) { - ser = mod.modifySerializer(config, beanDesc, ser); - } - } - } - return ser; - } - - /* - /********************************************************** - /* Other public methods that are not part of - /* JsonSerializerFactory API - /********************************************************** - */ - - /** - * Method that will try to construct a {@link BeanSerializer} for - * given class. Returns null if no properties are found. - */ - public JsonSerializer findBeanSerializer(SerializerProvider prov, JavaType type, BeanDescription beanDesc) - throws JsonMappingException - { - // First things first: we know some types are not beans... - if (!isPotentialBeanType(type.getRawClass())) { - // 03-Aug-2012, tatu: Except we do need to allow serializers for Enums, - // as per [Issue#24] - if (!type.isEnumType()) { - return null; - } - } - return constructBeanSerializer(prov, beanDesc); - } - - /** - * Method called to create a type information serializer for values of given - * non-container property - * if one is needed. If not needed (no polymorphic handling configured), should - * return null. - * - * @param baseType Declared type to use as the base type for type information serializer - * - * @return Type serializer to use for property values, if one is needed; null if not. - */ - public TypeSerializer findPropertyTypeSerializer(JavaType baseType, - SerializationConfig config, AnnotatedMember accessor) - throws JsonMappingException - { - AnnotationIntrospector ai = config.getAnnotationIntrospector(); - TypeResolverBuilder b = ai.findPropertyTypeResolver(config, accessor, baseType); - // Defaulting: if no annotations on member, check value class - if (b == null) { - return createTypeSerializer(config, baseType); - } - Collection subtypes = config.getSubtypeResolver().collectAndResolveSubtypes( - accessor, config, ai, baseType); - return b.buildTypeSerializer(config, baseType, subtypes); - } - - /** - * Method called to create a type information serializer for values of given - * container property - * if one is needed. If not needed (no polymorphic handling configured), should - * return null. - * - * @param containerType Declared type of the container to use as the base type for type information serializer - * - * @return Type serializer to use for property value contents, if one is needed; null if not. - */ - public TypeSerializer findPropertyContentTypeSerializer(JavaType containerType, - SerializationConfig config, AnnotatedMember accessor) - throws JsonMappingException - { - JavaType contentType = containerType.getContentType(); - AnnotationIntrospector ai = config.getAnnotationIntrospector(); - TypeResolverBuilder b = ai.findPropertyContentTypeResolver(config, accessor, containerType); - // Defaulting: if no annotations on member, check value class - if (b == null) { - return createTypeSerializer(config, contentType); - } - Collection subtypes = config.getSubtypeResolver().collectAndResolveSubtypes(accessor, - config, ai, contentType); - return b.buildTypeSerializer(config, contentType, subtypes); - } - - /* - /********************************************************** - /* Overridable non-public factory methods - /********************************************************** - */ - - /** - * Method called to construct serializer for serializing specified bean type. - * - * @since 2.1 - */ - @SuppressWarnings("unchecked") - protected JsonSerializer constructBeanSerializer(SerializerProvider prov, - BeanDescription beanDesc) - throws JsonMappingException - { - // 13-Oct-2010, tatu: quick sanity check: never try to create bean serializer for plain Object - // 05-Jul-2012, tatu: ... but we should be able to just return "unknown type" serializer, right? - if (beanDesc.getBeanClass() == Object.class) { - return prov.getUnknownTypeSerializer(Object.class); -// throw new IllegalArgumentException("Can not create bean serializer for Object.class"); - } - final SerializationConfig config = prov.getConfig(); - BeanSerializerBuilder builder = constructBeanSerializerBuilder(beanDesc); - builder.setConfig(config); - - // First: any detectable (auto-detect, annotations) properties to serialize? - List props = findBeanProperties(prov, beanDesc, builder); - if (props == null) { - props = new ArrayList(); - } - // [databind#638]: Allow injection of "virtual" properties: - prov.getAnnotationIntrospector().findAndAddVirtualProperties(config, beanDesc.getClassInfo(), props); - - // [JACKSON-440] Need to allow modification bean properties to serialize: - if (_factoryConfig.hasSerializerModifiers()) { - for (BeanSerializerModifier mod : _factoryConfig.serializerModifiers()) { - props = mod.changeProperties(config, beanDesc, props); - } - } - - // Any properties to suppress? - props = filterBeanProperties(config, beanDesc, props); - - // [JACKSON-440] Need to allow reordering of properties to serialize - if (_factoryConfig.hasSerializerModifiers()) { - for (BeanSerializerModifier mod : _factoryConfig.serializerModifiers()) { - props = mod.orderProperties(config, beanDesc, props); - } - } - - /* And if Object Id is needed, some preparation for that as well: better - * do before view handling, mostly for the custom id case which needs - * access to a property - */ - builder.setObjectIdWriter(constructObjectIdHandler(prov, beanDesc, props)); - - builder.setProperties(props); - builder.setFilterId(findFilterId(config, beanDesc)); - - AnnotatedMember anyGetter = beanDesc.findAnyGetter(); - if (anyGetter != null) { - if (config.canOverrideAccessModifiers()) { - anyGetter.fixAccess(); - } - JavaType type = anyGetter.getType(beanDesc.bindingsForBeanType()); - // copied from BasicSerializerFactory.buildMapSerializer(): - boolean staticTyping = config.isEnabled(MapperFeature.USE_STATIC_TYPING); - JavaType valueType = type.getContentType(); - TypeSerializer typeSer = createTypeSerializer(config, valueType); - // last 2 nulls; don't know key, value serializers (yet) - // TODO: support '@JsonIgnoreProperties' with any setter? - MapSerializer mapSer = MapSerializer.construct(/* ignored props*/ null, type, staticTyping, - typeSer, null, null, /*filterId*/ null); - // TODO: can we find full PropertyName? - PropertyName name = new PropertyName(anyGetter.getName()); - BeanProperty.Std anyProp = new BeanProperty.Std(name, valueType, null, - beanDesc.getClassAnnotations(), anyGetter, PropertyMetadata.STD_OPTIONAL); - builder.setAnyGetter(new AnyGetterWriter(anyProp, anyGetter, mapSer)); - } - // Next: need to gather view information, if any: - processViews(config, builder); - - // Finally: let interested parties mess with the result bit more... - if (_factoryConfig.hasSerializerModifiers()) { - for (BeanSerializerModifier mod : _factoryConfig.serializerModifiers()) { - builder = mod.updateBuilder(config, beanDesc, builder); - } - } - - JsonSerializer ser = (JsonSerializer) builder.build(); - - if (ser == null) { - // If we get this far, there were no properties found, so no regular BeanSerializer - // would be constructed. But, couple of exceptions. - // First: if there are known annotations, just create 'empty bean' serializer - if (beanDesc.hasKnownClassAnnotations()) { - return builder.createDummy(); - } - } - return ser; - } - - protected ObjectIdWriter constructObjectIdHandler(SerializerProvider prov, - BeanDescription beanDesc, List props) - throws JsonMappingException - { - ObjectIdInfo objectIdInfo = beanDesc.getObjectIdInfo(); - if (objectIdInfo == null) { - return null; - } - ObjectIdGenerator gen; - Class implClass = objectIdInfo.getGeneratorType(); - - // Just one special case: Property-based generator is trickier - if (implClass == ObjectIdGenerators.PropertyGenerator.class) { // most special one, needs extra work - String propName = objectIdInfo.getPropertyName().getSimpleName(); - BeanPropertyWriter idProp = null; - - for (int i = 0, len = props.size() ;; ++i) { - if (i == len) { - throw new IllegalArgumentException("Invalid Object Id definition for "+beanDesc.getBeanClass().getName() - +": can not find property with name '"+propName+"'"); - } - BeanPropertyWriter prop = props.get(i); - if (propName.equals(prop.getName())) { - idProp = prop; - /* Let's force it to be the first property to output - * (although it may still get rearranged etc) - */ - if (i > 0) { - props.remove(i); - props.add(0, idProp); - } - break; - } - } - JavaType idType = idProp.getType(); - gen = new PropertyBasedObjectIdGenerator(objectIdInfo, idProp); - // one more thing: must ensure that ObjectIdWriter does not actually write the value: - return ObjectIdWriter.construct(idType, (PropertyName) null, gen, objectIdInfo.getAlwaysAsId()); - - } - // other types are simpler - JavaType type = prov.constructType(implClass); - // Could require type to be passed explicitly, but we should be able to find it too: - JavaType idType = prov.getTypeFactory().findTypeParameters(type, ObjectIdGenerator.class)[0]; - gen = prov.objectIdGeneratorInstance(beanDesc.getClassInfo(), objectIdInfo); - return ObjectIdWriter.construct(idType, objectIdInfo.getPropertyName(), gen, - objectIdInfo.getAlwaysAsId()); - } - - /** - * Method called to construct a filtered writer, for given view - * definitions. Default implementation constructs filter that checks - * active view type to views property is to be included in. - */ - protected BeanPropertyWriter constructFilteredBeanWriter(BeanPropertyWriter writer, - Class[] inViews) - { - return FilteredBeanPropertyWriter.constructViewBased(writer, inViews); - } - - protected PropertyBuilder constructPropertyBuilder(SerializationConfig config, - BeanDescription beanDesc) - { - return new PropertyBuilder(config, beanDesc); - } - - protected BeanSerializerBuilder constructBeanSerializerBuilder(BeanDescription beanDesc) { - return new BeanSerializerBuilder(beanDesc); - } - - /* - /********************************************************** - /* Overridable non-public introspection methods - /********************************************************** - */ - - /** - * Helper method used to skip processing for types that we know - * can not be (i.e. are never consider to be) beans: - * things like primitives, Arrays, Enums, and proxy types. - *

- * Note that usually we shouldn't really be getting these sort of - * types anyway; but better safe than sorry. - */ - protected boolean isPotentialBeanType(Class type) - { - return (ClassUtil.canBeABeanType(type) == null) && !ClassUtil.isProxyType(type); - } - - /** - * Method used to collect all actual serializable properties. - * Can be overridden to implement custom detection schemes. - */ - protected List findBeanProperties(SerializerProvider prov, - BeanDescription beanDesc, BeanSerializerBuilder builder) - throws JsonMappingException - { - List properties = beanDesc.findProperties(); - final SerializationConfig config = prov.getConfig(); - - // [JACKSON-429]: ignore specified types - removeIgnorableTypes(config, beanDesc, properties); - - // and possibly remove ones without matching mutator... - if (config.isEnabled(MapperFeature.REQUIRE_SETTERS_FOR_GETTERS)) { - removeSetterlessGetters(config, beanDesc, properties); - } - - // nothing? can't proceed (caller may or may not throw an exception) - if (properties.isEmpty()) { - return null; - } - // null is for value type serializer, which we don't have access to from here (ditto for bean prop) - boolean staticTyping = usesStaticTyping(config, beanDesc, null); - PropertyBuilder pb = constructPropertyBuilder(config, beanDesc); - - ArrayList result = new ArrayList(properties.size()); - TypeBindings typeBind = beanDesc.bindingsForBeanType(); - for (BeanPropertyDefinition property : properties) { - final AnnotatedMember accessor = property.getAccessor(); - // [JACKSON-762]: type id? Requires special handling: - if (property.isTypeId()) { - if (accessor != null) { // only add if we can access... but otherwise? - if (config.canOverrideAccessModifiers()) { - accessor.fixAccess(); - } - builder.setTypeId(accessor); - } - continue; - } - // [JACKSON-235]: suppress writing of back references - AnnotationIntrospector.ReferenceProperty refType = property.findReferenceType(); - if (refType != null && refType.isBackReference()) { - continue; - } - if (accessor instanceof AnnotatedMethod) { - result.add(_constructWriter(prov, property, typeBind, pb, staticTyping, (AnnotatedMethod) accessor)); - } else { - result.add(_constructWriter(prov, property, typeBind, pb, staticTyping, (AnnotatedField) accessor)); - } - } - return result; - } - - /* - /********************************************************** - /* Overridable non-public methods for manipulating bean properties - /********************************************************** - */ - - /** - * Overridable method that can filter out properties. Default implementation - * checks annotations class may have. - */ - protected List filterBeanProperties(SerializationConfig config, - BeanDescription beanDesc, List props) - { - AnnotationIntrospector intr = config.getAnnotationIntrospector(); - AnnotatedClass ac = beanDesc.getClassInfo(); - String[] ignored = intr.findPropertiesToIgnore(ac); - if (ignored != null && ignored.length > 0) { - HashSet ignoredSet = ArrayBuilders.arrayToSet(ignored); - Iterator it = props.iterator(); - while (it.hasNext()) { - if (ignoredSet.contains(it.next().getName())) { - it.remove(); - } - } - } - return props; - } - - /** - * Method called to handle view information for constructed serializer, - * based on bean property writers. - *

- * Note that this method is designed to be overridden by sub-classes - * if they want to provide custom view handling. As such it is not - * considered an internal implementation detail, and will be supported - * as part of API going forward. - */ - protected void processViews(SerializationConfig config, BeanSerializerBuilder builder) - { - // [JACKSON-232]: whether non-annotated fields are included by default or not is configurable - List props = builder.getProperties(); - boolean includeByDefault = config.isEnabled(MapperFeature.DEFAULT_VIEW_INCLUSION); - final int propCount = props.size(); - int viewsFound = 0; - BeanPropertyWriter[] filtered = new BeanPropertyWriter[propCount]; - // Simple: view information is stored within individual writers, need to combine: - for (int i = 0; i < propCount; ++i) { - BeanPropertyWriter bpw = props.get(i); - Class[] views = bpw.getViews(); - if (views == null) { // no view info? include or exclude by default? - if (includeByDefault) { - filtered[i] = bpw; - } - } else { - ++viewsFound; - filtered[i] = constructFilteredBeanWriter(bpw, views); - } - } - // minor optimization: if no view info, include-by-default, can leave out filtering info altogether: - if (includeByDefault && viewsFound == 0) { - return; - } - builder.setFilteredProperties(filtered); - } - - /** - * Method that will apply by-type limitations (as per [JACKSON-429]); - * by default this is based on {@link com.fasterxml.jackson.annotation.JsonIgnoreType} - * annotation but can be supplied by module-provided introspectors too. - */ - protected void removeIgnorableTypes(SerializationConfig config, BeanDescription beanDesc, - List properties) - { - AnnotationIntrospector intr = config.getAnnotationIntrospector(); - HashMap,Boolean> ignores = new HashMap,Boolean>(); - Iterator it = properties.iterator(); - while (it.hasNext()) { - BeanPropertyDefinition property = it.next(); - AnnotatedMember accessor = property.getAccessor(); - if (accessor == null) { - it.remove(); - continue; - } - Class type = accessor.getRawType(); - Boolean result = ignores.get(type); - if (result == null) { - BeanDescription desc = config.introspectClassAnnotations(type); - AnnotatedClass ac = desc.getClassInfo(); - result = intr.isIgnorableType(ac); - // default to false, non-ignorable - if (result == null) { - result = Boolean.FALSE; - } - ignores.put(type, result); - } - // lotsa work, and yes, it is ignorable type, so: - if (result.booleanValue()) { - it.remove(); - } - } - } - - /** - * Helper method that will remove all properties that do not have a mutator. - */ - protected void removeSetterlessGetters(SerializationConfig config, BeanDescription beanDesc, - List properties) - { - Iterator it = properties.iterator(); - while (it.hasNext()) { - BeanPropertyDefinition property = it.next(); - // one caveat: as per [JACKSON-806], only remove implicit properties; - // explicitly annotated ones should remain - if (!property.couldDeserialize() && !property.isExplicitlyIncluded()) { - it.remove(); - } - } - } - - /* - /********************************************************** - /* Internal helper methods - /********************************************************** - */ - - /** - * Secondary helper method for constructing {@link BeanPropertyWriter} for - * given member (field or method). - */ - protected BeanPropertyWriter _constructWriter(SerializerProvider prov, - BeanPropertyDefinition propDef, TypeBindings typeContext, - PropertyBuilder pb, boolean staticTyping, AnnotatedMember accessor) - throws JsonMappingException - { - final PropertyName name = propDef.getFullName(); - if (prov.canOverrideAccessModifiers()) { - accessor.fixAccess(); - } - JavaType type = accessor.getType(typeContext); - BeanProperty.Std property = new BeanProperty.Std(name, type, propDef.getWrapperName(), - pb.getClassAnnotations(), accessor, propDef.getMetadata()); - - // Does member specify a serializer? If so, let's use it. - JsonSerializer annotatedSerializer = findSerializerFromAnnotation(prov, - accessor); - /* 02-Feb-2012, tatu: Unlike most other code paths, serializer produced - * here will NOT be resolved or contextualized, unless done here, so: - */ - if (annotatedSerializer instanceof ResolvableSerializer) { - ((ResolvableSerializer) annotatedSerializer).resolve(prov); - } - // 05-Sep-2013, tatu: should be primary property serializer so: - annotatedSerializer = prov.handlePrimaryContextualization(annotatedSerializer, property); - // And how about polymorphic typing? First special to cover JAXB per-field settings: - TypeSerializer contentTypeSer = null; - // 16-Feb-2014, cgc: contentType serializers for collection-like and map-like types - if (ClassUtil.isCollectionMapOrArray(type.getRawClass()) || type.isCollectionLikeType() || type.isMapLikeType()) { - contentTypeSer = findPropertyContentTypeSerializer(type, prov.getConfig(), accessor); - } - // and if not JAXB collection/array with annotations, maybe regular type info? - TypeSerializer typeSer = findPropertyTypeSerializer(type, prov.getConfig(), accessor); - BeanPropertyWriter pbw = pb.buildWriter(prov, propDef, type, annotatedSerializer, - typeSer, contentTypeSer, accessor, staticTyping); - return pbw; - } -} diff --git a/src/main/java/com/fasterxml/jackson/databind/ser/BeanSerializerFactory.java.rej b/src/main/java/com/fasterxml/jackson/databind/ser/BeanSerializerFactory.java.rej deleted file mode 100644 index c243c3686c..0000000000 --- a/src/main/java/com/fasterxml/jackson/databind/ser/BeanSerializerFactory.java.rej +++ /dev/null @@ -1,36 +0,0 @@ -*************** -*** 391,404 **** - JavaType valueType = type.getContentType(); - TypeSerializer typeSer = createTypeSerializer(config, valueType); - // last 2 nulls; don't know key, value serializers (yet) -- // TODO: support '@JsonIgnoreProperties' with any setter? -- MapSerializer mapSer = MapSerializer.construct(/* ignored props*/ null, type, staticTyping, -- typeSer, null, null, /*filterId*/ null); - // TODO: can we find full PropertyName? - PropertyName name = PropertyName.construct(anyGetter.getName()); - BeanProperty.Std anyProp = new BeanProperty.Std(name, valueType, null, - beanDesc.getClassAnnotations(), anyGetter, PropertyMetadata.STD_OPTIONAL); -- builder.setAnyGetter(new AnyGetterWriter(anyProp, anyGetter, mapSer)); - } - // Next: need to gather view information, if any: - processViews(config, builder); ---- 391,409 ---- - JavaType valueType = type.getContentType(); - TypeSerializer typeSer = createTypeSerializer(config, valueType); - // last 2 nulls; don't know key, value serializers (yet) -+ -+ // 23-Feb-2015, tatu: As per [#705], need to support custom serializers -+ JsonSerializer anySer = findSerializerFromAnnotation(prov, anyGetter); -+ if (anySer == null) { -+ // TODO: support '@JsonIgnoreProperties' with any setter? -+ anySer = MapSerializer.construct(/* ignored props*/ null, type, staticTyping, -+ typeSer, null, null, /*filterId*/ null); -+ } - // TODO: can we find full PropertyName? - PropertyName name = PropertyName.construct(anyGetter.getName()); - BeanProperty.Std anyProp = new BeanProperty.Std(name, valueType, null, - beanDesc.getClassAnnotations(), anyGetter, PropertyMetadata.STD_OPTIONAL); -+ builder.setAnyGetter(new AnyGetterWriter(anyProp, anyGetter, anySer)); - } - // Next: need to gather view information, if any: - processViews(config, builder);