SpringBoot整合系列-整合JPA
出處地址:https://www.cnblogs.com/V1haoge/p/9959865.html
SpringBoot整合JPA進行資料庫開發
步驟
第一步:新增必要的jar包
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-jpa</artifactId></dependency><dependency> <groupId>com.querydsl</groupId> <artifactId>querydsl-apt</artifactId> <version>${querydsl.version}</version> <scope>provided</scope></dependency><dependency> <groupId>com.querydsl</groupId> <artifactId>querydsl-jpa</artifactId> <version>${querydsl.version}</version></dependency>
第二步:新增必要的配置
spring.datasource.url = jdbc:h2:file:D:\testdb;DB_CLOSE_ON_EXIT=FALSE spring.datasource.username = sa spring.datasource.password = sa spring.datasource.driverClassName =org.h2.Driver
第三步:新增實體,並新增註解
@Entity @Table(name = "USER")public class User { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private int useId; @Column private String useName; @Column private UseSex useSex; @Column private int useAge; @Column(unique = true) private String useIdNo; @Column(unique = true) private String usePhoneNum; @Column(unique = true) private String useEmail; @Column private LocalDateTime createTime; @Column private LocalDateTime modifyTime; @Column private UseState useState; }
第四步:新增持久層
@Repository public interface UserRepository extends JpaRepository { }
注意:
繼承自JpaRepository的持久層可以直接使用其定義好的CRUD操作,其實只有增刪查操作,關於修改的操作還是需要自定義的。
第五步:持久層的使用
@Service public class UserService { @Autowired private UserRepository repository; public ResponseEntity addUser(final User user) { return new ResponseEntity<>(repository.save(user),HttpStatus.OK); } }
注意:其實在JpaRepository中已經定義了許多方法用於執行實體的增刪查操作。
JPA高階功能
方法名匹配
在UserRepository中定義按照規則命名的方法,JPA可以將其自動轉換為SQL,而免去手動編寫的煩惱,比如定義如下方法:
User getUserByUseIdNo(String useIdNo);
JPA會自動將其轉換為如下的SQL:
select * from USER where use_id_no = ?
下面簡單羅列方法命名規則:
關鍵字 | 例子 | sql |
---|---|---|
And | findByNameAndAge | ...where x.name=?1 and x.age=?2 |
Or | findByNameOrAge | ...where x.name=?1 or x.age=?2 |
Between | findByCreateTimeBetween | ...where x.create_time between ?1 and ?2 |
LessThan | findByAgeLessThan | ...where x.age < ?1 |
GreaterThan | findByAgeGreaterThan | ...where x.age > ?1 |
IsNull | findByAgeIsNull | ...where x.age is null |
IsNotNull,NotNull | findByAgeIsNotNull | ...where x.age not null |
Like | findByNameLike | ...where x.name like ?1 |
NotLike | findByNameNotLike | ...where x.name not like ?1 |
OrderBy | findByAgeOrderByNameDesc | ...where x.age =?1 order by x.name desc |
Not | findByNameNot | ...where x.name <>?1 |
In | findByAgeIn | ...where x.age in ?1 |
NotIn | findByAgeNotIn | ...where x.age not in ?1 |
@Query註解
使用@Query註解在介面方法之上自定義執行SQL。
@Modifying@Query(value = "update USER set USE_PHONE_NUM = :num WHERE USE_ID= :useId", nativeQuery = true)void updateUsePhoneNum(@Param(value = "num") String num, @Param(value = "useId") int useId);
上面的更新語句必須加上@Modifying註解,其實在JpaRepository中並未定義更新的方法,所有的更新操作均需要我們自己來定義,一般採用上面的方式來完成。
/** * 表示一個查詢方法是修改查詢,這會改變執行的方式。只在@Query註解標註的方法或者派生的方法上新增這個註解,而不能 * 用於預設實現的方法,因為這個註解會修改執行方式,而預設的方法已經繫結了底層的APi。 */@Retention(RetentionPolicy.RUNTIME)@Target({ ElementType.METHOD, ElementType.ANNOTATION_TYPE })@Documentedpublic @interface Modifying { boolean flushAutomatically() default false; boolean clearAutomatically() default false; }
JPQL(SQL拼接)
使用JPQL需要在持久層介面的實現列中完成,即UserRepositoryImpl,這個類是UserRepository的實現類,我們在其中定義JPQL來完成複雜的SQL查詢,包括動態查詢,連表查詢等高階功能。
QBE(QueryByExampleExecutor)
使用QBE來進行持久層開發,需要用到兩個介面類,Example和ExampleMatcher,開發方式如下:
List users = repository.findAll(Example.of(user));
或者配合ExampleMarcher使用:
ExampleMatcher matcher = ExampleMatcher.matching().withIgnoreCase(); List users = repository.findAll(Example.of(user, matcher));
以上邏輯一般位於service之中。其中user模型中儲存著查詢的條件值,null的欄位不是條件,只有設定了值的欄位才是條件。ExampleMatcher是用來自定義欄位匹配模式的。
處理列舉
使用Spring-Data-Jpa時,針對列舉的處理有兩種方式,對應於EnumType列舉的兩個值:
public enum EnumType { /** Persist enumerated type property or field as an integer. */ ORDINAL, /** Persist enumerated type property or field as a string. */ STRING }
其中ORDINAL表示的是預設的情況,這種情況下將會將列舉值在當前列舉定義的序號儲存到資料庫,這個需要是從0開始計算的,正對應列舉值定義的順序。STRING表示將列舉的名稱儲存到資料庫中。
前者用於儲存序號,這對列舉的變更要求較多,我們不能隨便刪除列舉值,不能隨意更改列舉值的位置,而且必須以0開頭,而這一般又與我們定義的業務序號不一致,限制較多,一旦發生改變,極可能造成業務混亂;後者較為穩妥。
正常情況下,如果不在列舉欄位上新增@Enumerated註解的話,預設就以ORDINAL模式儲存,若要以STRING模式儲存,請在列舉欄位上新增如下註解:
@Enumerated(EnumType.STRING)@Column(nullable=false) // 一般要加上非null約束private UseState useState;
分頁功能
Spring-Data-Jpa中實現分頁使用到了Pageable介面,這個介面將作為一個引數參與查詢。
Pageable有一個抽象實現類AbstractPageRequest,是Pageable的抽象實現,而這個抽象類有兩個實現子類:PageRequest和QPageRequest,前者現已棄用,現在我們使用QPageRequest來定義分頁引數,其有三個構造器:
public QPageRequest(int page, int size) { this(page, size, QSort.unsorted()); }public QPageRequest(int page, int size, OrderSpecifier<?>... orderSpecifiers) { this(page, size, new QSort(orderSpecifiers)); }public QPageRequest(int page, int size, QSort sort) { super(page, size); this.sort = sort; }
在這裡面我們可以看到一個QSort,這個QSort是專門用於與QPageRequest相配合使用的類,用於定義排序規則。預設情況下采用的是無排序的模式,即上面第一個構造器中的描述。
要構造一個QSort需要藉助querydsl
來完成,其中需要OrderSpecifier來完成。
這裡有個簡單的用老版本實現的分頁查詢:
public ResponseEntity<Page<User>> getUserPage(final int pageId) { Sort sort = new Sort(new Sort.Order(Sort.Direction.DESC, "useId")); Page<User> users = repository.findAll(new PageRequest(pageId,2, sort)); return new ResponseEntity<>(users, HttpStatus.OK); }
至於新版本的分頁查詢和排序涉及內容較多較複雜,稍後再看。
注意:分頁首頁頁碼為0
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/4650/viewspace-2817644/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- SpringBoot整合Spring Data JPASpring Boot
- SpringBoot整合系列-整合H2Spring Boot
- SpringBoot整合系列–整合MyBatis-plusSpring BootMyBatis
- Spring Data JPA系列2:SpringBoot整合JPA詳細教程,快速在專案中熟練使用JPASpring Boot
- SpringBoot資料訪問(二) SpringBoot整合JPASpring Boot
- SpringSession系列-整合SpringBootGseSessionSpring Boot
- SpringBoot第九篇:整合Spring Data JPASpring Boot
- Spring Data JPA(二):SpringBoot整合H2Spring Boot
- ElasticSearch與SpringBoot的整合與JPA方法的使用ElasticsearchSpring Boot
- SpringBoot 實踐系列-整合 RocketMQSpring BootMQ
- Flowable實戰(六)整合JPA
- 個人學習系列 - SpringBoot整合RabbitMQSpring BootMQ
- SpringBoot系列——MyBatis-Plus整合封裝Spring BootMyBatis封裝
- SpringBoot系列(六)整合thymeleaf詳解版Spring Boot
- MySQL-SpringBoot整合JPA實現資料讀寫分離MySqlSpring Boot
- hibernate及SpringBoot整合Jpa實現對資料庫操作Spring Boot資料庫
- 【springboot】學習4:整合JDBC、整合druid、整合mybatis、整合 SpringSecuritySpring BootJDBCUIMyBatisGse
- Spring同時整合JPA與MybatisSpringMyBatis
- Spring Boot:整合Spring Data JPASpring Boot
- [Redis 客戶端整合] SpringBoot 整合 LettuceRedis客戶端Spring Boot
- [Redis 客戶端整合] SpringBoot 整合 JedisRedis客戶端Spring Boot
- SpringBoot 整合 rabbitmqSpring BootMQ
- SpringBoot 整合 elkSpring Boot
- SpringBoot 整合 elasticsearchSpring BootElasticsearch
- SpringBoot 整合 apolloSpring Boot
- springboot整合redis?Spring BootRedis
- SpringBoot整合RedisSpring BootRedis
- flowable 整合 springbootSpring Boot
- SpringBoot整合MQTTSpring BootMQQT
- ElasticSearch 整合 SpringBootElasticsearchSpring Boot
- SpringBoot整合ESSpring Boot
- Springboot整合pagehelperSpring Boot
- springBoot整合thymeleafSpring Boot
- SpringBoot 整合 RedisSpring BootRedis
- SpringBoot整合NacosSpring Boot
- SpringBoot 整合 dockerSpring BootDocker
- Springboot整合RabbitMQSpring BootMQ
- springBoot整合flowableSpring Boot