Skip to content

Commit 45a0cad

Browse files
committed
revised core conversion package for BeanWrapper/BeanFactory integration
1 parent e9823b5 commit 45a0cad

File tree

70 files changed

+1258
-1106
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

70 files changed

+1258
-1106
lines changed

org.springframework.beans/src/main/java/org/springframework/beans/AbstractPropertyAccessor.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,8 @@
2121
import java.util.List;
2222
import java.util.Map;
2323

24+
import org.springframework.core.convert.ConversionService;
25+
2426
/**
2527
* Abstract implementation of the {@link PropertyAccessor} interface.
2628
* Provides base implementations of all convenience methods, with the

org.springframework.beans/src/main/java/org/springframework/beans/BeanWrapperImpl.java

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@
3838
import org.apache.commons.logging.LogFactory;
3939
import org.springframework.core.GenericCollectionTypeResolver;
4040
import org.springframework.core.MethodParameter;
41+
import org.springframework.core.convert.ConversionException;
4142
import org.springframework.util.Assert;
4243
import org.springframework.util.ObjectUtils;
4344
import org.springframework.util.StringUtils;
@@ -145,7 +146,7 @@ public BeanWrapperImpl(Object object) {
145146
* Create new BeanWrapperImpl, wrapping a new instance of the specified class.
146147
* @param clazz class to instantiate and wrap
147148
*/
148-
public BeanWrapperImpl(Class clazz) {
149+
public BeanWrapperImpl(Class<?> clazz) {
149150
registerDefaultEditors();
150151
setWrappedInstance(BeanUtils.instantiateClass(clazz));
151152
}
@@ -365,8 +366,8 @@ public boolean isWritableProperty(String propertyName) {
365366
return false;
366367
}
367368

368-
public Object convertIfNecessary(
369-
Object value, Class requiredType, MethodParameter methodParam) throws TypeMismatchException {
369+
public <T> T convertIfNecessary(
370+
Object value, Class<T> requiredType, MethodParameter methodParam) throws TypeMismatchException {
370371
try {
371372
return this.typeConverterDelegate.convertIfNecessary(value, requiredType, methodParam);
372373
}
@@ -572,16 +573,17 @@ public Object run() {
572573
}
573574
}
574575

575-
Object value = null;
576+
Object value;
576577

577578
if (System.getSecurityManager() != null) {
578579
try {
579580
value = AccessController.doPrivileged(new PrivilegedExceptionAction<Object>() {
580581
public Object run() throws Exception {
581582
return readMethod.invoke(object, (Object[]) null);
582583
}
583-
},acc);
584-
} catch (PrivilegedActionException pae) {
584+
}, acc);
585+
}
586+
catch (PrivilegedActionException pae) {
585587
throw pae.getException();
586588
}
587589
}
@@ -625,7 +627,7 @@ else if (value instanceof Set) {
625627
}
626628
else if (value instanceof Map) {
627629
Map map = (Map) value;
628-
Class mapKeyType = GenericCollectionTypeResolver.getMapKeyReturnType(pd.getReadMethod(), i + 1);
630+
Class<?> mapKeyType = GenericCollectionTypeResolver.getMapKeyReturnType(pd.getReadMethod(), i + 1);
629631
// IMPORTANT: Do not pass full property name in here - property editors
630632
// must not kick in for map keys but rather only for map values.
631633
Object convertedMapKey = this.typeConverterDelegate.convertIfNecessary(key, mapKeyType);
@@ -945,6 +947,11 @@ public Object run() throws Exception {
945947
throw new MethodInvocationException(propertyChangeEvent, ex.getTargetException());
946948
}
947949
}
950+
catch (ConversionException ex) {
951+
PropertyChangeEvent pce =
952+
new PropertyChangeEvent(this.rootObject, this.nestedPath + propertyName, oldValue, pv.getValue());
953+
throw new TypeMismatchException(pce, pd.getPropertyType(), ex);
954+
}
948955
catch (IllegalArgumentException ex) {
949956
PropertyChangeEvent pce =
950957
new PropertyChangeEvent(this.rootObject, this.nestedPath + propertyName, oldValue, pv.getValue());

org.springframework.beans/src/main/java/org/springframework/beans/ConfigurablePropertyAccessor.java

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2007 the original author or authors.
2+
* Copyright 2002-2009 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -16,6 +16,8 @@
1616

1717
package org.springframework.beans;
1818

19+
import org.springframework.core.convert.ConversionService;
20+
1921
/**
2022
* Interface that encapsulates configuration methods for a PropertyAccessor.
2123
* Also extends the PropertyEditorRegistry interface, which defines methods
@@ -29,6 +31,17 @@
2931
*/
3032
public interface ConfigurablePropertyAccessor extends PropertyAccessor, PropertyEditorRegistry, TypeConverter {
3133

34+
/**
35+
* Specify a Spring 3.0 ConversionService to use for converting
36+
* property values, as an alternative to JavaBeans PropertyEditors.
37+
*/
38+
void setConversionService(ConversionService conversionService);
39+
40+
/**
41+
* Return the associated ConversionService, if any.
42+
*/
43+
ConversionService getConversionService();
44+
3245
/**
3346
* Set whether to extract the old property value when applying a
3447
* property editor to a new value for a property.

org.springframework.beans/src/main/java/org/springframework/beans/PropertyEditorRegistrySupport.java

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@
5757
import org.springframework.beans.propertyeditors.StringArrayPropertyEditor;
5858
import org.springframework.beans.propertyeditors.URIEditor;
5959
import org.springframework.beans.propertyeditors.URLEditor;
60+
import org.springframework.core.convert.ConversionService;
6061
import org.springframework.core.io.Resource;
6162
import org.springframework.core.io.support.ResourceArrayPropertyEditor;
6263
import org.springframework.util.ClassUtils;
@@ -75,6 +76,8 @@
7576
*/
7677
public class PropertyEditorRegistrySupport implements PropertyEditorRegistry {
7778

79+
private ConversionService conversionService;
80+
7881
private boolean defaultEditorsActive = false;
7982

8083
private boolean configValueEditorsActive = false;
@@ -90,6 +93,22 @@ public class PropertyEditorRegistrySupport implements PropertyEditorRegistry {
9093
private Map<Class, PropertyEditor> customEditorCache;
9194

9295

96+
/**
97+
* Specify a Spring 3.0 ConversionService to use for converting
98+
* property values, as an alternative to JavaBeans PropertyEditors.
99+
*/
100+
public void setConversionService(ConversionService conversionService) {
101+
this.conversionService = conversionService;
102+
}
103+
104+
/**
105+
* Return the associated ConversionService, if any.
106+
*/
107+
public ConversionService getConversionService() {
108+
return this.conversionService;
109+
}
110+
111+
93112
//---------------------------------------------------------------------
94113
// Management of default editors
95114
//---------------------------------------------------------------------

org.springframework.beans/src/main/java/org/springframework/beans/TypeConverterDelegate.java

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,8 @@
3030
import org.springframework.core.CollectionFactory;
3131
import org.springframework.core.GenericCollectionTypeResolver;
3232
import org.springframework.core.MethodParameter;
33+
import org.springframework.core.convert.ConversionService;
34+
import org.springframework.core.convert.TypeDescriptor;
3335
import org.springframework.util.ClassUtils;
3436
import org.springframework.util.StringUtils;
3537

@@ -160,6 +162,18 @@ protected <T> T convertIfNecessary(
160162
// Custom editor for this type?
161163
PropertyEditor editor = this.propertyEditorRegistry.findCustomEditor(requiredType, propertyName);
162164

165+
// No custom editor but custom ConversionService specified?
166+
ConversionService conversionService = this.propertyEditorRegistry.getConversionService();
167+
if (editor == null && conversionService != null && convertedValue != null &&
168+
conversionService.canConvert(convertedValue.getClass(), requiredType)) {
169+
if (methodParam != null) {
170+
return (T) conversionService.convert(convertedValue, new TypeDescriptor(methodParam));
171+
}
172+
else {
173+
return conversionService.convert(convertedValue, requiredType);
174+
}
175+
}
176+
163177
// Value not of required type?
164178
if (editor != null || (requiredType != null && !ClassUtils.isAssignableValue(requiredType, convertedValue))) {
165179
if (editor == null) {
@@ -265,7 +279,7 @@ protected PropertyEditor findDefaultEditor(Class requiredType, PropertyDescripto
265279
* @return the new value, possibly the result of type conversion
266280
* @throws IllegalArgumentException if type conversion failed
267281
*/
268-
protected Object doConvertValue(Object oldValue, Object newValue, Class requiredType, PropertyEditor editor) {
282+
protected Object doConvertValue(Object oldValue, Object newValue, Class<?> requiredType, PropertyEditor editor) {
269283
Object convertedValue = newValue;
270284
boolean sharedEditor = false;
271285

@@ -307,6 +321,8 @@ protected Object doConvertValue(Object oldValue, Object newValue, Class required
307321
}
308322
}
309323

324+
Object returnValue = convertedValue;
325+
310326
if (requiredType != null && !requiredType.isArray() && convertedValue instanceof String[]) {
311327
// Convert String array to a comma-separated String.
312328
// Only applies if no PropertyEditor converted the String array before.
@@ -335,7 +351,7 @@ protected Object doConvertValue(Object oldValue, Object newValue, Class required
335351
}
336352
}
337353

338-
return convertedValue;
354+
return returnValue;
339355
}
340356

341357
/**

org.springframework.beans/src/main/java/org/springframework/beans/TypeMismatchException.java

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -56,10 +56,10 @@ public TypeMismatchException(PropertyChangeEvent propertyChangeEvent, Class requ
5656
*/
5757
public TypeMismatchException(PropertyChangeEvent propertyChangeEvent, Class requiredType, Throwable cause) {
5858
super(propertyChangeEvent,
59-
"Failed to convert property value of type [" +
60-
ClassUtils.getDescriptiveType(propertyChangeEvent.getNewValue()) + "]" +
59+
"Failed to convert property value of type '" +
60+
ClassUtils.getDescriptiveType(propertyChangeEvent.getNewValue()) + "'" +
6161
(requiredType != null ?
62-
" to required type [" + ClassUtils.getQualifiedName(requiredType) + "]" : "") +
62+
" to required type '" + ClassUtils.getQualifiedName(requiredType) + "'" : "") +
6363
(propertyChangeEvent.getPropertyName() != null ?
6464
" for property '" + propertyChangeEvent.getPropertyName() + "'" : ""),
6565
cause);
@@ -83,8 +83,8 @@ public TypeMismatchException(Object value, Class requiredType) {
8383
* @param cause the root cause (may be <code>null</code>)
8484
*/
8585
public TypeMismatchException(Object value, Class requiredType, Throwable cause) {
86-
super("Failed to convert value of type [" + ClassUtils.getDescriptiveType(value) + "]" +
87-
(requiredType != null ? " to required type [" + ClassUtils.getQualifiedName(requiredType) + "]" : ""),
86+
super("Failed to convert value of type '" + ClassUtils.getDescriptiveType(value) + "'" +
87+
(requiredType != null ? " to required type '" + ClassUtils.getQualifiedName(requiredType) + "'" : ""),
8888
cause);
8989
this.value = value;
9090
this.requiredType = requiredType;

org.springframework.beans/src/main/java/org/springframework/beans/factory/config/ConfigurableBeanFactory.java

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
import org.springframework.beans.factory.BeanFactory;
2626
import org.springframework.beans.factory.HierarchicalBeanFactory;
2727
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
28+
import org.springframework.core.convert.ConversionService;
2829
import org.springframework.util.StringValueResolver;
2930

3031
/**
@@ -134,6 +135,17 @@ public interface ConfigurableBeanFactory extends HierarchicalBeanFactory, Single
134135
*/
135136
BeanExpressionResolver getBeanExpressionResolver();
136137

138+
/**
139+
* Specify a Spring 3.0 ConversionService to use for converting
140+
* property values, as an alternative to JavaBeans PropertyEditors.
141+
*/
142+
void setConversionService(ConversionService conversionService);
143+
144+
/**
145+
* Return the associated ConversionService, if any.
146+
*/
147+
ConversionService getConversionService();
148+
137149
/**
138150
* Add a PropertyEditorRegistrar to be applied to all bean creation processes.
139151
* <p>Such a registrar creates new PropertyEditor instances and registers them

org.springframework.beans/src/main/java/org/springframework/beans/factory/support/AbstractBeanFactory.java

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,7 @@
6666
import org.springframework.beans.factory.config.Scope;
6767
import org.springframework.core.DecoratingClassLoader;
6868
import org.springframework.core.NamedThreadLocal;
69+
import org.springframework.core.convert.ConversionService;
6970
import org.springframework.util.Assert;
7071
import org.springframework.util.ClassUtils;
7172
import org.springframework.util.StringUtils;
@@ -120,6 +121,9 @@ public abstract class AbstractBeanFactory extends FactoryBeanRegistrySupport imp
120121
/** Resolution strategy for expressions in bean definition values */
121122
private BeanExpressionResolver beanExpressionResolver;
122123

124+
/** Spring 3.0 ConversionService to use instead of PropertyEditors */
125+
private ConversionService conversionService;
126+
123127
/** Custom PropertyEditorRegistrars to apply to the beans of this factory */
124128
private final Set<PropertyEditorRegistrar> propertyEditorRegistrars =
125129
new LinkedHashSet<PropertyEditorRegistrar>(4);
@@ -620,6 +624,14 @@ public BeanExpressionResolver getBeanExpressionResolver() {
620624
return this.beanExpressionResolver;
621625
}
622626

627+
public void setConversionService(ConversionService conversionService) {
628+
this.conversionService = conversionService;
629+
}
630+
631+
public ConversionService getConversionService() {
632+
return this.conversionService;
633+
}
634+
623635
public void addPropertyEditorRegistrar(PropertyEditorRegistrar registrar) {
624636
Assert.notNull(registrar, "PropertyEditorRegistrar must not be null");
625637
this.propertyEditorRegistrars.add(registrar);
@@ -669,6 +681,7 @@ public TypeConverter getTypeConverter() {
669681
else {
670682
// Build default TypeConverter, registering custom editors.
671683
SimpleTypeConverter typeConverter = new SimpleTypeConverter();
684+
typeConverter.setConversionService(getConversionService());
672685
registerCustomEditors(typeConverter);
673686
return typeConverter;
674687
}
@@ -937,6 +950,7 @@ protected String originalBeanName(String name) {
937950
* @param bw the BeanWrapper to initialize
938951
*/
939952
protected void initBeanWrapper(BeanWrapper bw) {
953+
bw.setConversionService(getConversionService());
940954
registerCustomEditors(bw);
941955
}
942956

org.springframework.beans/src/main/java/org/springframework/beans/propertyeditors/PropertiesEditor.java

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2007 the original author or authors.
2+
* Copyright 2002-2009 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -37,13 +37,6 @@
3737
* @see java.util.Properties#load
3838
*/
3939
public class PropertiesEditor extends PropertyEditorSupport {
40-
41-
/**
42-
* Any of these characters, if they're first after whitespace or first
43-
* on a line, mean that the line is a comment and should be ignored.
44-
*/
45-
private final static String COMMENT_MARKERS = "#!";
46-
4740

4841
/**
4942
* Convert {@link String} into {@link Properties}, considering it as

0 commit comments

Comments
 (0)