Spring Boot 3 與 Hibernate JPA 教學(二) ORM是甚麼

Spring Boot 3 搭配 Hibernate JPA 開發專案,資料庫的部分採用 ORM。

ORM 代表物件/關聯映射,是一種將物件導向程式設計 (OOP) 語言中的物件自動映射到關聯式資料庫中的資料表的技術。 ORM 允許程式設計師使用物件導向的方法執行資料庫操作。這提供了透過物件導向的方法執行資料庫操作的能力,同時將資料庫中的表格對應到Java類別。

ORM 具有以下優點

• 它簡化了資料庫操作。 ORM 使開發人員無需編寫資料庫查詢。

• 改進資料庫設計。 ORM 使開發人員能夠專注於資料庫設計。

• 提高資料庫效能。 ORM可以最佳化資料庫查詢。

ORM可以分為以下兩大類

Full ORM:Full ORM 讓開發人員充分利用OOP 語言的特性來執行資料庫操作。

• Semi-ORM:Semi-ORM部分利用OOP語言的特性,為開發人員進行資料庫操作

Hibernate實體註解( Annotation )與映射

Hibernate 是一個基於 Java 的 ORM(物件關聯映射)框架,並使用各種註解將資料庫表映射到 Java 類別。這些註解告訴 Hibernate 哪個類別對應於哪個資料表以及欄位(屬性)如何對應。以下是一些基本的 Hibernate 註解以及如何使用這些註解進行基本映射:

@Entity註解

這個註解顯示一個類別是一個Hibernate實體類別。因此,此類將與資料庫表關聯。

@Table註解

此註釋指示實體對應於哪個資料庫表。如果不指定表名,則預設使用類別名。

@Id 和 @GenerateValue 註解

這些註解指示什麼屬性是主鍵以及如何建立它。可以使用 @GenerateValue 指定策略(IDENTITY、SEQUENCE、AUTO 等)

@Column註解

此註解指定資料庫中欄位(屬性)欄位的名稱、類型和其他屬性。

參數設定對象說明
nameTable 的欄位名稱針對同一個欄位,我們可以在實體類別與 table,分別使用不同的名稱。
length字串長度超出的部份會被截斷(truncate)。
nullable值是否可為 nullJava 基本型態預設為 false;參考型態預設為 true。
unique值是否唯一Java 基本型態預設為 false;參考型態預設為 true。
precision整數與小數的總位數適用於 Java 的 BigDecimal 型態;MySQL 的 DECIMAL 型態。
scale小數在 precision 所佔的位數適用於 Java 的 BigDecimal 型態;MySQL 的 DECIMAL 型態。
@Column 使用說明

Spring Boot 3 上撰寫 ORM 的程式

先在專案的「src\main\resources」路徑下,找到「application.properties」的檔案,並在裡頭配置數個參數。

# 資料來源
spring.datasource.url=jdbc:mysql://localhost:3306/spdb
spring.datasource.username=spdbuser
spring.datasource.password=1234
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver

# 資料庫資訊
spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.MySQLDialect
spring.jpa.properties.hibernate.dialect_version=8
spring.jpa.properties.hibernate.dialect.storage_engine=innodb

# 資料表配置
spring.jpa.hibernate.ddl-auto=update

# 是否在 console 印出 SQL 指令並對其格式化
spring.jpa.properties.hibernate.show_sql=true
spring.jpa.properties.hibernate.format_sql=true

Spring Data JPA 允許我們在程式中直接定義資料表(table),並可在啟動 Spring Boot 程式時,控制 Hibernate 自動去配置 table。有以下幾個選項。

spring.jpa.hibernate.ddl-auto

  • create:重新建立 table,故原有的資料會遺失,請慎用。
  • create-drop:同 create,且程式關閉後,會自動刪除 table。
  • update:會根據我們的定義去更新 table,補上新欄位,但不刪除舊欄位。
  • validate:會檢查 table 是否缺少我們在程式中定義的欄位。若有,則拋出例外,具有提醒的效果。
  • none:不做自動配置。

建立專用的 package

請建立專用的 package: com.example.myjpa.entity

未來建立的 entity 都放在此 package 中。

Spring boot 3 中 entity 專用的資料夾

建立 MyBook.java

建立書籍的物件,有 id ,書名,價格,出版日期 等欄位

package com.example.myjpa.entity;

import java.time.LocalDate;

import jakarta.persistence.Column;
import jakarta.persistence.Entity;
import jakarta.persistence.GeneratedValue;
import jakarta.persistence.GenerationType;
import jakarta.persistence.Id;
import jakarta.persistence.Table;

@Entity
@Table(name = "mybook")
public class MyBook {

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

    @Column(name = "name", length = 30, unique = true, nullable = false)
    private String name;//書名
    
    @Column(name = "price")
    private int price;//價格
    
    @Column(name = "publicationDate", nullable = false)
    private LocalDate publicationDate;//出版日期
    
    // getter, setter ...
    
}

Spring Boot 3 啟動吧

Spring Boot 3 啟動之後,可以觀察一下產生出來的 log 訊息

Spring Boot 3 JPA log

可以看到有產生 table 的 SQL 語法

Table: mybook 順利被建立起來囉

MyBook.java 增加欄位

增加出版社的欄位 publishingHouse

@Column(name = “publishingHouse”, length = 50, unique = true, nullable = false)
private String publishingHouse;

重新啟動 Srping Boot 3

Spring Boot 3 JPA 增加欄位的 SQL語法

可以看到 alert 的 sql 語法,增加了出版社的欄位