Reputation: 511
I have the filter class bellow with 3 attributes to search for available books. I have two search cases: search through a list of book codes or search by date.
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class BookFilter {
Set<Long> bookCodes;
LocalDate fromDate;
LocalDate toDate;
}
This is my Controller
@GetMapping("/books")
public ResponseEntity<Page<BookView>> findAvailableBooks(BookFilter bookFilter, Pageable pageable) {
Page<Book> page = service.findAvailableBooks(bookFilter);
Page<BookView> map = page.map(book-> modelMapper.map(book, BookView.class));
return ResponseEntity.status(HttpStatus.OK).body(map);
}
And I'm trying to send request in Postman like:
http://localhost:8887/v1/api/library/books?fromDate=01-01-2019&toDate=01-31-2019
But I'm stuck in typeMismatch error: Failed to convert from type String to LocalDate. What am I missing?
Upvotes: 1
Views: 2817
Reputation: 1948
/* 1. Get as String */
@GetMapping("/books")
ResponseEntity<Page<BookView>> findAvailableBooks(@RequestParam(value = "fromDate", required = false) String fromDate, @RequestParam(value = "toDate", required = false) String toDate, Pageable pageable) {
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("dd-MM-yyyy");
LocalDate fromLocalDate = LocalDate.parse(fromDate, formatter);
LocalDate toLocalDate = LocalDate.parse(toDate, formatter);
// other code
}
/* 2. Using @DateTimeFormat */
@GetMapping("/books")
ResponseEntity<Page<BookView>> findAvailableBooks(@RequestParam(value = "fromDate", required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE_TIME) LocalDateTime fromDate, @RequestParam(value = "toDate", required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE_TIME) LocalDateTime toDate, Pageable pageable) {
// other code
}
Send LocalDate as a String with @RequestParam and then convert it to the desired date format
Use @DateTimeFormat (iso = DateTimeFormat.ISO.DATE_TIME) with the desired format in the date parameter
Also, a very similar question was asked before on this topic here:
How to use LocalDateTime RequestParam in Spring? I get "Failed to convert String to LocalDateTime"
Upvotes: 2
Reputation: 7790
You need to add @JsonFormat
annotation to your LocalDate
members
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class BookFilter {
Set<Long> bookCodes;
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "dd-MM-yyyy")
LocalDate fromDate;
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "dd-MM-yyyy")
LocalDate toDate;
}
See this question: Spring Data JPA - ZonedDateTime format for json serialization
Upvotes: 1
Reputation: 29
You can use custom serializer/deserializer for string to LocalDate conversion.
import com.fasterxml.jackson.annotation.JsonFormat;
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateDeserializer;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer;
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "MM-dd-yyyy")
@JsonDeserialize(using = LocalDateDeserializer.class)
@JsonSerialize(using = LocalDateSerializer.class)
private LocalDate toDate;
after adding the below dependencies
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.9.7</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.datatype</groupId>
<artifactId>jackson-datatype-jsr310</artifactId>
<version>2.9.7</version>
</dependency>
Upvotes: 1
Reputation: 37
Add @JsonFormat(pattern = "dd-MM-yyyy")
before LocalDate
So your BookFilter class will look like this
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class BookFilter {
Set<Long> bookCodes;
@JsonFormat(pattern = "dd-MM-yyyy")
LocalDate fromDate;
@JsonFormat(pattern = "dd-MM-yyyy")
LocalDate toDate;
}
Upvotes: 1