使用自定义DateFormatter配置转换服务

时间:2014-04-14 14:09:09

标签: spring thymeleaf

我正在尝试在我的spring / thymeleaf应用程序中添加自定义DateFormatter,并提供以下文档: http://www.thymeleaf.org/doc/html/Thymeleaf-Spring3.html#conversions-utility-object

问题是我没有对我的bean定义使用xml配置,而是使用具有以下实现的WebConfig.java类:

@Configuration
@EnableWebMvc
@ComponentScan(basePackages = {"com.myapp.web.controller","net.atos.wfs.wts.adminportal.web.domain"})
public class WebConfig extends WebMvcConfigurerAdapter {

private static final Logger LOG = LoggerFactory.getLogger(WebConfig.class);


@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
    registry.addResourceHandler("/resources/**").addResourceLocations("/resources/");
}

@Override
public void addInterceptors(InterceptorRegistry registry) {
    LocaleChangeInterceptor localeChangeInterceptor = new LocaleChangeInterceptor();
    localeChangeInterceptor.setParamName("lang");
    registry.addInterceptor(localeChangeInterceptor);
}

@Bean
public LocaleResolver localeResolver() {
    CookieLocaleResolver cookieLocaleResolver = new CookieLocaleResolver();
    cookieLocaleResolver.setDefaultLocale(StringUtils.parseLocaleString("en"));
    return cookieLocaleResolver;
}

@Bean
public ServletContextTemplateResolver templateResolver() {
    ServletContextTemplateResolver resolver = new ServletContextTemplateResolver();
    resolver.setPrefix("/WEB-INF/views/");
    resolver.setSuffix(".html");
    //NB, selecting HTML5 as the template mode.
    resolver.setTemplateMode("HTML5");
    resolver.setCacheable(false);
    return resolver;

}

public SpringTemplateEngine templateEngine() {
    SpringTemplateEngine engine = new SpringTemplateEngine();
    engine.setTemplateResolver(templateResolver());
    engine.setMessageResolver(messageResolver());
    engine.addDialect(new LayoutDialect());
    return engine;
}

@Bean
public ViewResolver viewResolver() {

    ThymeleafViewResolver viewResolver = new ThymeleafViewResolver();
    viewResolver.setTemplateEngine(templateEngine());
    viewResolver.setOrder(1);
    viewResolver.setViewNames(new String[]{"*"});
    viewResolver.setCache(false);
    return viewResolver;
}

@Bean
public IMessageResolver messageResolver() {
    SpringMessageResolver messageResolver = new SpringMessageResolver();
    messageResolver.setMessageSource(messageSource());
    return messageResolver;
}

@Override
public void addFormatters(FormatterRegistry registry) {
    super.addFormatters(registry);
    registry.addFormatter(new DateFormatter());
}

@Bean
public MessageSource messageSource() {

    ReloadableResourceBundleMessageSource messageSource = new ReloadableResourceBundleMessageSource();
    messageSource.setBasename("/WEB-INF/messages/messages");
    // if true, the key of the message will be displayed if the key is not
    // found, instead of throwing a NoSuchMessageException
    messageSource.setUseCodeAsDefaultMessage(true);
    messageSource.setDefaultEncoding("UTF-8");
    // # -1 : never reload, 0 always reload
    messageSource.setCacheSeconds(0);
    return messageSource;
}

 }

这是我的Custom DateFormatter的代码:

public class DateFormatter implements Formatter<Date> {

    @Autowired
    private MessageSource messageSource;


    public DateFormatter() {
        super();
    }

    public Date parse(final String text, final Locale locale) throws ParseException {
        final SimpleDateFormat dateFormat = createDateFormat(locale);
        return dateFormat.parse(text);
    }

    public String print(final Date object, final Locale locale) {
        final SimpleDateFormat dateFormat = createDateFormat(locale);
        return dateFormat.format(object);
    }

    private SimpleDateFormat createDateFormat(final Locale locale) {

        //The following line is not working (nullPointerException on messageSource)
        //final String format = this.messageSource.getMessage("date.format", null, locale);
        //The following line is working :
        final String format = "dd/MM/yyyy";
        final SimpleDateFormat dateFormat = new SimpleDateFormat(format);
        dateFormat.setLenient(false);
        return dateFormat;
    }

}

我的问题是:如何添加能够使用@Autowired元素的自定义格式化程序?

xml配置就是这个:

<?xml version="1.0" encoding="UTF-8"?>
<beans ...>

  ...    
  <mvc:annotation-driven conversion-service="conversionService" />
  ...

  <!-- **************************************************************** -->
  <!--  CONVERSION SERVICE                                              -->
  <!--  Standard Spring formatting-enabled implementation               -->
  <!-- **************************************************************** -->
  <bean id="conversionService"
        class="org.springframework.format.support.FormattingConversionServiceFactoryBean">
    <property name="formatters">
      <set>
        <bean class="thymeleafexamples.stsm.web.conversion.VarietyFormatter" />
        <bean class="thymeleafexamples.stsm.web.conversion.DateFormatter" />
      </set>
    </property>
  </bean>

  ...

</beans>

我尝试在WebConfig类中使用以下配置:

@Bean
    public FormattingConversionServiceFactoryBean conversionService() {
        FormattingConversionServiceFactoryBean conversionService = new FormattingConversionServiceFactoryBean();
        Set<Formatter<?>> formatters = new TreeSet<Formatter<?>>();
        formatters.add(new DateFormatter());
        conversionService.setFormatters(formatters);
        return conversionService;
    }

但在这种情况下,格式化程序不会在我的应用程序中考虑。

提前致谢, 安托。

2 个答案:

答案 0 :(得分:3)

将此添加到您的WebMvcConfigurerAdapter

@Override
public void addFormatters(FormatterRegistry registry) {
    registry.addFormatter(dateFormatter);
}

@Autowired
private DateFormatter dateFormatter;

@Bean
public DateFormatter dateFormatter() {
    return new DateFormatter("dd/MM/yyyy");
}

答案 1 :(得分:1)

我使用了以下配置类,并且能够调用自定义格式化程序。我无法传递messageSource,它始终为null,因为稍后在应用程序启动时创建了自动配置bean。

@Configuration
public class ThymeleafConfig {
    @Autowired
    private MessageSource messageSource;

    @Bean
    public SpringSecurityDialect securityDialect() {
        return new SpringSecurityDialect();
    }

    @Bean
    public ConversionService conversionService() {
        DefaultFormattingConversionService conversionService = new DefaultFormattingConversionService( false );
        conversionService.addFormatter( dateFormatter() );
        return conversionService;
    }

    @Bean
    public DateFormatter dateFormatter() {
        return new DateFormatter( messageSource );
    }

}

您还需要在模板中确保使用字段周围的双括号。即

<td th:text="${{user.createDate}}">12-MAR-2015</td>