So I have been learning REST API with Spring Boot
I have a User bean
@JsonFilter("UserFilter")
public class User {
private int id;
@Size(min = 2, message = "Name should have at least 2 characters")
private String name;
@JsonProperty("Birth Date")
@Past(message = "Birth date should be in the past")
private LocalDate birthDate;
public User(int id, String name, LocalDate birthDate) {
this.id = id;
this.name = name;
this.birthDate = birthDate;
}
@Override
public String toString() {
return "User{" +
"id=" + id +
", name='" + name + ''' +
", birth=" + birthDate +
'}';
}
}
and I have a UserDao to access User data
@Component
public class UserDaoService {
private static List<User> users = new ArrayList<>();
static {
users.add(new User(1, "Alice", LocalDate.now()
.minusYears(18)
.minusMonths(1)));
users.add(new User(2, "Bob", LocalDate.now()
.minusYears(21)
.plusMonths(3)
.plusDays(5)));
users.add(new User(3, "Cathy", LocalDate.now()
.minusDays(7)
.minusYears(25)));
users.add(new User(4, "David", LocalDate.now()
.minusYears(23)));
}
public List<User> findAll() {
return users;
}
public User findById(int id) {
return users.stream()
.filter(user -> user.getId() == id)
.findFirst()
.orElse(null);
}
}
I also have a UserController where I map Endpoints/Requests to REST API responses.
@RestController
public class UserController {
private UserDaoService service;
public UserController(UserDaoService service) {
this.service = service;
}
@GetMapping("/users")
public MappingJacksonValue findAllUsers() {
List<User> usersList = service.findAll();
MappingJacksonValue mjv = new MappingJacksonValue(usersList);
SimpleBeanPropertyFilter filter = SimpleBeanPropertyFilter.filterOutAllExcept("name", "Birth Date");
FilterProvider filters = new SimpleFilterProvider().addFilter("UserFilter", filter);
mjv.setFilters(filters);
return mjv;
}
@GetMapping("/users/{id}")
public EntityModel<User> findUserById(@PathVariable int id) {
User usr = service.findById(id);
if (usr == null)
throw new UserNotFoundException("id:" + id);
EntityModel<User> model = EntityModel.of(usr);
WebMvcLinkBuilder link = WebMvcLinkBuilder.linkTo(WebMvcLinkBuilder.methodOn(this.getClass()).findAllUsers());
model.add(link.withRel("all-users"));
return model;
}
}
For the findAllUsers() method I tried to make use of dynamic filtering using MappingJacksonValue. For findUserById() method I don’t want to apply any filtering but I do want to add a link to the full list of users (using EntityModel) when a person views details on a single user.
When I make a GET request to localhost:8080/users/3 I get the following error:
HttpMessageConversionException: type definition error: [simple type, class SpringBootFramwork.RESTAPI.beans.User]
caused by InvalidDefinitionException: Cannot resolve PropertyFilter with id 'UserFilter'; no FilterProvider configured (through reference chain: org.springframework.hateoas.EntityModel["content"])
It seems when I comment out the @JsonFilter annotation from the User bean the GET request works, but of course no filtering when I GET localhost:8080/users (retrieve all of the users). Why is it when I add the @JsonFilter annotation to my User bean I get the above error? How can I fix this?
{
“id”: 3,
“name”: “Cathy”,
“Birth Date”: “1999-04-19”,
“_links”: {
“all-users”: {
“href”: “http://localhost:8080/users”
}
}
}
Sihle Calana is a new contributor to this site. Take care in asking for clarification, commenting, and answering.
Check out our Code of Conduct.