diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/format/WebConversionService.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/format/WebConversionService.java index fa1df0bfc2fc..ea51a7e3dfb9 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/format/WebConversionService.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/format/WebConversionService.java @@ -59,15 +59,32 @@ public class WebConversionService extends DefaultFormattingConversionService { private final String dateFormat; + private final String timeFormat; + + private final String dateTimeFormat; + /** * Create a new WebConversionService that configures formatters with the provided date * format, or register the default ones if no custom format is provided. * @param dateFormat the custom date format to use for date conversions */ public WebConversionService(String dateFormat) { + this(dateFormat, null, null); + } + + /** + * Create a new WebConversionService that configures formatters with the provided date + * and time formats, or register the default ones if no custom formats are provided. + * @param dateFormat the custom date format to use for date conversions + * @param timeFormat the custom time format to use for time conversions + * @param dateTimeFormat the custom datetime format to use for datetime conversions + */ + public WebConversionService(String dateFormat, String timeFormat, String dateTimeFormat) { super(false); - this.dateFormat = StringUtils.hasText(dateFormat) ? dateFormat : null; - if (this.dateFormat != null) { + this.dateFormat = getNonEmptyFormat(dateFormat); + this.timeFormat = getNonEmptyFormat(timeFormat); + this.dateTimeFormat = getNonEmptyFormat(dateTimeFormat); + if (this.dateFormat != null || this.timeFormat != null || this.dateTimeFormat != null) { addFormatters(); } else { @@ -95,6 +112,17 @@ private void registerJsr310() { dateTime.setDateFormatter( DateTimeFormatter.ofPattern(this.dateFormat).withResolverStyle(ResolverStyle.SMART)); } + + if (this.timeFormat != null) { + dateTime.setTimeFormatter( + DateTimeFormatter.ofPattern(this.timeFormat).withResolverStyle(ResolverStyle.SMART)); + } + + if (this.dateTimeFormat != null) { + dateTime.setDateTimeFormatter( + DateTimeFormatter.ofPattern(this.dateTimeFormat).withResolverStyle(ResolverStyle.SMART)); + } + dateTime.registerFormatters(this); } @@ -117,4 +145,8 @@ private void registerJavaDate() { dateFormatterRegistrar.registerFormatters(this); } + private static String getNonEmptyFormat(final String format) { + return StringUtils.hasText(format) ? format : null; + } + } diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxAutoConfiguration.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxAutoConfiguration.java index 18a25fc81ef2..dab1d88e0da2 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxAutoConfiguration.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxAutoConfiguration.java @@ -203,7 +203,8 @@ public EnableWebFluxConfiguration(WebFluxProperties webFluxProperties, @Bean @Override public FormattingConversionService webFluxConversionService() { - WebConversionService conversionService = new WebConversionService(this.webFluxProperties.getDateFormat()); + WebConversionService conversionService = new WebConversionService(this.webFluxProperties.getDateFormat(), + this.webFluxProperties.getTimeFormat(), this.webFluxProperties.getDateTimeFormat()); addFormatters(conversionService); return conversionService; } diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxProperties.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxProperties.java index 707ca1cf67e5..ffd575dc3039 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxProperties.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/reactive/WebFluxProperties.java @@ -32,6 +32,16 @@ public class WebFluxProperties { */ private String dateFormat; + /** + * Time format to use. For instance, `HH:mm:ss`. + */ + private String timeFormat; + + /** + * Datetime format to use. For instance, `yyyy-MM-dd HH:mm:ss`. + */ + private String dateTimeFormat; + /** * Path pattern used for static resources. */ @@ -45,6 +55,22 @@ public void setDateFormat(String dateFormat) { this.dateFormat = dateFormat; } + public String getTimeFormat() { + return this.timeFormat; + } + + public void setTimeFormat(final String timeFormat) { + this.timeFormat = timeFormat; + } + + public String getDateTimeFormat() { + return this.dateTimeFormat; + } + + public void setDateTimeFormat(final String dateTimeFormat) { + this.dateTimeFormat = dateTimeFormat; + } + public String getStaticPathPattern() { return this.staticPathPattern; } diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcAutoConfiguration.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcAutoConfiguration.java index 36676cc9c0c9..acf74e68f783 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcAutoConfiguration.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcAutoConfiguration.java @@ -421,7 +421,8 @@ private boolean isReadable(Resource resource) { @Bean @Override public FormattingConversionService mvcConversionService() { - WebConversionService conversionService = new WebConversionService(this.mvcProperties.getDateFormat()); + WebConversionService conversionService = new WebConversionService(this.mvcProperties.getDateFormat(), + this.mvcProperties.getTimeFormat(), this.mvcProperties.getDateTimeFormat()); addFormatters(conversionService); return conversionService; } diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcProperties.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcProperties.java index da6e0ee7b6e1..b6437afaa3b6 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcProperties.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/web/servlet/WebMvcProperties.java @@ -60,6 +60,16 @@ public class WebMvcProperties { */ private String dateFormat; + /** + * Time format to use. For instance, `HH:mm:ss`. + */ + private String timeFormat; + + /** + * Datetime format to use. For instance, `yyyy-MM-dd HH:mm:ss`. + */ + private String dateTimeFormat; + /** * Whether to dispatch TRACE requests to the FrameworkServlet doService method. */ @@ -140,6 +150,22 @@ public void setDateFormat(String dateFormat) { this.dateFormat = dateFormat; } + public String getTimeFormat() { + return this.timeFormat; + } + + public void setTimeFormat(final String timeFormat) { + this.timeFormat = timeFormat; + } + + public String getDateTimeFormat() { + return this.dateTimeFormat; + } + + public void setDateTimeFormat(final String dateTimeFormat) { + this.dateTimeFormat = dateTimeFormat; + } + public boolean isIgnoreDefaultModelOnRedirect() { return this.ignoreDefaultModelOnRedirect; } diff --git a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/format/WebConversionServiceTests.java b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/format/WebConversionServiceTests.java index 7b4724122d38..efd9bcbb2053 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/format/WebConversionServiceTests.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/web/format/WebConversionServiceTests.java @@ -50,11 +50,31 @@ void customDateFormatWithJavaTime() { customDateFormat(java.time.LocalDate.of(2018, 1, 1)); } + @Test + void customTimeFormatWithJavaTime() { + customTimeFormat(java.time.LocalTime.of(13, 37, 42)); + } + + @Test + void customDateTimeFormatWithJavaTime() { + customDateTimeFormat(java.time.LocalDateTime.of(2019, 10, 28, 13, 37, 42)); + } + private void customDateFormat(Object input) { WebConversionService conversionService = new WebConversionService("dd*MM*yyyy"); assertThat(conversionService.convert(input, String.class)).isEqualTo("01*01*2018"); } + private void customTimeFormat(Object input) { + WebConversionService conversionService = new WebConversionService(null, "HH*mm*ss", null); + assertThat(conversionService.convert(input, String.class)).isEqualTo("13*37*42"); + } + + private void customDateTimeFormat(Object input) { + WebConversionService conversionService = new WebConversionService(null, null, "dd*MM*yyyy HH*mm*ss"); + assertThat(conversionService.convert(input, String.class)).isEqualTo("28*10*2019 13*37*42"); + } + @Test void convertFromStringToDate() { WebConversionService conversionService = new WebConversionService("yyyy-MM-dd");