Spring-data-jpa最全的查询语法总结,直入超神

🤵‍♂️ 个人主页:@香菜的个人主页

✍🏻作者简介:csdn 认证博客专家,游戏开发领域优质创作者,华为云享专家,2021年度华为云年度十佳博主

🐋 希望大家多多支持,我们一起进步!😄

如果文章对你有帮助的话,

欢迎评论 💬点赞👍🏻 收藏 📂加关注+

系列文章:Spring Boot学习大纲,可以留言自己想了解的技术点

前言

之前文章已经写过一次spring data,链接:spring-data 一统江湖,玩转多种数据源

主要的内容可以参考官方的:Spring Data JPA - Reference Documentation

今天这篇文章总结下spring data jpa的查询语法,在开发中能够灵活使用,在开始下面的之前我们定义一个entity,以便后面的部分使用

这里定义一个玩家的entity

@Data
@Entity
@Table(name = "player_info")
@ApiModel(description = "玩家信息")
public class PlayerEntity implements Serializable {private static final long serialVersionUID = 1L;   @Id    @Column(name = "id", nullable = false)@GeneratedValue(strategy = GenerationType.IDENTITY)@ApiModelProperty(value = "主键")@JsonProperty(access = JsonProperty.Access.WRITE_ONLY)private Integer id;        @ApiModelProperty(value = "玩家名字")@Column(name = "player_name")private String playerName; @ApiModelProperty(value = "玩家类型")@Column(name = "player_type")private String playerType;}

1、方法命名查询

这种方式是最简单的,也是最方便的,可能也是很多人包括我选择spring data jpa的主要原因之一,通过简单的组合就可以实现查询

1.1 例子几步走

1.1.1 声明一个扩展 Repository 的接口或其子接口之一

这里的entity使用PlayerEntity ,主键是用Integer

interface PlayerRepository extends Repository<PlayerEntity, Integer> { … }

1.1.2 声明查询方法

interface PlayerRepository extends Repository<PlayerEntity, Integer> {List<PlayerEntity> findByPlayerName(String playerName);
}

1.2 查询语法

按照Spring Data JPA 定义的规则,查询方法以findBy开头,涉及条件查询时,条件的属性用条件关键字连接,要注意的是:条件属性首字母需大写。框架在进行方法名解析时,会先把方法名多余的前缀截取掉,然后对剩下部分进行解析。

2、SQL查询

这个是常用的一种方式,直接使用sql查询,使用query注解,并且nativeQuery = true,直白点就是使用sql查询

方法名可以根据自己习惯进行命名

public interface PlayerDao extends JpaRepository<PlayerEntity, Integer>, JpaSpecificationExecutor<PlayerEntity>{@Query(value = "SELECT max(0 + SUBSTR( player_id, 3 )) FROM parking_info WHERE LEFT ( player_id, 2 ) = :zoneId", nativeQuery = true)int getMaxPlayerId(String zoneId);}

这里的问题是没办法在开发的时候做语法检查,只能在调试中进行检查

3、JPQL查询

和原生SQL语句类似,并且完全面向对象,通过类名和属性访问,而不是表名和表的属性。

这个和上面的区别在于nativeQuery = false,当然默认也是false,

@Query(value = "select companyCode from PlayerEntity where playerId = :playerId")
String findCompanyCodeByPlayerId(String playerId);

一定要注意,这里的字段和类名都是类中定义的

4、复杂查询 Specification

4.1 接口说明

需要Spring Data Jpa 支持 Criteria 查询方式,使用这种方式需要继承 JpaSpecificationExecutor 接口,该接口提供了如下一些方法

JpaSpecificationExecutor这个接口基本是围绕着Specification接口来定义的

public interface Specification<T> extends Serializable {long serialVersionUID = 1L;static <T> Specification<T> not(@Nullable Specification<T> spec) {return spec == null ? (root, query, builder) -> {return null;} : (root, query, builder) -> {return builder.not(spec.toPredicate(root, query, builder));};}static <T> Specification<T> where(@Nullable Specification<T> spec) {return spec == null ? (root, query, builder) -> {return null;} : spec;}default Specification<T> and(@Nullable Specification<T> other) {return SpecificationComposition.composed(this, other, CriteriaBuilder::and);}default Specification<T> or(@Nullable Specification<T> other) {return SpecificationComposition.composed(this, other, CriteriaBuilder::or);}@NullablePredicate toPredicate(Root<T> root, CriteriaQuery<?> query, CriteriaBuilder criteriaBuilder);
}

通常来说我们一般使用toPredicate方法

Root:查询的根对象(查询的任何属性都可以从更对象获取)

CriteriaQuery:顶层查询对象,自定义查询方式(了解,一般不用)

CriteriaBuilder:查询构造器,封装了很多查询条件

4.2 看个官方的例子

4.2.1 定义查询条件

public class CustomerSpecs {public static Specification<Customer> isLongTermCustomer() {return (root, query, builder) -> {LocalDate date = LocalDate.now().minusYears(2);return builder.lessThan(root.get(Customer_.createdAt), date);};}public static Specification<Customer> hasSalesOfMoreThan(MonetaryAmount value) {return (root, query, builder) -> {// build query here};}
}

4.2.2 调用查询方法

List<Customer> customers = customerRepository.findAll(isLongTermCustomer());

4.2.3 项目中使用方法

 Sort sort;if (order == null){sort = Sort.unsorted();}else {sort = Sort.by(order? Sort.Direction.DESC:Sort.Direction.ASC,"totalParkingSpace");}Pageable pageable = PageRequest.of(page, size,sort);Specification<ParkingInfoEntity> sp = (root, query, cb) -> {List<Predicate> condition = new ArrayList<>();if (parkingType != null) {Predicate parkingTypePredicate = cb.equal(root.get("parkingType"), parkingType);condition.add(parkingTypePredicate);}if (StringUtils.hasText(keyword)) {String likeKeyword = "%" + keyword + "%";Predicate parkingId = cb.like(root.get("parkingId"), likeKeyword);Predicate parkingName = cb.like(root.get("parkingName"), likeKeyword);Predicate parkingAddress = cb.like(root.get("parkingAddress"), likeKeyword);Predicate belongCompany = cb.like(root.get("belongCompany"), likeKeyword);Predicate or = cb.or(parkingId, parkingName, parkingAddress, belongCompany);condition.add(or);}return cb.and(condition.toArray(new Predicate[0]));};Page<ParkingInfoEntity> all = parkingInfoDao.findAll(sp, pageable);

注:这种方式主要应用在复杂条件查询时候,可以简单的理解为手动拼接sql,只不过这里更安全,更不容易出错。

用过的都说好

4.3 调用数据库内置函数

CriteriaBuilder还提供了function方法,在function方法里可以直接传方法名进去

/**
name: 方法名
returnType: 返回类型
arguments:表达式
**/
public <T> Expression<T> function(String name, Class<T> returnType, Expression... arguments) {return new ParameterizedFunctionExpression(this, returnType, name, arguments);}

调用代码如下

Expression<BigDecimal> round = cb.function("round", BigDecimal.class, quot);
cb.greaterThanOrEqualTo(round, 80)

5、QueryByExampleExecutor

它允许动态查询创建,并且不需要编写包含字段名称的查询

5.1 用法

Query by Example API 由四部分组成

  • 实例,entity的实例
  • ExampleMatcher,ExampleMatcher包含有关如何匹配特定字段的详细信息。它可以在多个示例中重复使用。
  • Example,查询用的对象,包含查询的匹配方式和字段的值(entity实例)

5.2 实例

它用于创建查询

Person person = new Person();                          
person.setFirstname("Dave");                           ExampleMatcher matcher = ExampleMatcher.matching()     .withIgnorePaths("lastname")                         .withIncludeNullValues()                             .withStringMatcher(StringMatcher.ENDING);            
Example<Person> example = Example.of(person, matcher);

6、总结

简单查询使用 查询方法组合

复杂查询使用SQL查询和JPQL查询

动态查询使用Specification和Example API

在工作中根据自己的需求选择对应的方式

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/351752.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

0x0000007b电脑蓝屏的解决方法

AHCI是高级主机控制接口&#xff0c;可以发挥SATA硬盘潜在的加速功能&#xff0c;尤其是固态硬盘&#xff0c;更加需要使用AHCI硬盘模式&#xff0c;开启ahci一般在安装系统之前进入BIOS进行设置&#xff0c;但是不同主板BIOS设置界面不尽相同&#xff0c;很多人都不懂bios怎么…

蓝屏0x0000007b要怎么办?有什么简单的处理方法?

遇到蓝屏0x0000007b要怎么办?相信很多人都遇到过吧?这种蓝屏其实是很让人烦恼的&#xff0c;会导致系统直接无法使用&#xff0c;今天小编就来给大家详细的说说。 一.电脑蓝屏0x0000007b怎么办 1.首先点击开机键将电脑关闭&#xff0c;然后重启电脑开机按下F10进入bios。 2.选…

出现蓝屏代码0x0000007b的原因及解决办法

出现蓝屏代码0x0000007b的原因通常是硬盘的存储控制器驱动加载错误&#xff0c;我们可以通过对BIOS界面进行修复来解决这个问题。下面小编将详细介绍解决蓝屏代码0x0000007b的方法&#xff0c;一起来看看吧 导致驱动加载错误的情况有以下三种&#xff1a; 一、无法自动识别硬盘…

有效解决应用程序无法正常启动(0xc000007b)的错误

尝试了各种办法&#xff0c;最后就这个方法非常实用&#xff01;一下子就解决了问题&#xff01;大家快来用&#xff01; 博主遇到的问题是SPSS、Origin和某些绘图软件集体失灵&#xff0c;都显示无法正常启动应用程序 知道肯定是缺少了一些东西&#xff0c;于是开始自己手动…

0xc000007b应用程序无法正常启动解决方案(亲测有效)

这种问题的出现&#xff0c;大多数都是不小心删掉了c的静态库的东西&#xff0c;解决方案有很多&#xff0c;但是都有点复杂&#xff0c;我这里提供两种方法&#xff0c;可以解决大部分用户的难题。 在这里奉劝小伙伴们一句&#xff0c;不要手欠去动系统软件哈&#xff0c;就是…

软件提示无法正常启动0xc000007b的解决方法

#软件提示无法正常启动0xc000007b的解决方法 0xc000007b问题是由于我们缺少电脑.dll运行库问题所导致的&#xff0c;所以可以 下载DirectX修复工具进行修复&#xff1a; 可修复DirectX运行库VC个版本运行库msvcp.dll等各类dll缺失问题 当初博主遇到这个问题的时候&#xff…

应用程序无法正常启动(0xc000007b)解决

注&#xff1a;本文对0xc000007b的问题本质进行了说明&#xff0c;可以说对网上杂七杂八的声音做了一个统一。 问题情景&#xff1a; vs2013 写的一个64位的exe程序&#xff0c;release后带着来自系统目录C:\Windows\SysWOW64\msvcr120.dll 到一个没有runtime的win7环境去运行&…

应用程序无法正常启动0xc00007b的解决(二)

【背景】 基于Visual Studio环境开发的程序换一个运行环境时常常出现这样的情况&#xff1a;先提示“无法启动此程序&#xff0c;因为计算机丢失**.dll。尝试重新安装该程序以解决此问题”&#xff0c;很容易想到的办法就是从原来的环境中搜索相应的**.dll&#xff0c;然后放到…

应用程序无法正常启动,提示错误代码0xc000007b怎么办?

许多用户在访问《FIFA》、《孤岛惊魂》、《使命召唤》等游戏或其他应用程序时&#xff0c;收到了0xc000007b错误&#xff0c;提示“应用程序无法正常启动(0xc000007b)”。 导致错误代码0xc000007b的原因有很多&#xff0c;小编列出的是相对常见的原因&#xff1a; 1、当你尝试启…

0xc000007b的解决办法(续)

最后更新&#xff1a;2021-3-1 请大家首先确定已经按照原文的方法及步骤尝试过&#xff0c;但是还是没有解决问题再来看这篇文章。如果你还没有看过原文&#xff0c;请先看原文&#xff1a; http://blog.csdn.net/VBcom/article/details/6070705 看到这里的朋…

零基础如何入门网络安全(黑客)

给大家一个忠告&#xff0c;如果你完全没有基础的话&#xff0c;前期最好不要盲目去找资料学习&#xff0c;因为大部分人把资料收集好之后&#xff0c;基本上都是放在收藏夹吃灰&#xff0c;同时资料收集的多了&#xff0c;学起来就会迷茫&#xff0c;也会让自己很有压力。 第…

Nginx之location与rewrite

Nginx之location与rewrite 一.location location 对访问的路径做访问控制或者代理转发1.匹配分类 精准匹配&#xff1a; location / {...} 前缀匹配&#xff1a; location ^~ / {...} 正则匹配&#xff1a; location ~ / {...} location ~* / {...} 部分…

gismo-3维IGA

文章目录 前言一、简单示例二、gismo-3维IGA3维程序中的几何模型 三、xml文件的理解1、xml文件示例2、gismo中二维示例文件-一个曲面&#xff08;简单&#xff09; 四、三维程序中xml文件的理解三维几何模型边界信息 五、三维程序运行细化四次细化5次 总结 #pic_center 前言 只…

30天从入门到精通TensorFlow1.x 第四天,TensorFlow中的计算图或数据流图

文章目录 一、接前一天二、计算图或数据流图1. 什么是计算图或者数据流图2. 为什么需要计算图或者数据流图3. 执行顺序和延迟加载在tf中的使用 一、接前一天 这几天主要学习了张量的创建方法&#xff0c;以及变量&#xff0c;变量命名域共享变量等概念。今天主要熟悉 数据流图…

通达信l1l2行情接口-十档行情有哪些优势?

据提供系统或用户编制的条件选股公式进行选股选定一个条件选股公式或多个组合条件后&#xff0c;计算机自动帮您选出当时或历史上某一段时间内满足条件的所有股票十档行情 英文&#xff0c;列在行情下载显示窗口&#xff0c;同时可保留成板块。 那通达信l1l2行情接口-十档行情…

ciscn 2023 初赛 pwn shell we go

ciscn 2023 初赛 pwn shell we go 这题go pwn&#xff0c;符号恢复就恢复很长时间了&#xff0c;网上的插件好多都没用 根着流程&#xff0c;可以看到这里有一个验证&#xff0c;以空格来分割&#xff0c;第一个参数会验证是否为nAcDsMicN 如果第一个参数验证通过&#xff0c…

[AHK]获取通达信软件上的股票代码

PC上的股票交易软件的自动止损、自动下单等功能比较弱&#xff0c;不如期货交易软件。 自力更生&#xff0c;程序员都是自己打造工具。 根据IPO模型&#xff08;Input 输入&#xff0c;Process处理&#xff0c;Output输出&#xff09;&#xff0c;为了方便自动化首先要获取当…

(十)服务器K8S集群部署SpringBoot项目实战

1.准备springboot项目 可以在 https://start.spring.io/网站准备一个项目&#xff0c;这里作为k8s的学习所以springboot项目中准备一个简单的访问接口即可。 2.服务器环境准备 安装Jdk 1.更新系统软件包&#xff1a; sudo yum update2.安装 OpenJDK 11&#xff1a; sudo…

毕业三年,自学软件测试到就业,我用了4个月

我转行的经历 17年毕业&#xff0c;普通专科&#xff0c;通信专业。 当初选择这个专业是因为有一个校企合作&#xff0c;承诺学生毕业之后给学生安排就业&#xff0c;在学校里面混了三年之后&#xff0c;学校也是履行了当初安排就业的承诺&#xff0c;给我“发配”到了上海&a…

Python数据攻略-DataFrame的数据计算和整理

大家好&#xff0c;我是Mr数据杨。今天&#xff0c;我们要踏上一场探索Python的旅程&#xff0c;途中我们将讲解算术运算、NumPy和SciPy函数的应用、DataFrame的排序、过滤、统计和遍历等技巧。想象一下如果《三国演义》中的诸葛亮有了Python的帮助&#xff0c;他将如何更有效地…