學習目标
能夠說出Spring的體系結構
能夠編寫IOC入門案例
能夠編寫DI入門案例
思考:為什麼學習Spring而不是直接學習SpringBoot
1 Spring介紹
思考:我們為什麼要學習Spring架構?
- 工作上面 Java擁有世界上數量最多的程式員最多的崗位需求與高額薪資95%以上伺服器端還是要用Java開發
- 專業角度 簡化開發,降低企業級開發的複雜性架構整合,高效整合其他技術,提高企業級應用開發與運作效率
Spring和SpringBoot關系
關系:Spring Boot建構在Spring之上,相容并繼承了原生Spring架構的特性和功能。通過Spring Boot,開發者無需手動配置太多内容,可以快速搭建基于Spring的應用程式。同時,Spring Boot與Spring緊密結合,可以友善地使用Spring的各種特性和擴充元件。
總而言之,Spring Boot是對Spring的拓展和增強,旨在簡化Spring應用程式的開發和部署。Spring和Spring Boot共同構成了一個強大、靈活且易于使用的Java應用程式開發生态系統。
1.1 學習Spring的什麼知識
- 簡化開發 IOC(控制反轉)AOP(面向切面程式設計) 事務處理
- 架構整合 MyBatisMyBatis-plusStrutsStruts2Hibernate……
1.3 怎麼學
- 學習Spring架構設計思想
- 學習基礎操作,思考操作與設計思想間的聯系
- 學習案例,熟練應用操作的同時,體會設計思想
2 Spring初認識
目前我們使用的是Spring幾版本?
從官網發現以及到了6.x
2.1 Spring家族
- 官網:https://spring.io
- Spring發展到今天已經形成了一種開發的生态圈,Spring提供了若幹個項目,每個項目用于完成特定的功能。
3 Spring體系結構
問題導入
通過系統架構圖,Spring能不能進行資料層開發?Spring能不能進行web層開發?
3.1 Spring Framework系統架構圖
- Spring Framework是Spring生态圈中最基礎的項目,是其他項目的根基
3.2 Spring Framework如何學習
- 1.核心容器 核心概念IOC/DI容器基本操作
- 2.AOP AOP概念AOP基本操作
- 3.Spring事務 事務使用
- 4.整合第三方架構 整合資料架構MyBatis
4 Spring核心概念
問題1:目前我們的代碼存在什麼問題以及怎麼解決這些問題?
思考:什麼是IoC,什麼是DI?
4.1 目前我們代碼存在的問題
從上圖思考問題:如果因為業務需要StudentServiceImpl,需要一個新的StudentDao實作 StudentDaoImpl2,name我們就需要在StudentServiceImpl中修改代碼,也就是修改
//建立成員對象
private StudentDao studentDao = new StudentDaoImpl2();
出現問題:
- 代碼書寫現狀 耦合度偏高
- 解決方案 使用對象時,在程式中不要主動使用new産生對象,轉換為由外部提供對象
4.2 核心概念
- IOC(Inversion of Control)控制反轉 使用對象時,由主動new産生對象轉換為由外部提供對象,此過程中對象建立控制權由程式轉移到外部,此思想稱為控制反轉。通俗的講就是“将new對象的權利交給Spring,我們從Spring中擷取對象使用即可”
- Spring技術對IoC思想進行了實作 Spring提供了一個容器,稱為IOC容器,用來充當IoC思想中的“外部”IOC容器負責對象的建立、初始化等一系列工作,被建立或被管理的對象在IoC容器中統稱為Bean對象
- DI(Dependency Injection)依賴注入 在容器中建立bean與bean之間的依賴關系的整個過程,稱為依賴注入。
- 目标:充分解耦 使用IoC容器管理bean(IOC)在IoC容器内将有依賴關系的bean進行關系綁定(DI)
- 最終效果 使用對象時不僅可以直接從IoC容器中擷取,并且擷取到的bean已經綁定了所有的依賴關系
二、IOC和DI入門案例【重點】
1 IOC入門案例【重點】
思考:Spring中的IOC代碼如何實作?
1.1 門案例思路分析
- 管理什麼?(Service與Dao)
- 如何将被管理的對象告知IOC容器?(配置檔案)
- 被管理的對象交給IOC容器,如何擷取到IoC容器?(接口)
- IOC容器得到後,如何從容器中擷取bean?(接口方法)
- 使用Spring導入哪些坐标?(pom.xml)
1.2 實作步驟
【第一步】導入Spring坐标
【第二步】定義Spring管理的類(接口)
【第三步】建立Spring配置檔案,配置對應類作為Spring管理的bean對象
【第四步】初始化IOC容器(Spring核心容器/Spring容器),通過容器擷取bean對象
- 項目結構
- 建立maven子產品
- Student實體類
1.3 實作代碼
【第0步】導入Spring坐标
<dependencies>
<!--導入spring的坐标spring-context,對應版本是5.2.10.RELEASE-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.3.15</version>
</dependency>
<!-- 導入junit的測試包 -->
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter</artifactId>
<version>5.8.2</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.28</version>
</dependency>
</dependencies>
【第一步】導入Student實體類
@Data
@ToString
@AllArgsConstructor
public class Student {
private String name;
private String address;
private Integer age;
private Integer status;
}
【第二步】定義Spring管理的類(接口)
- StudentDao接口和StudentDaoImpl實作類
package com.zbbmeta.dao;
public interface StudentDao {
/**
* 添加學生
*/
void save();
}
package com.zbbmeta.dao.impl;
import com.zbbmeta.dao.StudentDao;
public class StudentDaoImpl implements StudentDao {
@Override
public void save() {
System.out.println("DAO: 添加學生資訊到資料庫...");
}
}
- StudentService接口和StudentServiceImpl實作類
package com.zbbmeta.service;
public interface StudentService {
/**
* 添加學生
*/
void save();
}
package com.zbbmeta.service.impl;
import com.zbbmeta.dao.StudentDao;
import com.zbbmeta.dao.impl.StudentDaoImpl;
import com.zbbmeta.service.StudentService;
public class StudentServiceImpl implements StudentService {
//建立成員對象
private StudentDao studentDao = new StudentDaoImpl();
@Override
public void save() {
}
}
【第三步】建立Spring配置檔案在resources目錄下,配置對應類作為Spring管理的bean對象
- 定義1_ioc_di.xml配置檔案并配置StudentDaoImpl
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<!--
1.目标:使用xml進行spring的IOC開發,讓IOC建立StudentDaoImpl對象
-->
<!--1.建立StudentDaoImpl對象
<bean id="" class="">
id:設定對象别名,這個id值必須唯一,便于以後從IOC容器中擷取這個對象
class:設定對那個類全名生成對象
-->
<bean class="com.zbbmeta.dao.impl.StudentDaoImpl" id="studentDao"></bean>
</beans>
注意事項:bean定義時id屬性在同一個上下文中(IOC容器中)不能重複
【第四步】初始化IOC容器(Spring核心容器/Spring容器),通過容器擷取Bean對象
package com.zbbmeta;
import com.zbbmeta.dao.StudentDao;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class QuickStartApplication {
public static void main(String[] args) {
//1.根據配置檔案1_ioc.xml建立IOC容器
ClassPathXmlApplicationContext ac = new ClassPathXmlApplicationContext("1_ioc_di.xml");
//2.從IOC容器裡面擷取id="studentDao"對象
StudentDao studentDao = (StudentDao) ac.getBean("studentDao");
//3.執行對象方法
studentDao.save();
//4.關閉容器
ac.close();
}
}
1.4 運作結果
2 DI入門案例【重點】
思考:Spring中的IOC中已經存在了,studentDao,那麼現在如果我還有建立一個bean對象studentService可以像剛才一樣直接建立?
不可以,因為studentService中,建立了studentDao對象,所有要将stuentDao注入(DI)到studentService
2.1 DI入門案例思路分析
- 基于IOC管理bean
- Service中使用new形式建立的Dao對象是否保留?(否)
- Service中需要的Dao對象如何進入到Service中?(提供方法)
- Service與Dao間的關系如何描述?(配置)
2.2 實作步驟
【第一步】删除使用new的形式建立對象的代碼
【第二步】提供依賴對象對應的setter方法
【第三步】配置service與dao之間的關系
2.3 實作代碼
【第一步】删除使用new的形式建立對象的代碼
package com.zbbmeta.service.impl;
import com.zbbmeta.dao.StudentDao;
import com.zbbmeta.dao.impl.StudentDaoImpl;
import com.zbbmeta.service.StudentService;
public class StudentServiceImpl implements StudentService {
//建立成員對象
//【第一步】删除使用new的形式建立對象的代碼,解除對象之間的耦合度
// private StudentDao studentDao = new StudentDaoImpl();
private StudentDao studentDao ;
@Override
public void save() {
System.out.println("Service: 添加學生資訊到資料庫...");
studentDao.save();
}
}
【第二步】提供依賴對象對應的setter方法
package com.zbbmeta.service.impl;
import com.zbbmeta.dao.StudentDao;
import com.zbbmeta.service.StudentService;
public class StudentServiceImpl implements StudentService {
//建立成員對象
//【第一步】删除使用new的形式建立對象的代碼,解除對象之間的耦合度
// private StudentDao studentDao = new StudentDaoImpl();
private StudentDao studentDao ;
//【第二步】提供依賴對象對應的setter方法
public void setStudentDao(StudentDao studentDao) {
this.studentDao = studentDao;
}
@Override
public void save() {
System.out.println("Service: 添加學生資訊到資料庫...");
studentDao.save();
}
}
【第三步】配置service與dao之間的關系
在applicationContext.xml中配置
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<!--
1.目标:使用xml進行spring的IOC開發,讓IOC建立StudentDaoImpl對象
bean 可以看出 new StudentDaoImpl()
-->
<!--1.建立StudentDaoImpl對象
<bean id="" class="">
id:設定對象别名,這個id值必須唯一,便于以後從IOC容器中擷取這個對象
class:設定對那個類全名生成對象
-->
<bean class="com.zbbmeta.dao.impl.StudentDaoImpl" id="studentDao"></bean>
<!--
1.1目标:使用xml進行spring的IOC開發,BookServiceImpl對象
-->
<bean class="com.zbbmeta.service.impl.StudentServiceImpl" id="studentService">
<!--3.給StudentServiceImpl對象裡面studentDao成員指派(DI 依賴注入)
調用 public void setStudentDao(StudentDao studentDao) {this.studentDao = studentDao;}
name="studentDao" 含義是調用setStudentDao方法
ref="studentDao", 從IOC容器中查找id="setStudentDao"的對象傳遞給setStudentDao方法作為參數使用
-->
<property name="studentDao" ref="studentDao"></property>
</bean>
</beans>
【第四步】初始化IOC容器(Spring核心容器/Spring容器),通過容器擷取studentDao對象
package com.zbbmeta;
import com.zbbmeta.service.StudentService;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class DIApplication {
public static void main(String[] args) {
/**
* //目标:從IOC容器裡面擷取studentService對象執行
*/
//1.根據配置檔案1_ioc.xml建立IOC容器
ClassPathXmlApplicationContext ac = new ClassPathXmlApplicationContext("1_ioc_di.xml");
//2.從IOC容器裡面擷取id="studentService"對象
StudentService studentService = (StudentService) ac.getBean("studentService");
//3.執行對象方法
studentService.save();
//4.關閉容器
ac.close();
}
}
控制台結果
2.4 圖解示範