上一章我們有介紹了使用傳統的JDBC去存取我們的資料庫,這樣做的缺點是我們在開發一項功能時我們就要撰寫一次的SQL語法,也會導致了我們DAO內的程式變成一個巨獸級的程式,當你有接過專案看過一個DAO內的class要存取資料庫做查詢的語法時你就會瞬間的崩潰了.
就此ORM(Object-Relational Mapping)的技術就誕生了,ORM利用了Model數據層與數據訪問層做了關聯,利用數據層的名稱直接與資料表名稱互相對應的連結起來,大部分情況我們程式存取數據庫只是在做CRUD的(新增,修改,刪除,讀取)這四樣操作而已,那像是hibernate與jpa的技術就這樣誕生了,他幫我們解決了利用程式對資料庫做這些的操作,讓我們更換資料庫時不需要在重寫一次程式碼,
相關ORM的概念你可以參考這篇文章(http://www.cnblogs.com/xiaowuzi/p/3485302.html )他對ORM做了非常詳述的解釋
介紹Spring Data JPA的原因是Spring Boot推薦使用Spring Data JPA去做ORM 持久層,原因是Spring框架
對JPA的支持度是非常的完美的,他有分頁,排序等其他的功能,可以利用程式就辦到了
我們先來介紹如何使用Spring Data JPA
加入spring-boot-starter-data-jpa依賴
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
建立一個Model
我建立一個與上個文章使用的Model名稱不同,你可以依照個人的喜好去做命名@Entity
的Bean是告訴Spring這是數據模型層的宣告
@Table
name: Table的name對映到資料庫中的資料表名稱
@Column
name: 對應到Table的欄位中的欄位名稱
@Id
: 是此資料表的Primary Key
@GeneratedValue
: 告訴此Column的生成方式 ,如果設定成GenerationType.AUTO
讓容器來自動產生
還有其他的註解用法
詳細用法你可以參照官方文件做設計如下網址
(https://docs.spring.io/spring-data/jpa/docs/current/reference/html/ )
這是Spring-Data JPA相關文件
程式碼如下圖:
package com.tutorial.Model;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
@Entity
@Table(name = "memberaccountjpa")
public class MemberAccountJPA {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private int id;
@Column(name="EMAIL")
private String email;
@Column(name="CELLPHONE")
private String cellphone;
@Column(name="PASSWORD")
private String password;
@Column(name="ADDRESS")
private String address;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getCellphone() {
return cellphone;
}
public void setCellphone(String cellphone) {
this.cellphone = cellphone;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
}
在DAO Package建立一個MemberRepository類
這是一個interface並非是一個Class
我們要讓此interface繼承JpaRepository
程式碼如下
package com.tutorial.Dao;
import java.util.List;
import org.springframework.data.jpa.repository.JpaRepository;
import com.tutorial.Model.MemberAccountJPA;
public interface MemberRepository extends JpaRepository<MemberAccountJPA, Long>{
List<MemberAccountJPA> findAll();
List<MemberAccountJPA> findByEmail(String email);
}
package com.tutorial.Controller;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import javax.sql.DataSource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import com.tutorial.Dao.MemberRepository;
import com.tutorial.Model.MemberAccountJPA;
@Controller
public class MemberController {
//透過 @RequestMapping 指定從/會被對應到此addMemberPage()方法
// @Autowired
// MemberAccount memberAccount;
//
// @Autowired
// MemberService memberService;
//
@Autowired
MemberRepository memberRepository;
@Autowired
DataSource dataSource;
@GetMapping("/addMemberPage")
public String addMemberPage(){
List<MemberAccountJPA> memberAccountJPA= new ArrayList<MemberAccountJPA>();
memberAccountJPA = memberRepository.findAll();
for(int i=0;i<memberAccountJPA.size();i++){
System.out.println(memberAccountJPA.get(i).getId());
}
return "addMemberPage";
}
}
1.請在資料庫建立一個與名稱@Table(name = "memberaccountjpa")
,name字串中的資料表
2.妳可以省略@Table
,但是要確保資料庫內有與此Model類別一樣名稱的資料表
spring.jpa.properties.hibernate.hbm2ddl.auto=create-drop
網路上的範例會加入這一行配置...請小心使用,他在程式一啟動會自動先將你的Table Drop在自動建立與Model數據定義的欄位名稱一模一樣的Table假如你的資料庫內有非常重要的資料!!!那妳就安心上路吧~~
先想看看為何不再使用Service層?
關鍵在於Model的
@Entity
-的宣告與MemberRepository
介面中繼承了(extends
)JpaRepository<MemberAccountJPA, Long>
您好,
我依照您的教學執行時會發生以下ERROR,
請問是什麼原因呢?
Description:
Field memberRepository in com.example.demo.MemberController required a bean of type 'com.example.Dao.MemberRepository' that could not be found.
The injection point has the following annotations:
- @org.springframework.beans.factory.annotation.Autowired(required=true)
Action:
Consider defining a bean of type 'com.example.Dao.MemberRepository' in your configuration.
沒掃到吧,在Application加入@ComponentScan
我遇到一樣的問題哦,我把進入點(application)檔案往上提ㄧ個層級解決了這個問題
請問有沒有遇過這樣的問題?
Whitelabel Error Page
This application has no explicit mapping for /error, so you are seeing this as a fallback.
Thu Nov 07 15:44:40 CST 2019
There was an unexpected error (type=Internal Server Error, status=500).
Circular view path [addMemberPage]: would dispatch back to the current handler URL [/addMemberPage] again. Check your ViewResolver setup! (Hint: This may be the result of an unspecified view, due to default view name generation.)
我已找到問題了調整@Controller就好了,我改@RestController
我用STS 3.9.9版是出現404
404已解決,可以參考以下的連結files所放位子
http://zetcode.com/springboot/static/