Spring Batch 3.0.8中CSV时间戳映射java.sql.Date失败求助
解决Spring Batch BeanWrapperFieldSetMapper日期转换失败问题
这个问题我之前也碰到过,核心原因是BeanWrapperFieldSetMapper默认的日期转换器无法识别你CSV里的'06-05-2018T01:02:08Z'这种带时区和单引号的时间格式,下面给你几个可行的解决方案:
方案一:自定义FieldSetMapper(最直接)
创建一个继承BeanWrapperFieldSetMapper的子类,通过重写initBinder方法注册自定义日期编辑器,精准匹配你的时间格式:
public class CustomBMSContractFieldSetMapper extends BeanWrapperFieldSetMapper<BMSContract> { @Override protected void initBinder(DataBinder binder) { // 注意格式要和CSV中的日期完全匹配,这里要确认06是日还是月,示例按日处理 SimpleDateFormat dateFormat = new SimpleDateFormat("dd-MM-yyyy'T'HH:mm:ss'Z'"); dateFormat.setLenient(false); // 开启严格格式校验,避免无效日期被转换 // 注册编辑器,处理java.sql.Date类型的转换 binder.registerCustomEditor(java.sql.Date.class, new CustomDateEditor(dateFormat, true)); } }
然后把XML配置里的BeanWrapperFieldSetMapper替换成这个自定义类:
<property name="fieldSetMapper"> <bean class="com.your.package.CustomBMSContractFieldSetMapper"> <property name="prototypeBeanName" value="bmsContract" /> </bean> </property>
方案二:全局配置ConversionService(适合多场景复用)
如果你的项目需要统一处理多种日期格式,可以通过Spring的ConversionService配置全局转换器:
- 先写一个字符串转
java.sql.Date的转换器:
public class StringToSqlDateConverter implements Converter<String, java.sql.Date> { // 定义匹配CSV的日期格式,记得处理单引号 private static final DateTimeFormatter FORMATTER = DateTimeFormatter.ofPattern("dd-MM-yyyy'T'HH:mm:ss'Z'"); @Override public java.sql.Date convert(String source) { if (source == null || source.trim().isEmpty()) { return null; } // 先去掉CSV里的单引号,再解析 String cleanSource = source.replace("'", ""); LocalDateTime localDateTime = LocalDateTime.parse(cleanSource, FORMATTER); // 转成java.sql.Date(注意这个类型只保留日期部分,时间会丢失,如果需要保留时间建议用java.sql.Timestamp) return java.sql.Date.valueOf(localDateTime.toLocalDate()); } }
- 配置
ConversionService并注册转换器:
<bean id="customConversionService" class="org.springframework.context.support.ConversionServiceFactoryBean"> <property name="converters"> <set> <bean class="com.your.package.StringToSqlDateConverter" /> </set> </property> </bean>
- 在
BeanWrapperFieldSetMapper中引用这个ConversionService:
<property name="fieldSetMapper"> <bean class="org.springframework.batch.item.file.mapping.BeanWrapperFieldSetMapper"> <property name="prototypeBeanName" value="bmsContract" /> <property name="conversionService" ref="customConversionService" /> </bean> </property>
额外提示
- 确认日期格式的顺序:你的CSV里是
06-05-2018,如果是“月-日-年”的话,格式要改成MM-dd-yyyy'T'HH:mm:ss'Z',别搞反了! - 如果CSV中的日期带单引号,一定要先去除(方案一里可以在编辑器里处理,方案二里已经在转换器里做了)
- 如果你需要保留时间部分,建议把
BMSContract里的REFRESH_TMS字段改成java.sql.Timestamp,这样能完整保留时分秒信息
内容的提问来源于stack exchange,提问作者JamesD
相关产品推荐
相关产品推荐

