SpringBootJPA詳解

一、SpringBootJPA教程

SpringBootJPA是在Spring Boot框架下的Java語言持久化框架。

使用JPA編寫數據庫訪問層,相較於mybatis優點是可以使用JPA(Java Persistence API)的各種特性,比如使用EntityManager直接進行增刪改查等。因為JPA api是javax.persistence包下的,和JavaEE耦合度較高,而Hibernate、mybatis等持久化框架是單獨的jar包,和JavaEE的耦合度較低,所以開發者可以根據自己項目的特點選擇適合的持久化框架。

SpringBootJPA相較於Hibernate框架,提供更簡潔的API接口,也更加易於使用。

// 引入Spring Boot starter用於簡化pom.xml文件
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>

二、SpringBootJPA配置多數據源

在SpringBoot項目中,配置多數據源步驟如下:

1、定義數據源

@Configuration
public class DataSourceConfig {

    @Bean
    @Primary
    @ConfigurationProperties("spring.datasource.one")
    public DataSource dataSourceOne(){
        return DataSourceBuilder.create().build();
    }

    @Bean
    @ConfigurationProperties("spring.datasource.two")
    public DataSource dataSourceTwo(){
        return DataSourceBuilder.create().build();
    }

}

2、配置JPA數據源

@Configuration
@EnableJpaRepositories(basePackages = "com.example.demo.repository.one",
        entityManagerFactoryRef = "entityManagerFactoryOne",
        transactionManagerRef = "transactionManagerOne")
public class JpaConfigOne {

    @Autowired
    @Qualifier("dataSourceOne")
    private DataSource dataSourceOne;

    @Bean("entityManagerFactoryOne")
    public LocalContainerEntityManagerFactoryBean setEntityManagerFactoryOne(EntityManagerFactoryBuilder builder) {
        return builder
                .dataSource(dataSourceOne)
                .packages("com.example.demo.entity.one")
                .persistenceUnit("persistenceUnitOne")
                .build();
    }

    @Bean(name = "transactionManagerOne")
    PlatformTransactionManager transactionManagerOne(EntityManagerFactoryBuilder builder) {
        return new JpaTransactionManager(setEntityManagerFactoryOne(builder).getObject());
    }
}

3、配置第二個數據源

@Configuration
@EnableJpaRepositories(basePackages = "com.example.demo.repository.two",
        entityManagerFactoryRef = "entityManagerFactoryTwo",
        transactionManagerRef = "transactionManagerTwo")
public class JpaConfigTwo {

    @Autowired
    @Qualifier("dataSourceTwo")
    private DataSource dataSourceTwo;

    @Bean("entityManagerFactoryTwo")
    public LocalContainerEntityManagerFactoryBean setEntityManagerFactoryTwo(EntityManagerFactoryBuilder builder) {
        return builder
                .dataSource(dataSourceTwo)
                .packages("com.example.demo.entity.two")
                .persistenceUnit("persistenceUnitTwo")
                .build();
    }

    @Bean(name = "transactionManagerTwo")
    PlatformTransactionManager transactionManagerTwo(EntityManagerFactoryBuilder builder) {
        return new JpaTransactionManager(setEntityManagerFactoryTwo(builder).getObject());
    }
}

三、SpringBootJPA增刪改查

通過使用繼承JpaRepository接口的方式,JPA會自動根據方法的命名規則創建具體的SQL語句,從而實現基本的CRUD操作。

public interface UserRepository extends JpaRepository<User, Long> {

    // 根據用戶名查詢用戶
    User findByUsername(String username);

    // 根據id刪除用戶
    void deleteById(Long id);

    // 根據年齡和性別查詢用戶
    List<User> findByAgeAndGender(Integer age, Boolean gender);

    // 查詢年齡大於等於18歲的用戶
    @Query("select u from User u where u.age >= ?1")
    List<User> findByAgeGreaterThanOrEqualTo(Integer age);

}

四、SpringBootJPA常用註解

1、@Entity:被映射到數據庫表的實體類,必須帶有此註解

2、@Table:指定該實體映射的表名。如果表名和實體類名相同,則此註解可省略不寫。

3、@Id:指定作為數據表主鍵的屬性,必須帶有此註解。如果主鍵屬性不確定,可以嘗試使用@IdClass註解。

4、@GeneratedValue:指定主鍵生成策略,常用的有AUTO(JPA實現依據底層數據庫主鍵自動匹配)、IDENTITY(使用數據庫自增長字段)等等。

5、@Transient:指定該屬性在數據庫中不需要映射到某個具體的數據庫字段上。

五、SpringBootJPA和Mybatis

SpringBootJPA和mybatis都可以作為持久化框架,各有優缺點。可以根據具體的情況選擇使用。比如在需要高並發情況下,mybatis的性能優勢明顯;而對於一些簡單業務場景,使用SpringBootJPA進行開發,減少了代碼的冗餘,對開發效率會有較大提升。

六、SpringBootJPA關閉懶加載

在JPA中,使用懶加載可以避免在需要時浪費太多數據庫查詢次數,但是在某些情況下,需要關閉懶加載。可以通過在查詢時使用@Query註解的join fetch語法來解決這一問題。

@Query("select u from User u join fetch u.roles where u.id = ?1")
User findByIdFetchRole(Long id);

七、SpringBootJPA不支持count

在JPA中,查詢數據時提供了眾多的查詢方式,但是唯一的缺憾就是JPA不支持count,只能使用查詢全部列表再計算數量的方式進行統計。

// 查詢全部數據
List<User> userList = userRepository.findAll();
// 查詢數據量統計
int count = userList.size();

八、SpringBootJPA自動生成表自動生成

使用SpringBootJPA可以自動生成表,也可以指定表的生成策略。

表生成策略

Hibernate底層提供很多種生成策略:

1、create:每次都會刪除原表,重新創建新表,如果表中有數據會沒有。適合測試環境使用。

2、create-drop:每次生成EntityManagerFactory時根據對應的entities和tables進行創建或者刪除表。適合測試環境使用。

3、update:Hibernate根據程序的規則映射到數據庫,並根據比較生成不同的SQL語句完成表結構的更新,以達到表結構與程序分離,表結構的更新將經過DDL語句完成,此過程被視為覆蓋式生成。適合生產環境和開發模式切換使用。

4、validate:校驗數據表中字段與entity中定義是否一致,不一致拋出異常;一致時使用。適合生產環境使用。

spring.jpa.hibernate.ddl-auto=update

九、SpringBootJPA OneToMany

在實際項目中,關於一對多關係的建模比較常見。

1、One端(單表):

@Entity
@Table(name = "t_sys_user")
public class User implements Serializable {
    private static final long serialVersionUID = -1220531363291923315L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @Column(name = "username")
    private String username;

    @Column(name = "password")
    private String password;

    @OneToMany(mappedBy = "user", cascade = CascadeType.ALL)
    private List<Role> roles;
} 

2、Many端(多表):

@Entity
@Table(name = "t_sys_role")
public class Role implements Serializable {
    private static final long serialVersionUID = 7601217352332679224L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @Column(name = "role_name")
    private String roleName;

    @Column(name = "role_code")
    private String roleCode;

    @Column(name = "remark")
    private String remark;

    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "user_id")
    private User user;
} 

user端有一個List<Role> roles,表示該user對應多個Role實體,@OneToMany表示一對多的關係。mappedBy = “user”表示該關係由Role實體的user屬性維護。

Role端則包含了一個User類型的屬性,表示該Role所對應的User實體。

可以通過user.getRoles()獲取該用戶對應的多個角色信息。

原創文章,作者:小藍,如若轉載,請註明出處:https://www.506064.com/zh-hant/n/189894.html

(0)
打賞 微信掃一掃 微信掃一掃 支付寶掃一掃 支付寶掃一掃
小藍的頭像小藍
上一篇 2024-11-29 13:52
下一篇 2024-11-29 13:52

相關推薦

  • 神經網絡代碼詳解

    神經網絡作為一種人工智能技術,被廣泛應用於語音識別、圖像識別、自然語言處理等領域。而神經網絡的模型編寫,離不開代碼。本文將從多個方面詳細闡述神經網絡模型編寫的代碼技術。 一、神經網…

    編程 2025-04-25
  • Linux sync詳解

    一、sync概述 sync是Linux中一個非常重要的命令,它可以將文件系統緩存中的內容,強制寫入磁盤中。在執行sync之前,所有的文件系統更新將不會立即寫入磁盤,而是先緩存在內存…

    編程 2025-04-25
  • Java BigDecimal 精度詳解

    一、基礎概念 Java BigDecimal 是一個用於高精度計算的類。普通的 double 或 float 類型只能精確表示有限的數字,而對於需要高精度計算的場景,BigDeci…

    編程 2025-04-25
  • Python安裝OS庫詳解

    一、OS簡介 OS庫是Python標準庫的一部分,它提供了跨平台的操作系統功能,使得Python可以進行文件操作、進程管理、環境變量讀取等系統級操作。 OS庫中包含了大量的文件和目…

    編程 2025-04-25
  • Python輸入輸出詳解

    一、文件讀寫 Python中文件的讀寫操作是必不可少的基本技能之一。讀寫文件分別使用open()函數中的’r’和’w’參數,讀取文件…

    編程 2025-04-25
  • git config user.name的詳解

    一、為什麼要使用git config user.name? git是一個非常流行的分布式版本控制系統,很多程序員都會用到它。在使用git commit提交代碼時,需要記錄commi…

    編程 2025-04-25
  • C語言貪吃蛇詳解

    一、數據結構和算法 C語言貪吃蛇主要運用了以下數據結構和算法: 1. 鏈表 typedef struct body { int x; int y; struct body *nex…

    編程 2025-04-25
  • MPU6050工作原理詳解

    一、什麼是MPU6050 MPU6050是一種六軸慣性傳感器,能夠同時測量加速度和角速度。它由三個傳感器組成:一個三軸加速度計和一個三軸陀螺儀。這個組合提供了非常精細的姿態解算,其…

    編程 2025-04-25
  • nginx與apache應用開發詳解

    一、概述 nginx和apache都是常見的web服務器。nginx是一個高性能的反向代理web服務器,將負載均衡和緩存集成在了一起,可以動靜分離。apache是一個可擴展的web…

    編程 2025-04-25
  • Linux修改文件名命令詳解

    在Linux系統中,修改文件名是一個很常見的操作。Linux提供了多種方式來修改文件名,這篇文章將介紹Linux修改文件名的詳細操作。 一、mv命令 mv命令是Linux下的常用命…

    編程 2025-04-25

發表回復

登錄後才能評論