简体   繁体   English

Spring数据中验证抛出ConstraintViolationException

[英]Validation in Spring Data throws ConstraintViolationException

I'm trying to implement a validation for my service based on Spring Data.我正在尝试根据 Spring 数据对我的服务实施验证。 The documentation online says, thet i would only need the annotations of javax.validation and everything should work fine.在线文档说,我只需要javax.validation的注释,一切都应该正常。 By fine I mean that if the validation failes it throws a MethodArgumentNotValidException that can be catched and handled (which should spring do by magic).我的意思是,如果验证失败,它会抛出一个可以被捕获和处理的MethodArgumentNotValidException (这应该是 spring 通过魔法完成的)。

However I'm not able to achieve this on my project, whenever I implement the validation a ConstraintViolationException inside a TransactionSystemException is thrown instead.但是,我无法在我的项目中实现这一点,每当我实施验证时,就会抛出TransactionSystemException中的ConstraintViolationException

Here is a minimal example:这是一个最小的例子:

Entity:实体:

@Entity
@Data
@NoArgsConstructor(access = AccessLevel.PROTECTED)
public class Foo {
  @Id
  UUID id = UUID.randomUUID();

  @NotBlank
  String name;
}

Repository:存储库:

public interface FooRepository extends PagingAndSortingRepository<Foo, UUID> {

}

Controller: Controller:

@RepositoryRestController
public class FooController {

  @Autowired
  FooRepository fooRepository;

  @PostMapping(value = "/foos", consumes = {MediaType.APPLICATION_JSON_VALUE, MediaTypes.HAL_JSON_VALUE})
  public @ResponseBody ResponseEntity<?> postFoo(HttpServletRequest request, @Valid @RequestBody Foo foo,
      PersistentEntityResourceAssembler resourceAssembler) {
    Foo savedFoo = fooRepository.save(foo);

    return new ResponseEntity<>(resourceAssembler.toFullResource(savedFoo), HttpStatus.CREATED);
  }
}

And the test code with which I run the code:以及我运行代码的测试代码:

@SpringBootTest
@AutoConfigureMockMvc(addFilters = false)
@AutoConfigureDataJpa
class FooTest {
  @Autowired
  MockMvc mockMvc;

  @Test
  void testPost() throws Exception {
    Foo foo = new Foo();
    assertNull(foo.getName());

    mockMvc.perform(
        post("/foos")
            .contentType(MediaType.APPLICATION_JSON)
            .content(new ObjectMapper().writeValueAsString(foo)))
        .andDo(print())
        .andExpect(status().isBadRequest());
  }
}

The Exception thrown is the following:抛出的异常如下:

Caused by: javax.validation.ConstraintViolationException: Validation failed for classes [Foo] during persist time for groups [javax.validation.groups.Default, ]
List of constraint violations:[
    ConstraintViolationImpl{interpolatedMessage='darf nicht leer sein', propertyPath=name, rootBeanClass=class Foo, messageTemplate='{javax.validation.constraints.NotBlank.message}'}
]
    at org.hibernate.cfg.beanvalidation.BeanValidationEventListener.validate(BeanValidationEventListener.java:140)
    at org.hibernate.cfg.beanvalidation.BeanValidationEventListener.onPreInsert(BeanValidationEventListener.java:80)
    at org.hibernate.action.internal.EntityInsertAction.preInsert(EntityInsertAction.java:227)
    at org.hibernate.action.internal.EntityInsertAction.execute(EntityInsertAction.java:100)
    at org.hibernate.engine.spi.ActionQueue.executeActions(ActionQueue.java:604)
    at org.hibernate.engine.spi.ActionQueue.lambda$executeActions$1(ActionQueue.java:478)

ConstraintViolationException is not related to validation. ConstraintViolationException 与验证无关。 It is because you are saving same foo object everytime you calling test method testPost().这是因为每次调用测试方法 testPost() 时,您都在保存相同的 foo object。 Everytime you are saving foo use different id.每次保存 foo 时都使用不同的 ID。 Id is the primary key and if you save more than one object with same id or primary key you will get ConstraintViolationException. Id 是主键,如果您保存多个 object 具有相同的 id 或主键,您将得到 ConstraintViolationException。

I have now found a solution, but I do not really understand it yet.我现在找到了解决方案,但我还没有真正理解它。 I will investigate this further and share my results here, if anyone can explain it to me, feel free to comment.我将进一步调查并在这里分享我的结果,如果有人可以向我解释,请随时发表评论。

I solved it by annotating my Controller with @RestController instead of @RepositoryRestController .我通过用@RestController而不是@RepositoryRestController注释我的 Controller 来解决它。

https://jira.spring.io/browse/DATAREST-593 https://jira.spring.io/browse/DATAREST-593

This soultion works for me: https://stackoverflow.com/a/44304198/4567795这个灵魂对我有用:https://stackoverflow.com/a/44304198/4567795

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 处理 spring 引导中的 javax.validation.ConstraintViolationException - handling the javax.validation.ConstraintViolationException in spring boot 为什么在抛出ConstraintViolationException(bean验证)时,Spring Data JPA给JPA实体一个id - Why is JPA entity given an id by Spring Data JPA when ConstraintViolationException thrown (bean validation) 带有 JSR 303 的 Spring Data REST 返回 RepositoryConstraintViolationException 而不是 ConstraintViolationException - Spring Data REST with JSR 303 returns RepositoryConstraintViolationException instead of ConstraintViolationException 错误javax.validation.ConstraintViolationException - Error javax.validation.ConstraintViolationException 如何在 Spring 启动 GraphQL 中实现 javax.validation.ConstraintViolationException 的异常处理程序? - How to implement exception handler for javax.validation.ConstraintViolationException in Spring boot GraphQL? spring-boot中的自定义ConstraintViolationException - Custom ConstraintViolationException in spring-boot 休眠弹簧:@ManyToMany DataIntegrityViolationException ConstraintViolationException - Hibernate Spring: @ManyToMany DataIntegrityViolationException ConstraintViolationException 合并并保存更新的实体的SaveOrUpdate会引发ConstraintViolationException - Merge and saveOrUpdate of updated entity throws constraintViolationException Springboot 2 CrudRepository.save总是抛出ConstraintViolationException - Springboot 2 CrudRepository.save always throws ConstraintViolationException Spring验证抛出错误提交事务 - Spring Validation throws Error Committing Transaction
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM