使用Spring从控制器层调用存储库和服务

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了使用Spring从控制器层调用存储库和服务相关的知识,希望对你有一定的参考价值。

我使用Spring Boot和Spring Data。

我不介意将存储库层和服务层分开

所以我有我的UserRepository和CRUD方法以及一些Spring Data方法

  • 找到所有
  • findByUsername

我也有UserService和业务方法。

  • checkPassword(字符串登录,字符串密码)
  • businessMethodAction(String username)

这是我的问题:

在我的控制器中,我必须从UserService调用方法,有时从UserRepository调用。目前,我在我的控制器中注入了两个,我称之为服务或存储库

@Inject
UserService userService;

@Inject
UserRepository userRepository;

@RequestMapping("{username}")
private void myMethod(@PathVariable String username){
    return userRepository.findOne(username);
}

@RequestMapping("{username}/doBusineesAction")
private void myMethod(@PathVariable String username){
    return userService.doLogicalThin(username);
}

我只是问,因为我很困惑地注入两个并在同一个班级中调用一个或另一个

另一方面,这意味着要像这样在服务层中复制方法

public User findOne(String username){
 return userRepository.findOne(username);
}

你怎么看?

答案

控制器层不应该直接调用存储库。您应该始终使用服务层,因为服务层封装了围绕该调用的业务逻辑。仅仅因为目前没有任何业务逻辑,并不意味着你应该完全跳过该层。

另一答案

在我看来,服务层必须实现业务逻辑,并且必须从控制器调用它。在大多数情况下,除了从DAO对象调用方法之外,该层必须执行更多操作。如果您的应用程序具有很大的尺寸,这可能是最佳解决方案此外,您可以将逻辑分成几个部分并使其在一个事务中工作,这有助于您将数据保存在无争议状态。

另一答案

如果您的控制器不需要业务逻辑或执行单个存储库操作,则可以直接使用存储库。使用服务来实现需要业务逻辑或存储库调用编排的用例。

另一答案

正确的注释是@Autowired,而不是@Inject,如果你使用的是弹簧靴。

另一答案

如果它是一个分层的CRUD应用程序,我认为只要应用程序简单,小,控制器就可以了解存储库并直接调用它进行简单的读取操作

权衡:

  • 调用repo的控制器删除了服务层的抽象层
  • 控制器和存储库现在耦合在一起
  • 如果您的读操作没有要求/用例/业务逻辑,我建议不要推出完整的服务。 YAGNI(你不需要它)。这意味着,考虑到业务需求,在此时实现额外的“传递”服务层是没有意义的。
  • 在您选择让控制器知道您的存储库之前,我建议您考虑是否已将存储库层与持久层分离。

controller -> service -> repository -> persistence相反,controller -> repository -> persistence的结构并不是一个强硬的规则。你的用例似乎适合后者。

另一答案

一种方法是保留控制器,用于在DB的规范化实体的视图和存储库上显示的业务级概念。然后,可以定义服务以解决控制器和存储库之间的多对多关系。

以上是关于使用Spring从控制器层调用存储库和服务的主要内容,如果未能解决你的问题,请参考以下文章

Spring Boot 应用中服务层有啥用?

即使 @Transactional 放置在服务层中,Spring boot JPA 存储库也会提交代码

从 Spring MVC 控制器访问服务层

aspectj 检查 Spring Boot 中损坏的层访问

Spring Boot - 不同数据库的相同存储库和相同实体

存储库和服务层之间的区别