Spring概述
Spring是分層的、JavaSE/EE一站式(full-stack)、輕量級開源框架。以IoC(Inverse Of Control:反轉控制)和AOP(Aspect Oriented Programming:面向切面編程)爲內核,提供了表現層Spring MVC和持久層Spring JDBC以及業務層事務管理等衆多的企業級應用技術,還能整合開源世界衆多著名的第三方框架和類庫,逐漸成爲使用最多的Java EE企業應用開源框架。
spring 的優勢
方便解耦,簡化開發、 AOP編程的支持、 聲明式事務的支持、 方便程序的測試、 方便集成各種優秀框架、 降低JavaEE API的使用難度
關於框架的特性,我們也會俗稱Spring爲開發架構的粘合劑。
spring 的體系結構
Spring的核心
IoC(Inverse of Control 控制反轉): 將對象創建權利交給Spring工廠進行管理。
AOP(Aspect Oriented Programming 面向切面編程),基於動態代理的功能增強方式。
1、IoC 的概念和作用
什麼是程序的耦合: 我們在開發中,會寫很多的類,而有些類之間不可避免的產生依賴關係,這種依賴關係稱之爲耦合。
代碼中的體現:早期我們的 JDBC 操作,註冊驅動時,我們爲什麼不使用 DriverManager 的 register 方法,而是採 用 Class.forName 的方式?原因就是:我們的類依賴了數據庫的具體驅動類(MySQL),如果這時候更換了數據庫品牌(比如 Oracle), 需要修改源碼來重新數據庫驅動。
解決程序耦合的思路:當是我們講解 jdbc 時,是通過反射來註冊驅動的,代碼如下:
Class.forName("com.mysql.jdbc.Driver");//此處只是一個字符串
此時的好處是,我們的類中不再依賴具體的驅動類,此時就算刪除 mysql 的驅動 jar 包,依然可以編譯(運行就不要想了,沒有驅動不可能運行成功的)。
工廠模式解耦:
代碼準備:
dao接口和實現類:
dao接口:
public interface IAccountDao {
/**
* 模擬保存賬戶
*/
void saveAccount();
}
dao實現類:
public class AccountDaoImpl implements IAccountDao {
public void saveAccount() {
System.out.println("保存了賬戶");
}
}
service接口和實現類:
service接口:
public interface IAccountService {
/**
* 模擬保存賬戶
*/
void saveAccount();
}
service實現類:
public class AccountServiceImpl implements IAccountService {
//手動初始化
private IAccountDao accountDao = new AccountDaoImpl();
public void saveAccount() {
accountDao.saveAccount();
}
}
Web層:模擬一個表現層
public class Client {
public static void main(String[] args) {
IAccountService as = new AccountServiceImpl();
as.saveAccount();
}
}
代碼解耦
在上述的代碼中,代碼耦合體現在兩個地方: service中手動初始化了dao; web層手動初始化了service
而解耦最明顯的特徵就是:哪怕缺少一個對象,起碼在編譯時不會報錯,只有在運行時纔會報錯。既然在jdbc中我們可以使用反射來進行解耦,那麼我們能否在三層中使用這個方案呢?
第一步:創建工廠
在resources目錄下創建資源文件,beans.properties:
accountDao=cn.itcast.dao.impl.AccountDaoImpl
accountService=cn.itcast.service.impl.AccountServiceImpl
第二步:編寫一個工廠:用來反射生成需要的對象
public class BeanFactory {
private static ResourceBundle rb = ResourceBundle.getBundle("beans");
private static Map<String,Object> map = new HashMap<String,Object>();
static{
try {
//獲取所有的key
Enumeration<String> keys = rb.getKeys();
//遍歷所有的key
while (keys.hasMoreElements()){
String key = keys.nextElement();
//通過key獲取value
String value = rb.getString(key);
//初始化對象
Object bean = Class.forName(value).newInstance();
//將所有初始化的對象存入map中。
map.put(key,bean);
}
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 對外提供一個從map中獲取對象的方法
* @param beanName
* @return
*/
public static Object getBean(String beanName){
return map.get(beanName);
}
}
第三步:代碼解耦
Web層:
public class Client {
public static void main(String[] args) {
//手動初始化
//IAccountService accountService = new AccountServiceImpl();
//從容器中獲取
IAccountService accountService = (IAccountService) BeanFactory.getBean("accountService");
accountService.saveAccount();
}
}
Service層:
public class AccountServiceImpl implements IAccountService {
//手動初始化
//private IAccountDao accountDao = new AccountDaoImpl();
//從容器中獲取
private IAccountDao accountDao = (IAccountDao) BeanFactory.getBean("accountDao");
public void saveAccount() {
accountDao.saveAccount();
}
}
控制反轉-Inversion Of Control
我們通過使用工廠模式,實現了表現層——業務層以及業務層——持久層的解耦。
它的核心思想就是:(1) 通過讀取配置文件反射創建對象;(2) 把創建出來的對象都存起來,當我們下次使用時可以直接從存儲的位置獲取。
2、使用 spring的 IOC解決程序耦合
案例的前期準備[會用]:
一、創建工程
二、業務層接口和實現類
接口:
public interface IAccountService {
/**
* 模擬保存賬戶
*/
void saveAccount();
}
實現類:
public class AccountServiceImpl implements IAccountService {
//手動初始化
private IAccountDao accountDao = new AccountDaoImpl();
@Override
public void saveAccount() {
accountDao.saveAccount();
}
}
三、持久層接口和實現類
接口:
public interface IAccountDao {
void saveAccount();
}
實現類:
public class AccountDaoImpl implements IAccountDao {
@Override
public void saveAccount() {
System.out.println("保存賬戶");
}
}
四、表現層
public class Client {
public static void main(String[] args) {
IAccountService accountService = new AccountServiceImpl();
accountService.saveAccount();
}
}
Spring基於xml的IOC解耦方案
一、 創建配置文件模板
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">
</beans>
Idea裏配置模板
二、創建配置文件
IoC底層實現:工廠(設計模式)+反射(機制) + 配置文件
在spring中,工廠和反射機制由框架完成,我們只需要編寫配置文件即可。
在resources下創建:applicationContext.xml
如果創建的配置文件報紅,刷新maven即可
三、導入依賴
<dependencies>
<!--IOC相關依賴-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.0.6.RELEASE</version>
</dependency>
</dependencies>
四、將dao和service的實現類裝配到容器中
<!-- spring 將自己管理的資源統稱爲bean
id:資源標識名稱,相當於properties中的key,通過該名稱可以獲取對象
class:資源路徑,一般是實現類的全路徑
-->
<!-- 將service實現類裝配到容器中 -->
<bean id="accountService" class="cn.itcast.service.impl.AccountServiceImpl"></bean>
<!-- 將dao實現類裝配到容器中 -->
<bean id="accountDao" class="cn.itcast.dao.impl.AccountDaoImpl"></bean>
五、從容器中獲取dao和service實現類
將web層代碼修改如下:
public class Client {
public static void main(String[] args) {
//加載配置文件,獲取spring工廠,從容器中獲取dao和service的實現類
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
//從容器中獲取service
IAccountService accountService = (IAccountService) ac.getBean("accountService");
System.out.println(accountService);
//從容器中獲取dao
IAccountDao accountDao = (IAccountDao) ac.getBean("accountDao");
System.out.println(accountDao);
}
}
Spring基於 XML 的 IOC 細節[掌握]
spring 中工廠的類結構圖
BeanFactory和 ApplicationContext 的區別
BeanFactory 纔是 Spring 容器中的頂層接口。
ApplicationContext 是它的子接口。
BeanFactory 和 ApplicationContext 的區別: 創建對象的時間點不一樣。
ApplicationContext:只要一讀取配置文件,默認情況下就會創建對象。
BeanFactory:什麼使用什麼時候創建對象。
Beanfactory的用法:
BeanFactory ac = new XmlBeanFactory(new ClassPathResource("applicationContext.xml"));
IOC 中 bean 標籤和管理對象細節
bean 標籤
作用:
用於配置對象讓 spring 來創建的。
默認情況下它調用的是類中的無參構造函數。如果沒有無參構造函數則不能創建成功。
屬性:
-
id:給對象在容器中提供一個唯一標識。用於獲取對象。
-
class:指定類的全限定類名。用於反射創建對象。默認情況下調用無參構造函數。
-
scope:指定對象的作用範圍。
* singleton :默認值,單例的.
* prototype :多例的.
-
init-method:指定類中的初始化方法名稱(生命週期相關)。
-
destroy-method:指定類中銷燬方法名稱(生命週期相關)。
bean 的生命週期
單例對象:scope="singleton"
一個應用只有一個對象的實例。它的作用範圍就是整個應用。
生命週期:
對象出生:當應用加載,創建容器時,對象就被創建了。
對象活着:只要容器在,對象一直活着。
對象死亡:當應用卸載,銷燬容器時,對象就被銷燬了。
多例對象:scope="prototype"
每次訪問對象時,都會重新創建對象實例。
生命週期:
對象出生:當使用對象時,創建新的對象實例(getBean)。
對象活着:只要對象在使用中,就一直活着。
對象死亡:當對象長時間不用時,被java的垃圾回收器回收了。
生命週期方法:
init-method:指定類中的初始化方法名稱(生命週期相關)。
destroy-method:指定類中銷燬方法名稱(生命週期相關)。
實例化 Bean 的三種方式
第一種方式:使用默認無參構造函數創建對象
在默認情況下: 它會根據默認無參構造函數來創建類對象。如果 bean 中沒有默認無參構造函數,將會創建失敗
第二種方式:使用靜態工廠的方法創建對象
使用工廠中的靜態方法創建對象,並存入 spring 容器
id 屬性:指定 bean 的 id,用於從容器中獲取
class 屬性:指定靜態工廠的全限定類名
factory-method 屬性:指定生產對象的靜態方法
第三種方式:使用實例工廠的方法創建對象
先把工廠的創建交給 spring 來管理。
然後再使用工廠的 bean 來調用裏面的方法
factory-bean 屬性:用於指定實例工廠 bean 的 id。
factory-method 屬性:用於指定實例工廠中創建對象的方法。
默認無參構造創建對象
<!-- 將service實現類裝配到容器中 -->
<bean id="accountService" class="cn.itcast.service.impl.AccountServiceImpl"></bean>
靜態工廠方法創建對象
第一步:創建靜態工廠
/**
* 假設service的實現類是由工廠中的靜態方法創建的
*/
public class StaticFactory {
public static IAccountService createAccountService(){
return new AccountServiceImpl();
}
}
第二步:編寫配置文件
<!-- 通過靜態工廠方法創建對象並裝配到容器中 -->
<bean id="accountService" class="cn.itcast.utils.StaticFactory" factory-method="createAccountService"></bean>
第三步:測試
public class ClientStatic {
public static void main(String[] args) {
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
IAccountService accountService = (IAccountService) ac.getBean("accountService");
System.out.println(accountService);
}
}
實例工廠方法創建對象
第一步:創建實例工廠
/**
* 假設service的實現類是由一個工廠的非靜態方法創建的
*/
public class InstanceFactory {
public IAccountService createAccountService(){
return new AccountServiceImpl();
}
}
第二步:編寫配置文件
<!-- 將實例工廠裝配到容器中 -->
<bean id="instanceFactory" class="cn.itcast.utils.InstanceFactory"></bean>
<!-- 調用實例工廠中的非靜態方法創建對象 -->
<bean id="accountService" factory-bean="instanceFactory" factory-method="createAccountService"></bean>
第三步:測試
public class ClientInstance {
public static void main(String[] args) {
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
IAccountService accountService = (IAccountService) ac.getBean("accountService");
System.out.println(accountService);
}
}
Spring的依賴注入
依賴注入的概念
依賴注入:Dependency Injection。它是 spring 框架核心 ioc 的具體實現。
我們的程序在編寫時,通過控制反轉,把對象的創建交給了 spring,但是代碼中不可能出現沒有依賴的情況。 ioc 解耦只是降低他們的依賴關係,但不會消除。例如:我們的業務層仍會調用持久層的方法。
那這種業務層和持久層的依賴關係,在使用 spring 之後,就讓 spring 來維護了。
簡單的說,就是坐等框架把持久層對象傳入業務層,而不用我們自己去獲取。
一、 構造方法注入屬性
顧名思義,就是使用類中的構造函數,給成員變量賦值。注意,賦值的操作不是我們硬編碼的,而是通過配置的方式,讓spring框架來爲我們注入。
要求:
-
bean對象需要創建有參數的構造方法
-
在配置文件中通過constructor-arg標籤注入屬性
創建AccountServiceImpl2: 創建並添加有參構造函數
public class AccountServiceImpl2 implements IAccountService {
private String name;
private Integer age;
private IAccountDao accountDao;
//使用有參構造來注入屬性
public AccountServiceImpl2(String name, Integer age, IAccountDao accountDao) {
this.name = name;
this.age = age;
this.accountDao = accountDao;
}
public void saveAccount() {
System.out.println(name+"..."+age+"..."+accountDao);
}
}
編寫配置文件
<!--
使用構造函數注入屬性值:
涉及的標籤: constructor-arg
屬性:
index:指定參數在構造函數參數列表的索引位置
name:指定參數在構造函數中的名稱,指定給誰賦值
=======上面三個屬性都是指給誰賦值,下面兩個屬性指的是賦什麼值的==============
value:它能賦的值是基本數據類型和 String 類型
ref:它能賦的值是其他 bean 類型,也就是說,必須得是在配置文件中配置過的 bean
-->
<bean id="accountService2" class="cn.itcast.service.impl.AccountServiceImpl2">
<constructor-arg name="name" value="張三"></constructor-arg>
<constructor-arg name="age" value="18"></constructor-arg>
<constructor-arg name="accountDao" ref="accountDao"></constructor-arg>
</bean>
二、Set方法注入
顧名思義,就是使用類中的set方法,給成員變量賦值。注意,賦值的操作不是我們硬編碼的,而是通過配置的方式,讓spring框架來爲我們注入。
要求:
-
在配置文件中通過proprety標籤注入屬性
創建AccountServiceImpl3:創建並提供屬性的set方法
public class AccountServiceImpl3 implements IAccountService {
private String name;
private Integer age;
private IAccountDao accountDao;
public void setName(String name) {
this.name = name;
}
public void setAge(Integer age) {
this.age = age;
}
public void setAccountDao(IAccountDao accountDao) {
this.accountDao = accountDao;
}
public void saveAccount() {
System.out.println(name+"..."+age+"..."+accountDao);
}
}
編寫配置文件
<!--
通過配置文件給 bean 中的屬性傳值:使用 set 方法的方式
涉及的標籤:
Property相關屬性:
name:找的是類中 set 方法後面的部分
ref:給屬性賦值是其他 bean 類型的
value:給屬性賦值是基本數據類型和 string 類型的
實際開發中,此種方式用的較多。
-->
<bean id="accountService3" class="cn.itcast.service.impl.AccountServiceImpl3">
<property name="name" value="李四"></property>
<property name="age" value="20"></property>
<property name="accountDao" ref="accountDao"></property>
</bean>
創建Client3測試
public class Client3 {
public static void main(String[] args) {
//加載配置文件,獲取spring工廠,從容器中獲取dao和service的實現類
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
//從容器中獲取service
IAccountService accountService = (IAccountService) ac.getBean("accountService3");
accountService.saveAccount();
}
}
三、P名稱空間注入
此種方式是通過在 xml中導入 p名稱空間,使用 p:propertyName屬性 來注入數據,它的本質仍然是調用類中的 set 方法實現注入功能
創建AccountServiceImpl4
public class AccountServiceImpl4 implements IAccountService {
private String name;
private Integer age;
private IAccountDao accountDao;
public void setName(String name) {
this.name = name;
}
public void setAge(Integer age) {
this.age = age;
}
public void setAccountDao(IAccountDao accountDao) {
this.accountDao = accountDao;
}
public void saveAccount() {
System.out.println(name+"..."+age+"..."+accountDao);
}
}
編寫配置文件
xmlns:p="http://www.springframework.org/schema/p"
配置文件:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<!-- 將dao實現類裝配到容器中 -->
<bean id="accountDao" class="cn.itcast.dao.impl.AccountDaoImpl"></bean>
<bean id="accountService4" class="cn.itcast.service.impl.AccountServiceImpl4" p:name="zhangsan" p:age="18" p:accountDao-ref="accountDao"></bean>
</beans>
創建Client4測試
public class Client4 {
public static void main(String[] args) {
//加載配置文件,獲取spring工廠,從容器中獲取dao和service的實現類
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
//從容器中獲取service
IAccountService accountService = (IAccountService) ac.getBean("accountService4");
accountService.saveAccount();
}
}
四、複雜類型的注入
顧名思義,就是給類中的集合成員傳值,它用的也是set方法注入的方式,只不過變量的數據類型都是集合。 我們這裏介紹注入數組,List,Set,Map,Properties。
創建AccountServiceImpl5
public class AccountServiceImpl5 implements IAccountService {
private String[] myStrs;
private List<String> myList;
private Set<String> mySet;
private Map<String, String> myMap;
private Properties myProps;
public void setMyStrs(String[] myStrs) {
this.myStrs = myStrs;
}
public void setMyList(List<String> myList) {
this.myList = myList;
}
public void setMySet(Set<String> mySet) {
this.mySet = mySet;
}
public void setMyMap(Map<String, String> myMap) {
this.myMap = myMap;
}
public void setMyProps(Properties myProps) {
this.myProps = myProps;
}
public void saveAccount() {
System.out.println(myStrs);
System.out.println(myList);
System.out.println(mySet);
System.out.println(myMap);
System.out.println(myProps);
}
}
編寫配置文件
<!--
注入集合屬性:
使用set方法注入集合屬性:
array:一般用來設置數組
list:一般用來設置list集合
map:一般用來設置map集合
props:一般用來設置properties
-->
<bean id="accountService5" class="cn.itcast.service.impl.AccountServiceImpl5">
<property name="myStrs">
<array>
<value>AAA</value>
<value>BBB</value>
<value>CCC</value>
</array>
</property>
<property name="myList">
<list>
<value>AAA</value>
<value>BBB</value>
<value>CCC</value>
</list>
</property>
<property name="mySet">
<set>
<value>AAA</value>
<value>BBB</value>
<value>CCC</value>
</set>
</property>
<property name="myMap">
<map>
<entry key="name1" value="AAA"></entry>
<entry key="name2" value="BBB"></entry>
<entry key="name3" value="CCC"></entry>
</map>
</property>
<property name="myProps">
<props>
<prop key="name1">AAA</prop>
<prop key="name2">BBB</prop>
<prop key="name3">CCC</prop>
</props>
</property>
</bean>
創建Client5測試
public class Client5 {
public static void main(String[] args) {
//加載配置文件,獲取spring工廠,從容器中獲取dao和service的實現類
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
//從容器中獲取service
IAccountService accountService = (IAccountService) ac.getBean("accountService5");
accountService.saveAccount();
}
}
基於註解的IOC配置[掌握]——重點:18大註解標籤
明確:寫在最前
學習基於註解的IoC配置,大家腦海裏首先得有一個認知,即註解配置和xml配置要實現的功能都是一樣的,都是要降低程序間的耦合。只是配置的形式不一樣。
關於實際的開發中到底使用xml還是註解,每家公司有不同的習慣。所以這兩種配置方式我們都需要掌握。
1、用於裝配Bean的註解
@Component (value=”xxx”):
作用:
在類上使用該註解,把資源讓spring來管理。相當於在xml中配置一個bean。
屬性:
value:指定bean的id。如果不指定value屬性,默認bean的id是當前類的類名。首字母小寫。
/**
* @Component註解:相當於配置了<bean>標籤
* value = "accountService":相當於配置了bean標籤的id屬性,單獨配置value時,可以省略value屬性名稱
*/
@Component(value="accountService")
public class AccountServiceImpl implements IAccountService {
}
@Component的三個衍生註解:
@Controller(value=”xxx”):
一般用於將web層裝配到容器中,使用方法和@Component(value=”xxx”)一摸一樣
@Service(value=”xxx”):
一般用於將web層裝配到容器中,使用方法和@Component(value=”xxx”)一摸一樣
@Repository(value=”xxx”):
一般用於將web層裝配到容器中,使用方法和@Component(value=”xxx”)一摸一樣
2、 用於屬性注入的註解
@Autowired:
只能按照bean類型注入,如果有多個類型匹配,默認將屬性名稱作爲id去容器中查找。
@Qualifier:
一般和@Autowired配合使用,用來注入指定id的bean,做方法的參數中可以獨立使用 屬性:value:指定bean的id。
@Resource:
用來注入指定id的bean類型,相當於@Autowired+@Qualifier 屬性name:指定bean的id。
@Value:
只能注入基本類型等數據,不能注入bean類型,可以使用${}在資源文件中獲取數據,前提是,外部資源文件被加載
3、 作用域的
@Scope:
用於指定bean的作用域,一般就是singleton和prototype
4、 生命週期相關的
@PostConstruct:
用於指定某一個方法爲初始化方法
@PreDestroy:
用於指定某一個方法爲銷燬方法
關於Spring註解和XML的選擇問題
註解的優勢:
配置簡單,維護方便(我們找到類,就相當於找到了對應的配置)。
XML的優勢:
修改時,不用改源碼。
Spring管理Bean方式的比較:
5、 其他配置類相關的
@Configuration:
聲明一個類爲配置類,用於替代applicationContext.xml的
@ComponentScan:
用於開啓註解掃描的包
@Import:
用於導入其他類的
@PropertySource:
用於加載外部資源文件的
@Bean:
用於將方法返回的bean類型的對象裝配到容器中
純註解案例
環境搭建
創建配置類
@Configuration
@ComponentScan("cn.itcast")
public class SpringConfiguration {
@Bean(name="jdbcTemplate")
public JdbcTemplate createJdbcTempalte(@Qualifier("dataSource") DataSource dataSource){
return new JdbcTemplate(dataSource);
}
@Bean(name="dataSource")
public DataSource createDataSource(){
DruidDataSource dataSource = new DruidDataSource();
dataSource.setDriverClassName("com.mysql.jdbc.Driver");
dataSource.setUrl("jdbc:mysql://localhost:3306/heima37");
dataSource.setUsername("root");
dataSource.setPassword("root");
return dataSource;
}
}
測試
public class AccountControllerTest {
@Test
public void saveAccuont() {
ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
AccountController accountController = (AccountController) ac.getBean("accountController");
Account account = new Account();
account.setName("admin11");
account.setMoney(1000f);
accountController.saveAccuont(account);
}
}
優化
在resources類的根目錄下創建properties資源文件:
jdbc.driverClass=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/heima25
jdbc.username=root
jdbc.password=root
springConfiguration:
@Configuration//聲明這是一個配置類,用來代替xml的
@ComponentScan("cn.itcast")//開啓註解掃描
@Import(value={JdbcConfig.class})
public class SpringConfiguration {
}
//加載外部資源文件
@PropertySource(value = {"classpath:jdbc.properties"})
public class JdbcConfig {
@Value("${jdbc.driverClass}")
private String driverClassName;
@Value("${jdbc.url}")
private String url;
@Value("${jdbc.username}")
private String username;
@Value("${jdbc.password}")
private String password;
@Bean(name="jdbcTemplate")
public JdbcTemplate createJdbcTempalte(@Qualifier("dataSource") DataSource dataSource){
return new JdbcTemplate(dataSource);
}
@Bean(name="dataSource")
public DataSource createDataSource(){
DruidDataSource dataSource = new DruidDataSource();
dataSource.setDriverClassName(driverClassName);
dataSource.setUrl(url);
dataSource.setUsername(username);
dataSource.setPassword(password);
return dataSource;
}
}
6、 Junit相關的
@RunWith:
用於替換底層的運行器,初始化spring容器的
屬性:
value:單獨配置時,value屬性名稱可以省略,配置SpringJUnit4ClassRunner.class來代替原來junit的運行器
@ContextConfiguration
用於指定配置文件或者配置類的
屬性:
value[]:用來指定xml配置文件的路徑
class[]: 用來指定配置類
Xml的配置步驟案例:
導入spring-test的座標: 此處需要注意的是,spring5及以上版本要求junit的版本必須是4.12及以上,否則用不了
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>5.0.6.RELEASE</version>
</dependency>
測試
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = {"classpath:applicationContext.xml"})
public class AccountControllerTest {
@Autowired
private AccountController accountController;
@Test
public void saveAccuont() {
Account account = new Account();
account.setName("admin13");
account.setMoney(1000f);
accountController.saveAccuont(account);
}
}
純註解的配置步驟(配置類)
環境搭建
導入spring-test的座標
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>5.0.6.RELEASE</version>
</dependency>
測試
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = {SpringConfiguration.class})
public class AccountControllerTest {
@Autowired
private AccountController accountController;
@Test
public void saveAccuont() {
Account account = new Account();
account.setName("admin14");
account.setMoney(1000f);
accountController.saveAccuont(account);
}
}
附:Spring—ICO練習源碼
https://download.csdn.net/download/zhuyi2576947717/10679802