Spring应用中CrudRepository统计去重手机号数量失效问题
解决Spring Data JPA统计Distinct Mobile的需求(无需原生SQL)
嘿,我来帮你搞定这个问题!你不用写原生SQL也能轻松实现统计指定customer_id下不同mobile数量的需求,Spring Data JPA提供了两种很方便的方式:
方法一:利用Spring Data JPA的方法命名约定
Spring Data JPA可以根据方法名自动生成对应的查询语句,完全不用手动写SQL。你只需要在你的CrudRepository接口里定义一个符合命名规则的方法就行:
public interface CustomerContactRepository extends CrudRepository<CustomerContact, Long> { // 方法名会自动生成统计distinct mobile的查询 long countDistinctMobileByCustomerId(Long customerId); }
这个方法的命名逻辑很清晰:
count表示要做统计操作DistinctMobile指定统计的是去重后的mobile字段ByCustomerId表示过滤条件是匹配传入的customerId参数
调用这个方法时,Spring Data JPA会自动生成等价于你目标SQL的JPQL,返回的就是指定customerId下不重复的mobile数量。
方法二:使用JPQL的@Query注解(非原生)
如果觉得方法名太长,或者需要更灵活的查询逻辑,你可以用JPQL写查询语句(这是基于实体类的查询语言,不是原生SQL):
import org.springframework.data.jpa.repository.Query; import org.springframework.data.repository.CrudRepository; import org.springframework.data.repository.query.Param; public interface CustomerContactRepository extends CrudRepository<CustomerContact, Long> { @Query("SELECT COUNT(DISTINCT cc.mobile) FROM CustomerContact cc WHERE cc.customerId = :customerId") long countDistinctMobileByCustomerId(@Param("customerId") Long customerId); }
这里要注意几个细节:
- JPQL里引用的是实体类名(
CustomerContact)和实体类的属性名(mobile、customerId),不是数据库的表名和列名 :customerId是参数占位符,配合@Param注解绑定传入的参数- 这个查询会被Spring Data JPA自动转换成对应的SQL,实现去重统计的效果
小提示
要确保你的CustomerContact实体类里的mobile和customerId属性正确映射到数据库的mobile和customer_id列,如果列名和属性名不一致,可以用@Column注解指定,比如:
@Column(name = "customer_id") private Long customerId;
内容的提问来源于stack exchange,提问作者Devratna
相关产品推荐
相关产品推荐

