跳转至

MVC架構模式 Controller Service Dao 三層式架構

MVC 架構模式是軟體工程中的一種軟體架構

用途: 將系統拆分成Model ,View ,Controller 三個部分 ,每個部份各自負責不同的功能

甚麼是軟體工程(Software Engineering) ?

面對一個大型的系統 ,工程師們需要如何分工合作 ,一起去解決問題

ex: Git版本控制: 管理多位工程師所寫的程式

MVC架構模式 優點

  • 職責分離 ,更容易維護程式
  • 使程式結構更直覺 ,有利於團隊分工
  • 可以重複使用寫好的程式

MVC架構模式 in Spring Boot

  • MVC架構模式是抽象的概念
  • 實際套用到Spring Boot 時 ,會轉化為Controller-Service-Dao 三層式架構
    • Controller 負責接收 Http request、驗證請求參數 → call Service
    • Service 負責業務邏輯 → call Dao
    • Dao (Data Access Object) 負責和資料庫溝通 → 存取數據到資料庫

使用三層式架構之前的 Controller

  1. 用 @GetMapping("") 去接住前端所傳過來的 Http request
  2. NamedParameterJdbcTemplate.query() 取得資料庫裡面的數據 (dao)

使用三層式架構之後

  • StudentController: 負責接收前端傳來的Htpp request ,並且驗證請求參數
  • StudnetService: 負責業務邏輯
  • StudentDao: 負責和資料庫溝通

相對應關係

  1. Class的命名需要以 Controller、Service、Dao 做結尾 ,用來表示這個Class是屬於哪一層
  2. 將Controller、Service、Dao 這些 Class變成 Bean 並使用 @Autowired 注入
    • controller 要用 @RestController 這樣@GetMapping才會生效
    • service、Dao 則是使用 @Component 交給Spring 容器 變成 Bean
  3. Controller 不能直接 call Dao ,Controller 只能call Service ,再透過 Service 去 call Dao
    • 因為希望每一層之間的關係越簡單越好 , 透過這樣的規則可以去降低各層之間的複雜度 ,讓程式更容易去維護
  4. Dao 只能去執行 sql , 去存取資料庫內部的數據 ,不能添加任何業務邏輯
    • 忠實地呈現資料庫的數據 ,不論我們從資料庫去查到了哪一些數據 ,Dao 只能夠將這些數據直接回傳給Service , 讓Service層負責進行業務邏輯的處理

實作Controller-Service-Dao 三層式架構

主要分成

dao - public interface StudentDao - public class StudentDaoImpl implements StudentDao

service - public interface StudentService - public class StudentServiceImpl implements StudentService

controller - public class StudentController

dao

XxxDao interface

  • 方法命名 get 、query、find ex: getById();

XxxDaoImpl 代表會去實作 XxxDao 這個 interface

  • Impl → Implement

service

XxxService interface

XxxServiceImpl

@Component
public class StudentServiceImpl implements StudentService{
    @Autowired
    private StudentDao studentDao; // 使用interface 作為變數類型
    public Student getById(Integer studentId){
        return studentDao.getById(studentId);
    }
}

* 為什麼要使用interface 作為變數類型 ?

原因:

private XxxDao xxxDao; 盡量使用interface 作為變數類型

@Autowired 會根據變數的類型去Spring 容器中尋找符合類型的Bean

當我們使用 interface 來當作變數的類型的時候

因為所有實現XxxDao這個interface的 class 都是可以透過java 的多型特性

去向上轉型成XxxDao的類型

當我們去刪除XxxDaoImpl 去使用新的class的時候

就不需要去改任何一行程式

就可以直接換成注入新的class了

Spring IoC 將兩個class之間的關聯性降到最低

使用 interface 當作變數類型可以去降低class之間的耦合度

多型: https://yubin551.gitbook.io/java-note/object_oriented_programming/polymorphism