I'm working on project with Spring boot 1.5.4.RELEASE with Spring Data JPA.
Stuck on issue that Hibernate validator isn't executed when updating entity or at least in some cases it doesn't validate.
For Person like below it is forbidden to have empty name and skills collection have to has min 1 element and max 5. Both of them are verified during call save on Spring Data repository. However for call save on already existing entity it will verify only constraints of name - and won't check skills.
@Entity
public class Person {
@Id
@GeneratedValue
private Long id;
@NotBlank
private String name;
@ElementCollection(fetch = FetchType.EAGER)
@Size(min = 1, max = 5)
private Set<String> skills = new HashSet<>();
protected Person() {
}
public Person(final String name, final Collection<String> skills) {
this.name = name;
this.skills.addAll(skills);
}
public void updateSkills(Collection<String> skills) {
this.skills.clear();
this.skills.addAll(skills);
}
public void updateName(final String name) {
this.name = name;
}
//getters
}
and when creating new entity with empty list of skills it will throw ConstraintValidationException as expected:
@Test(expected = ConstraintViolationException.class)
public void shouldFailWhenSkillsAreEmpty() {
//given
Person person = new Person("gucio", Collections.EMPTY_LIST);
//when
personRepository.save(person);
//then
}
however when doing same - storing empty list on entity update (merge underhood? not sure) it will pass while I would expect exception:
@Test(expected = ConstraintViolationException.class)
public void shouldFailWhenUpdateSkillsToEmpty() {
//given
Person person = new Person("gucio", Arrays.asList(JAVA, SQL));
person = personRepository.save(person);
person.updateSkills(Collections.EMPTY_LIST);
//when
personRepository.save(person);
//then
}
I have wrote test with manually created validator and validate such Person and as expected it returns 1 ConstraintViolation for field skills:
You can easily take a look into a sample project:
https://github.com/konczak/demo-skills-validation-issue
I understood that there is a difference under save method for transient and attached/detached entity but still I would expect validation for updating/merging. Again strange thing is that it will validate field name for blank value on update - it throws different exception but a original cause is ConstraingViolationException.
What am I missing or misunderstood in this case?