Метод Spring Data Rest @HandleBeforeCreate не вызывается

#spring #rest #spring-boot #spring-data-rest

#spring #rest #весенняя загрузка #spring-data-rest

Вопрос:

У меня есть 2 класса. Post и Comment . Сообщение @HandleBeforeCreate работает нормально, но комментарий @HandleBeforeCreate нет. Интересно, почему?

Класс PostEventHandler:

 @Component
@RepositoryEventHandler(Post.class)
public class PostEventHandler {

    @HandleBeforeCreate
    public void setPostAuthorname(Post Post) {
        System.out.println("This method called successfully!");
    }
}
  

Интерфейс PostRepository:

 @RepositoryRestResource(collectionResourceRel = "posts", path = "posts")
public interface PostRepository extends MongoRepository<Post, String> {

}
  

Нет реализации пользовательского контроллера / ресурса для Post класса. Но в моем интерфейсе репозитория комментариев у меня есть пользовательский метод, и он выглядит так:

 @RepositoryRestResource(collectionResourceRel = "comments", path = "comments")
public interface CommentRepository extends MongoRepository<Comment, String> {
    // announceId is a field in Comment class. Get method works fine
    List<Comment> findAllByAnnounceId(String announceId);
}
  

Класс CoomentEventHandler:

 @Component
@RepositoryEventHandler(Comment.class)
public class CommentEventHandler {

    @HandleBeforeCreate
    public void setCommentAuthorUsername(Comment comment) {
        System.out.println("This method never gets invoked!");
    }
}
  

Пользовательская реализация CommentController:

 @RepositoryRestController
public class CommentController {

    @Autowired
    private AnnounceRepository announceRepository;

    @Autowired
    private CommentRepository commentRepository;

    @RequestMapping(value = "/announces/{announceId}/comments", method = RequestMethod.GET)
    public ResponseEntity<List<Comment>> getAllComments(@PathVariable("announceId") String announceId) {
        System.out.println("This method called successfully with a valid PathVariable!);
        // Custom interface method works fine
        List<Comment> comments = commentRepository.findAllByAnnounceId(announceId);
        if (comments != null) {
            System.out.println("This method called successfully!);
            return new ResponseEntity<>(comments, HttpStatus.OK);
        }
        return new ResponseEntity<>(HttpStatus.NOT_FOUND);
    }   

    @RequestMapping(value = "/announces/{announceId}/comments", method = RequestMethod.POST)
    public ResponseEntity<Comment> createComment(@PathVariable("announceId") String announceId, @RequestBody Comment comment) {
        System.out.println("This method called successfully with a valid PathVariable and Comment object!");
        Announce announce = announceRepository.findOne(announceId);
        if (announce != null) {
            commentRepository.save(comment);
            announce.getCommentList().add(comment);
            announceRepository.save(announce);
            return new ResponseEntity<>(HttpStatus.CREATED);
        }
        return new ResponseEntity<>(HttpStatus.NOT_FOUND);
    }
}
  

Ответ №1:

Обработчики событий (например, аннотированные методы @HandleBeforeCreate) вызываются только при отправке HTTP-запроса на открытые конечные точки Spring Data REST. Именно по этой причине запрос POST по пути /posts запускает метод setPostAuthorname . В случае CommentController вам предоставляются пользовательские методы сопоставления запросов, и таким образом, при непосредственном вызове репозиториев методов обработчики событий никогда не будут запущены. Единственный способ, которым вы можете использовать этот подход, — это ввести компонент обработчика событий в ваш CommentController и вызвать соответствующие методы до и после вызова метода save repository ИЛИ, вызывая непосредственно из пользовательского интерфейса, я имею в виду, из клиента, и выполнить логику метода createComment из пользовательского интерфейса, выполнивОТПРАВИТЬ запрос по пути API exposed / comments.

С уважением.