protected setPropertyValue()

in grails-databinding-core/src/main/groovy/grails/databinding/SimpleDataBinder.groovy [627:692]


    protected setPropertyValue(obj, DataBindingSource source, MetaProperty metaProperty, propertyValue, DataBindingListener listener, boolean convertCollectionElements) {
        def propName = metaProperty.name
        def propertyType
        def propertyGetter
        if (metaProperty instanceof MetaBeanProperty) {
            def mbp = (MetaBeanProperty)metaProperty
            propertyType = mbp.getter?.returnType ?: mbp.field?.type
            if(propertyType && (propertyType.interface || Modifier.isAbstract(propertyType.modifiers))) {
                propertyType = mbp.field?.type
            }
            propertyGetter = mbp.getter
        }
        if (propertyType == null || propertyType == Object) {
            propertyType = metaProperty.type
            if(propertyType == null || propertyType == Object) {
                propertyType = getField(obj.getClass(), propName)?.type ?: Object
            }
        }
        if (propertyValue == null || propertyType == Object || propertyType.isAssignableFrom(propertyValue.getClass())) {
            if (convertCollectionElements && ((!(propertyValue instanceof Range) && propertyValue instanceof Collection && Collection.isAssignableFrom(propertyType) && propertyGetter))) {
                addElementsToCollection(obj, propName, propertyValue, true)
            } else {
                obj[propName] = propertyValue
            }
        } else if (propertyValue instanceof List &&
                  Set.isAssignableFrom(propertyType) &&
                  !SortedSet.isAssignableFrom(propertyType)) {
            addElementsToCollection(obj, propName, propertyValue, true)
        } else {
            if (propertyValue instanceof Map) {
                if (Collection.isAssignableFrom(propertyType) &&
                   propertyValue.size() == 1 &&
                   ((Map)propertyValue)[propertyValue.keySet()[0]] instanceof List) {
                    def key = propertyValue.keySet()[0]
                    List list = (List)((Map)propertyValue)[key]
                    addElementsToCollection(obj, propName, list)
                } else {
                    if (obj[propName] == null) {
                        initializeProperty(obj, propName, propertyType, source)
                    }
                    bind obj[propName], new SimpleMapDataBindingSource(propertyValue), listener
                }
            } else if (propertyValue instanceof DataBindingSource) {
                if (Collection.isAssignableFrom(propertyType) &&
                   propertyValue.size() == 1 &&
                   ((Map)propertyValue)[propertyValue.getPropertyNames()[0]] instanceof List) {
                    def key = propertyValue.getPropertyNames()[0]
                    List list = (List)((Map)propertyValue)[key]
                    addElementsToCollection(obj, propName, list)
                } else {
                    if (obj[propName] == null) {
                        initializeProperty(obj, propName, propertyType, source)
                    }
                    bind obj[propName], propertyValue, listener
                }
            } else if(Collection.isAssignableFrom(propertyType) && propertyValue instanceof String) {
                addElementToCollection obj, propName, propertyType, propertyValue, true
            } else if(Collection.isAssignableFrom(propertyType) && propertyValue instanceof Number) {
                addElementToCollection obj, propName, propertyType, propertyValue, true
            } else if(Collection.isAssignableFrom(propertyType) && propertyValue.getClass().isArray()) {
                addElementsToCollection obj, propName, propertyValue as Collection, true
            } else {
                obj[propName] = convert(propertyType, propertyValue)
            }
        }
    }