探秘Spring的PropertyEditor

探秘Spring的PropertyEditor

今天无意之中一位网友咨询一个问题让我有了深入了解一下Spring的PropertyEditor机制,虽然之前也大概知道些,但是都是知道它是什么,却不知道在Spring整个机制中它是如何执行的。今天就趁着中午闲暇时间看了一下Spring这方面的源码。所以这里主要是通过分析Spring的源码来了解PropertyEditor。

其实PropertyEditor是JDK里面的java.beans下面的类,是提供AWT进行渲染用的。Spring通过利用该接口,来实现Bean的属性转换器。我们在Spring的xml或者其他途径配置的bean属性都是字符串类型的值,,但是对应到每个具体的属性是各种类型的,Spring通过各种PropertyEditor来对各个属性进行类型转换,在Spring中的PropertyEditor并不是直接实现PropertyEditor接口,是通过PropertyEditorSupport类屏蔽了一些Spring不需要的方法比如paintValue,从而对它们提供了默认的实现,所以Spring里面的PropertyEditor都是在PropertyEditorSupport的基础上实现的。那么先看看Spring到底提供了哪些PropertyEditor的实现,下面截取了通过IDE工具找到的实现类截图:

这里面基本涉及到了所有JDK提供的类型,知道spring提供哪些PropertyEditor之后,还得需要这些PropertyEditor是怎么嵌入Spring的。

PropertyEditorRegistry

这个是Spring框架内部将PropertyEditor嵌入Spring的方式,其中BeanWrapperImpl就是一个例子。先看看BeanWrapperImpl的类图:

可以看到BeanWrapperImpl其实就是PropertyEditorRegistry的子类。其实PropertyEditorRegistry是一个接口,做具体事情的是PropertyEditorRegistrySupport。在PropertyEditorRegistrySupport中存在一个方法createDefaultEditors,这个方法就是初始化Spring中默认PropertyEditor。下面看看哪些是Spring默认的PropertyEditor:

private void createDefaultEditors() {this.defaultEditors = new HashMap<Class<?>, PropertyEditor>(64);.defaultEditors.put(Charset.class, new CharsetEditor());this.defaultEditors.put(Class.class, new ClassEditor());this.defaultEditors.put(Class[].class, new ClassArrayEditor());this.defaultEditors.put(Currency.class, new CurrencyEditor());this.defaultEditors.put(File.class, new FileEditor());this.defaultEditors.put(InputStream.class, new InputStreamEditor());this.defaultEditors.put(InputSource.class, new InputSourceEditor());this.defaultEditors.put(Locale.class, new LocaleEditor());this.defaultEditors.put(Pattern.class, new PatternEditor());this.defaultEditors.put(Properties.class, new PropertiesEditor());this.defaultEditors.put(Resource[].class, new ResourceArrayPropertyEditor());this.defaultEditors.put(TimeZone.class, new TimeZoneEditor());this.defaultEditors.put(URI.class, new URIEditor());this.defaultEditors.put(URL.class, new URLEditor());this.defaultEditors.put(UUID.class, new UUIDEditor());.defaultEditors.put(Collection.class, new CustomCollectionEditor(Collection.class));this.defaultEditors.put(Set.class, new CustomCollectionEditor(Set.class));this.defaultEditors.put(SortedSet.class, new CustomCollectionEditor(SortedSet.class));this.defaultEditors.put(List.class, new CustomCollectionEditor(List.class));this.defaultEditors.put(SortedMap.class, new CustomMapEditor(SortedMap.class));// Default editors for primitive arrays.this.defaultEditors.put(byte[].class, new ByteArrayPropertyEditor());this.defaultEditors.put(char[].class, new CharArrayPropertyEditor());// The JDK does not contain a default editor for char!this.defaultEditors.put(char.class, new CharacterEditor(false));this.defaultEditors.put(Character.class, new CharacterEditor(true));// Spring’s CustomBooleanEditor accepts more flag values than the JDK’s default editor.this.defaultEditors.put(boolean.class, new CustomBooleanEditor(false));this.defaultEditors.put(Boolean.class, new CustomBooleanEditor(true));.defaultEditors.put(byte.class, new CustomNumberEditor(Byte.class, false));this.defaultEditors.put(Byte.class, new CustomNumberEditor(Byte.class, true));this.defaultEditors.put(short.class, new CustomNumberEditor(Short.class, false));this.defaultEditors.put(Short.class, new CustomNumberEditor(Short.class, true));this.defaultEditors.put(int.class, new CustomNumberEditor(Integer.class, false));this.defaultEditors.put(Integer.class, new CustomNumberEditor(Integer.class, true));this.defaultEditors.put(long.class, new CustomNumberEditor(Long.class, false));this.defaultEditors.put(Long.class, new CustomNumberEditor(Long.class, true));this.defaultEditors.put(float.class, new CustomNumberEditor(Float.class, false));this.defaultEditors.put(Float.class, new CustomNumberEditor(Float.class, true));this.defaultEditors.put(double.class, new CustomNumberEditor(Double.class, false));this.defaultEditors.put(Double.class, new CustomNumberEditor(Double.class, true));this.defaultEditors.put(BigDecimal.class, new CustomNumberEditor(BigDecimal.class, true));this.defaultEditors.put(BigInteger.class, new CustomNumberEditor(BigInteger.class, true));// Only register config value editors if explicitly requested.if (this.configValueEditorsActive) {StringArrayPropertyEditor sae = new StringArrayPropertyEditor();this.defaultEditors.put(String[].class, sae);this.defaultEditors.put(short[].class, sae);this.defaultEditors.put(int[].class, sae);this.defaultEditors.put(long[].class, sae);}}

执行完这个那么BeanWrapperImpl就具备上面类型的转换功能,可能上面能够转换的类型还不能满足我们的需求,那么可以通过另一种方式将PropertyEditor注入到Spring中。

PropertyEditorRegistrar别为荒漠的艰难而哭泣,只为奔流入海功成名就那一天,

探秘Spring的PropertyEditor

相关文章:

你感兴趣的文章:

标签云: