创建一个Spring服务

介绍

注意:此子生成器比创建完整CRUD实体的实体子生成器简单得多

该子生成器生成一个Spring Service bean,您应该在此bean中编写应用程序的业务逻辑。

生成”Bar”的Service bean, 运行:

jhipster spring-service Bar

这将生成一个BarService:很少的代码行,但是它们通常会带来很多疑问。我们尝试回答以下最常见的问题。

为什么服务类不是由“entity”生成器生成的?

这里有两个主要的架构原则:

  • 我们不想提倡创建无用的服务:如果您所需要的只是数据库上的基本CRUD,则不需要Service Bean。因此,默认情况下,JHipster不会生成它们。

  • 我们认为Service Bean比repository更解耦。Service Bean将使用多个repository在它们之上提供业务逻辑。这就是为什么无法直接使用实体生成Service Bean的原因。

我们应该在Service Bean中使用接口吗?

简而言之: No.

如果您想得到详细答案,这里是:

使用Spring的主要兴趣之一是AOP。这项技术使Spring可以在Bean之上添加新行为:例如,这就是事务或安全的工作方式。

为了添加这些行为,Spring需要在您的类上创建一个代理,并且有两种创建代理的方法:

  • 如果您的类使用接口,则Spring将使用Java提供的标准机制来创建动态代理。

  • 如果您的类不使用接口,则Spring将使用CGLIB即时生成一个新类:这不是标准的Java机制,但其工作原理与标准机制一样。

还会有人认为接口更适合编写测试,但是我们认为我们不应该为了测试的而修改我们的生产代码,而且所有新的模拟框架(例如EasyMock)都允许您创建非常好的单元测试,在没有任何接口的情况下。

因此,最后,我们发现Service Bean的接口几乎没有用,这就是为什么我们不推荐它们的原因(但是我们还是为您保留了选择生成它们的选项!)。

为什么要使用事务来获取惰性的JPA关系?

默认情况下,JPA使用一对多和多对多实体关系的惰性初始模式。如果使用此默认配置,则可能会看到可怕的LazyInitializationException:这意味着您试图在事务外部使用未初始化的关系。

由于生成的Service类默认具有@Transactional注解,因此其所有方法都是事务性的。这意味着您可以在这些业务方法中获取所有必需的惰性关系,而无不用担心遇见LazyInitializationException

提示: 如果您不修改任何数据,请在方法上使用@Transactional(readOnly = true)。这是一个不错的性能优化(Hibernate不需要刷新其一级缓存,因为我们没有进行任何修改),并且通过某些JDBC驱动程序提高了质量(Oracle不允许您发送INSERT/UPDATE/DELETE语句)

我们可以为Service Bean添加安全特性吗?

是!您的类或方法上添加Spring Security的 @Secured批注,然后使用提供的AuthoritiesConstants类即可限制对特定用户权限的访问。