Spring数据查询方法

时间:2020-01-09 10:44:33  来源:igfitidea点击:

在本文中,我们将了解如何在Spring Data中为存储库接口方法生成查询,以及在Spring Data中针对查询方法的所有选项。

定义查询方法

在Spring Data Repository代理中,有两种方法可从方法名称派生持久存储特定的查询:

  • 通过直接从方法名称派生查询。

  • 通过使用手动定义的查询。

可用选项还取决于所使用的持久性存储。

Spring数据中的查询查找策略

以下策略可用于存储库基础结构来解决查询。使用XML配置,我们可以通过query-lookup-strategy属性在名称空间中配置策略。对于Java配置,可以使用Enable $ {store} Repositories注释的queryLookupStrategy属性。

可以使用具有以下值的Enum QueryLookupStrategy.Key访问可用的查询查找策略:

  • 创建-如果使用此选项,则Spring框架尝试根据查询方法名称自动构造查询。

  • USE_DECLARED_QUERY –对于此选项,Spring框架尝试查找声明的查询。该查询可以由@NamedQuery(与Spring Data JPA结合使用)或者@Query之类的注释定义。

  • CREATE_IF_NOT_FOUND –这是默认选项,它结合了CREATE和USE_DECLARED_QUERY。它首先查找一个声明的查询,如果找不到声明的查询,它将创建一个基于名称的自定义方法查询。

使用带有@EnableJpaRepositories注释的queryLookupStrategy属性的示例。

@Configuration
@EnableJpaRepositories(basePackages = "com.theitroad.springproject.dao", queryLookupStrategy=Key.CREATE)
@EnableTransactionManagement
@PropertySource("classpath:config/db.properties")
public class JPAConfig {
	...
	...

}

在Spring Data中创建查询

通过扩展Spring Data的Repository接口(如CrudRepository,JpaRepository,ReactiveCrudRepository),我们可以直接访问一组CRUD操作(即保存,saveAll,findById,findAll,findAllById,计数,删除,deleteById等)。我们还可以添加自定义查询方法,如EmployeeRepository的以下定义中所给。

public interface EmployeeRepository extends CrudRepository<Employee, Integer> {
	List<Employee> findByLastName(String lastName);
}

当Spring Data看到扩展其Repository标记接口的接口时,查询执行引擎会在运行时为这些接口创建代理实例。它扫描每个方法,并解析其方法签名。解析机制从方法中剥离前缀find ... By,Read ... By,query ... By,count ... By,get ... By,然后开始解析其余部分。

例如,在没有自定义方法findByLastName的情况下,看到findBy将解析该方法的其余部分,并开始在域类(Employee)中寻找相同的属性名称。因为它可以看到Employee具有lastName属性,所以它现在具有足够的信息来知道如何为该特定方法创建查询。

方法名称可能包含其他表达式,例如Distinct,用于在要创建的查询上设置不同的标志。但是,方法名称中的第一个" By"用作分隔符,以指示实际标准的开始。

下表描述了JPA支持的关键字以及包含该关键字的方法所转换的含义:

关键字示例JPQL代码段
AndfindByLastnameAndFirstname… where x.lastname = ?1 and x.firstname = ?2
OrfindByLastnameOrFirstname… where x.lastname = ?1 or x.firstname = ?2
Is,EqualsfindByFirstname, findByFirstnameIs, findByFirstnameEquals… where x.firstname = ?1
BetweenfindByStartDateBetween… where x.startDate between ?1 and ?2
LessThanfindByAgeLessThan… where x.age < ?1
LessThanEqualfindByAgeLessThanEqual… where x.age <= ?1
GreaterThanfindByAgeGreaterThan… where x.age > ?1
GreaterThanEqualfindByAgeGreaterThanEqual… where x.age >= ?1
AfterfindByStartDateAfter… where x.startDate > ?1
BeforefindByStartDateBefore… where x.startDate < ?1
IsNullfindByAgeIsNull… where x.age is null
IsNotNull,NotNullfindByAge(Is)NotNull… where x.age not null
LikefindByFirstnameLike… where x.firstname like ?1
NotLikefindByFirstnameNotLike… where x.firstname not like ?1
StartingWithfindByFirstnameStartingWith… where x.firstname like ?1 (parameter bound with appended %)
EndingWithfindByFirstnameEndingWith… where x.firstname like ?1 (parameter bound with prepended %)
ContainingfindByFirstnameContaining… where x.firstname like ?1 (parameter bound wrapped in %)
OrderByfindByAgeOrderByLastnameDesc… where x.age = ?1 order by x.lastname desc
NotfindByLastnameNot… where x.lastname <> ?1
InfindByAgeIn(Collection<Age> ages)… where x.age in ?1
NotInfindByAgeNotIn(Collection<Age> ages)… where x.age not in ?1
TruefindByActiveTrue()… where x.active = true
FalsefindByActiveFalse()… where x.active = false
IgnoreCasefindByFirstnameIgnoreCase… where UPPER(x.firstame) = UPPER(?1)

这些运算符中的许多运算符都可以与其他受支持的持久性存储(例如MongoDB,Apache Cassandra)一起使用,但是请务必查看特定的参考指南。

在Spring数据中声明查询

要声明查询,可以在Spring Data JPA的情况下使用@NamedQuery注释。这些配置元素的查询必须使用JPA查询语言进行定义。

在这里查看使用@NamedQuery Annotation的Spring Data JPA示例SpringData JPA @NamedQuery Annotation示例

我们还可以在Repository界面中使用@Query注释查询方法。对于Spring Data JPA,Spring Data JDBC,Spring Data MongoDB,Spring Data Neo4J @Query注释可用于定义查询。确保检查特定的参考指南。

Spring Data JDBC模块仅支持使用@Query注释手动定义查询。当前不支持从方法名称中查询。