mvc:resources /标签新老版本解析不同,是bug还是?

先来说说这个坑爹的问题,其实本来我是没注意到的,因为程序跑起来一切都正常。但是在tomcat启动时飞速打印log时,在中间“隐藏”了一个错误:

2015-02-15 16:03:22 [ catalina-exec-4:2202 ] – [ DEBUG ] [org.springframework.beans.TypeConverterDelegate] Original ConversionService attempt failed – ignored since PropertyEditor based conversion eventually succeededorg.springframework.core.type java.util.ArrayList; nested exception is org.springframework.core.convert.ConverterNotFoundException: No converter found capable of converting from type java.lang.String to type org.springframework.core.io.Resourceat org.springframework.core.convert.support.ConversionUtils.invokeConverter(ConversionUtils.java:41)at org.springframework.core.convert.support.GenericConversionService.convert(GenericConversionService.java:168)at ……..此处省略Caused by: org.springframework.core.convert.ConverterNotFoundException: No converter found capable of converting from type … 61 more

看这个错误应该是在类型转换的时候报的错。也就是将

=”” />

中的location转换成List<Resource>的时候报错的。Spring3中使用的是ConversionService来对外提供转换接口,这里我确实注册了一个ConversionService,但那也只是在默认之上添加了一个自己实现的DateFormatter,应该不会有影响的。

那到底是什么原因呢?我觉得像我这样的人,星期六在家完全不适合碰到稍微需要分析一下的问题。因为我容易逃避啊,觉得烦就跑去打Dota了,图个脑袋轻松。还好今天上班,可以来好好地分析一下这个问题。

其实我一开始并没有想到是<mvc:resources />标签解析的问题,,而是按照Dispatcher启动的顺序来做调试的。关于Dispatcher的启动过程,我打算在下一篇文章中来记录。通过上面繁琐的跟踪,最终定位到org.springframework.beans.TypeConverterDelegate类中的 convertIfNecessary(String propertyName, Object oldValue, Object newValue, Class<T> requiredType, TypeDescriptor typeDescriptor)方法:

public <T> T convertIfNecessary(String propertyName, Object oldValue, Object newValue,Class<T> requiredType, TypeDescriptor typeDescriptor) throws IllegalArgumentException {Object convertedValue = newValue;// Custom editor for this type?PropertyEditor editor = this.propertyEditorRegistry.findCustomEditor(requiredType, propertyName);ConversionFailedException firstAttemptEx = null;// No custom editor but custom ConversionService specified?ConversionService conversionService = this.propertyEditorRegistry.getConversionService();if (editor == null && conversionService != null && convertedValue != null && typeDescriptor != null) {TypeDescriptor sourceTypeDesc = TypeDescriptor.forObject(newValue);TypeDescriptor targetTypeDesc = typeDescriptor;if (conversionService.canConvert(sourceTypeDesc, targetTypeDesc)) {try {return (T) conversionService.convert(convertedValue, sourceTypeDesc, targetTypeDesc);}catch (ConversionFailedException ex) {// fallback to default conversion logic belowfirstAttemptEx = ex;}}}// Value not of required type?if (editor != null || (requiredType != null && !ClassUtils.isAssignableValue(requiredType, convertedValue))) {if (requiredType != null && Collection.class.isAssignableFrom(requiredType) && convertedValue instanceof String) {TypeDescriptor elementType = typeDescriptor.getElementTypeDescriptor();if (elementType != null && Enum.class.isAssignableFrom(elementType.getType())) {convertedValue = StringUtils.commaDelimitedListToStringArray((String) convertedValue);}}if (editor == null) {editor = findDefaultEditor(requiredType);}convertedValue = doConvertValue(oldValue, convertedValue, requiredType, editor);}boolean standardConversion = false;if (requiredType != null) {if (convertedValue != null) {(convertedValue instanceof Collection) {// Convert elements to target type, if determined.convertedValue = convertToTypedCollection((Collection) convertedValue, propertyName, requiredType, typeDescriptor);standardConversion = true;}// 省略部分代码,都是根据条件来调用不同的转换方法}// 省略部分代码}if (firstAttemptEx != null) {if (editor == null && !standardConversion && requiredType != null && !Object.class.equals(requiredType)) {throw firstAttemptEx;}logger.debug(“Original ConversionService attempt failed – ignored since ” +”PropertyEditor based conversion eventually succeeded”, firstAttemptEx);}return (T) convertedValue;}少一点预设的期待,那份对人的关怀会更自在

mvc:resources /标签新老版本解析不同,是bug还是?

相关文章:

你感兴趣的文章:

标签云: