Spring 經過單表 CURD 認識配置IOC的兩兄弟(XML&註解)

開篇絮叨

前面一篇文章花大量內容,重點學習了 Spring入門 的一些思想,以及簡單的學習了 IOC基礎 以及基於基於 XML 的配置方式,你們應該清楚,XML與註解經常是如影隨行的,他們就像一對雙胞胎,但兄弟兩個的想法都是一致的,那就是幫助開發者實現想要的功能,咱們所說的IOC 技術,無疑是爲了下降程序間的耦合,那麼,今天就來聊一聊,基於註解的IOC配置,固然爲了你們有對比學習,兩種配置同時講解,同時我把例舉得儘可能完整一些,就來完成一個對單表進行 CURD 的案例php

(一) 準備代碼與環境

(1) 添加必要的依賴

  • spring-context
  • mysql-connector-java
  • c3p0(數據庫鏈接池)
  • commons-dbutils(簡化JDBC的工具)—後面會簡單介紹一下
  • junit (單元自測)

說明:因爲我這裏建立的是一個Maven項目,因此在這裏修改 pom.xml 添加一些必要的依賴座標就能夠java

若是建立時沒有使用依賴的朋友,去下載咱們所須要的 jar 包導入就能夠了mysql

<dependencies>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>5.0.2.RELEASE</version>
        </dependency>

        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.6</version>
        </dependency>

        <dependency>
            <groupId>c3p0</groupId>
            <artifactId>c3p0</artifactId>
            <version>0.9.1.2</version>
        </dependency>

        <dependency>
            <groupId>commons-dbutils</groupId>
            <artifactId>commons-dbutils</artifactId>
            <version>1.4</version>
        </dependency>

        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.12</version>
            <scope>test</scope>
        </dependency>
    </dependencies>
複製代碼

簡單看一下,spring核心的一些依賴,以及數據庫相關的依賴等就都導入進來了spring

(2) 建立帳戶表以及實體

A:建立 Account 表

-- ----------------------------
-- Table structure for account
-- ----------------------------
CREATE TABLE `account`  (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(32),
  `balance` float,
  PRIMARY KEY (`id`)
)
複製代碼

B:建立 Account 類

沒什麼好說的,對應着咱們的表創出實體sql

public class Account implements Serializable {
    private  Integer id;
    private String name;
    private Float balance;
    ......補充 get set toString 方法
複製代碼

(3) 建立Service以及Dao

A:AccountService 接口

public interface AccountService {

    void add(Account account);

    void delete(Integer accpuntId);

    void update(Account account);

    List<Account> findAll();

    Account findById(Integer accountId);
}
複製代碼

B:AccountServiceImpl 實現類

public class AccountServiceImpl implements AccountService {

    private AccountDao accountDao;

    public void setAccountDao(AccountDao accountDao) {
        this.accountDao = accountDao;
    }

    public void add(Account account) {
        accountDao.addAccount(account);
    }

    public void delete(Integer accpuntId) {
        accountDao.deleteAccount(accpuntId);
    }

    public void update(Account account) {
        accountDao.updateAccount(account);
    }

    public List<Account> findAll() {
        return accountDao.findAllAccount();
    }

    public Account findById(Integer accountId) {
        return accountDao.findAccountById(accountId);
    }
}
複製代碼

C:AccountDao 接口

public interface AccountDao {

    void addAccount(Account account);

    void deleteAccount(Integer accountId);

    void updateAccount(Account account);

    List<Account> findAllAccount();

    Account findAccountById(Integer accountId);
}
複製代碼

D:AccountDaoImpl 實現類

因爲今天要完成的是一個增刪改查的操做,因此咱們引入了 DBUtils 這樣一個操做數據庫的工具,它的做用就是封裝代碼,達到簡化 JDBC 操做的目的,因爲之後整合 SSM 框架的時候,持久層的事情就能夠交給 MyBatis 來作,而今天咱們重點仍是講解 Spring 中的知識,因此這部分會用就能夠了,重點看 XML 與 註解 兩種配置方式數據庫

用到的內容基本講解:apache

QueryRunner 提供對 sql 語句進行操做的 API (insert delete update)安全

ResultSetHander 接口,定義了查詢後,如何封裝結果集(僅提供了咱們用到的)微信

  • BeanHander:將結果集中第第一條記錄封裝到指定的 JavaBean 中
  • BeanListHandler:將結果集中的全部記錄封裝到指定的 JavaBean 中,而且將每個 JavaBean封裝到 List 中去
public class AccountDaoImpl implements AccountDao {

    
    private QueryRunner runner;

    public void setRunner(QueryRunner runner) {
        this.runner = runner;
    }

    public void addAccount(Account account) {
        try {
            runner.update("insert into account(name,balance)values(?,?)", account.getName(), account.getBalance());
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }


    public void updateAccount(Account account) {
        try {
            runner.update("update account set name=?,balance=? where id=?", account.getName(), account.getBalance(), account.getId());
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

    public void deleteAccount(Integer accountId) {
        try {
            runner.update("delete from account where id=?", accountId);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

    public List<Account> findAllAccount() {
        try {
            return runner.query("select * from account", new BeanListHandler<Account>(Account.class));
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

    public Account findAccountById(Integer accountId) {
        try {
            return runner.query("select * from account where id = ? ", new BeanHandler<Account>(Account.class), accountId);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}
複製代碼

(二) XML 配置方式

在這裏有兩基本的方式,一是經過構造函數注入,另外一種就是經過Set注入,實際上所作的就是,使用類的構造函數或者Set給成員變量進行賦值,但特別的是,這裏是經過配置,使用 Spring 框架進行注入首先就是頭部的依賴信息,順便提一句,固然咱們能夠去官網查找貼過來session

先把針對上面功能的具體配置代碼貼出來

<?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">

    <!--配置Service-->
    <bean id="accountService" class="cn.ideal.service.impl.AccountServiceImpl">
        <property name="accountDao" ref="accountDao"></property>
    </bean>

    <!--配置Dao-->
    <bean id="accountDao" class="cn.ideal.dao.impl.AccountDaoImpl">
        <property name="runner" ref="runner"></property>
    </bean>

    <!--配置 QueryRunner-->
    <bean id="runner" class="org.apache.commons.dbutils.QueryRunner">
        <!--注入數據源-->
        <constructor-arg name="ds" ref="dataSource"></constructor-arg>
    </bean>

    <!--配置數據源-->
    <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <property name="driverClass" value="com.mysql.jdbc.Driver"></property>
        <property name="jdbcUrl" value="jdbc:mysql://localhost:3306/ideal_spring"></property>
        <property name="user" value="root"></property>
        <property name="password" value="root99"></property>

    </bean>
</beans>
複製代碼

分析一下:

配置 Bean 標籤的時候,咱們見到了兩種形式 property、constructor-arg 也就是對應着 set 方式 與構造函形式,先說一下比較常見的 set 方式,用上面的代碼中距離:

(1) Set 方式

顧名思義,就是經過去找你給出對應的 Set 方法,而後對成員變量進行賦值,先看下類中的代碼

public class AccountServiceImpl implements AccountService {
	//成員
    private AccountDao accountDao;
	//Set方法
    public void setAccountDao(AccountDao accountDao) {
        this.accountDao = accountDao;
    }
 	
    ...... 下面是增刪改查的方法
}
複製代碼

這是 bean.xml 中的配置

<!--配置Service-->
<bean id="accountService" class="cn.ideal.service.impl.AccountServiceImpl">
        <property name="accountDao" ref="accountDao"></property>
</bean>
複製代碼

而後 property 配置的過程當中,有一些屬性須要說一下

  • name:與成員變量名無關,與set方法後的名稱有關,例如 setAccountDao() 獲取到的就是accountDao,而且已經小寫了開頭
  • value:這裏能夠寫基本數據類型和 String
  • ref:這裏能夠引入另外一個bean,幫助咱們給其餘類型賦值 (例如這裏就經過 ref 引入了下面 id 值爲accountDao的 bean)

固然,之後可能會見到一種方式就是 使用 p名稱空間注入數據 (本質仍是set)

頭部中須要修改引入這一句

xmlns:p="http://www.springframework.org/schema/p"

我直接拿之前文章中的一個例子:

<beans xmlns="http://www.springframework.org/schema/beans" xmlns:p="http://www.springframework.org/schema/p" 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">
 
<bean id="accountService" class="cn.ideal.service.impl.AccountServiceImpl" p:name="湯姆" p:age="21" p:birthday-ref="nowdt"/>
<bean id="nowdt" class="java.util.Date"></bean>
</beans>
複製代碼

(2) 構造函數方式

下面就是使用構造函數的一種方式,這一種的前提就是:類中必須提供一個和參數列表相對應的構造函數

因爲咱們選擇的是 DBUtils 這樣一個工具,而它爲咱們提供了兩種構造函數,即帶參和無參,因此咱們能夠在其中注入數據源,也可使得每一條語句都獨立事務

還有一點須要說明的就是:咱們下面的數據源使用了 c3p0 這只是一種選擇方式,並非必定的,是由於使用 DBUtils 的時候須要手動傳遞一個 Connection 對象

<!--配置 QueryRunner-->
<bean id="runner" class="org.apache.commons.dbutils.QueryRunner">
    <!--注入數據源-->
    <constructor-arg name="ds" ref="dataSource"></constructor-arg>
</bean>
複製代碼

來講一下所涉及到的標籤:

  • constructor-arg(放在 bean 標籤內) 再說一說其中的一些屬性值
    • 給誰賦值:
      • index:指定參數在構造函數參數列表的索引位置
      • type:指定參數在構造函數中的數據類型
      • name:指定參數在構造函數中的名稱(更經常使用)
    • 賦什麼值:
      • value:這裏能夠寫基本數據類型和 String
      • ref:這裏能夠引入另外一個bean,幫助咱們給其餘類型賦值

(3) 注入集合屬性

爲了演示這些方式,咱們在一個實體成員中將常見的一些集合都寫出來,而後補充其 set 方法

private String[] strs;
private List<String> list;
private Set<String> set;
private Map<String,String> map;
private Properties props;
複製代碼

在配置中也是很簡單的,只須要按照下列格式寫標籤就能夠了,因爲增刪改查中並無涉及到集合的相關信息,這裏就是簡單提一下,能夠本身測試一下

<bean id="accountService" class="cn.ideal.service.impl.AccountServiceImpl">
	<property name="strs">
		<array>
            <value>張三</value>
            <value>李四</value>
            <value>王五</value>
        </array>
    </property>

    <property name="list">
        <list>
            <value>張三</value>
            <value>李四</value>
            <value>王五</value>
        </list>
    </property>

    <property name="set">
        <set>
            <value>張三</value>
            <value>李四</value>
            <value>王五</value>
        </set>
    </property>

    <property name="map">
        <map>
            <entry key="name" value="張三"></entry>
            <entry key="age" value="21"></entry>
        </map>
    </property>

    <property name="props">
        <props>
            <prop key="name">張三</prop>
            <prop key="age">21</prop>
        </props>
    </property>
 </bean>
複製代碼

(4) 測試代碼

public class AccountServiceTest {

    private ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
    private AccountService as = ac.getBean("accountService", AccountService.class);

    @Test
    public void testAdd(){
        Account account = new Account();
        account.setName("jack");
        account.setBalance(1000f);
        as.add(account);
    }

    @Test
    public void testUpdate(){
        Account account = as.findById(4);
        account.setName("傑克");
        account.setBalance(1500f);
        as.update(account);
    }

    @Test
    public void testFindAll(){
        List<Account> list = as.findAll();
        for(Account account : list) {
            System.out.println(account);
        }
    }

    @Test
    public void testDelete(){
        as.delete(4);
    }
}
複製代碼

(5) 執行效果

添加,修改(包含了查詢指定id),刪除

查詢全部

(三) 註解配置方式

首先,咱們先將上面的例子使用註解來實現一下,再來具體的講解:

(1) 改造原程序爲註解配置

首先須要爲 Dao 和 Service 的實現類中 添加註解

@Service("accountService")
public class AccountServiceImpl implements AccountService {
    @Autowired
    private AccountDao accountDao;
 	
   	下面的原封不動
}
複製代碼
@Repository("accountDao")
public class AccountDaoImpl implements AccountDao {
    @Autowired
    private QueryRunner runner;
   
    下面的原封不動
}
複製代碼
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:context="http://www.springframework.org/schema/context" 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 http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
	<!--開啓掃描-->
    <context:component-scan base-package="cn.ideal"></context:component-scan>

    <!--配置 QueryRunner-->
    <bean id="runner" class="org.apache.commons.dbutils.QueryRunner">
        <!--注入數據源-->
        <constructor-arg name="ds" ref="dataSource"></constructor-arg>
    </bean>

    <!--配置數據源-->
    <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <property name="driverClass" value="com.mysql.jdbc.Driver"></property>
        <property name="jdbcUrl" value="jdbc:mysql://localhost:3306/ideal_spring"></property>
        <property name="user" value="root"></property>
        <property name="password" value="root99"></property>
    </bean>
</beans>
複製代碼

到這裏,一個最基本的註解改造就完成了,你們能夠用前面的測試類進行一下測試

下面咱們正式說一下註解配置相關的知識

(2) 經常使用註解

A:建立對象

@Component

  • 讓Spring 來管理資源,至關於XML 中配置一個 bean <bean id="" class="">
  • 能夠在括號內指定 value 值,即指定 bean 的 id ,若是不指定就會默認的使用當前類的類名
  • 若是註解中只有一個value屬性要賦值,value能夠不寫,直接寫名稱,如上面例子中

@Controller @Service @Repository

對於建立對象的註解,Spring 還提供了三種更加明確的說法,做用是徹底相同的,可是針對不一樣的場景起了不一樣的叫法罷了

  • @Controller:通常用於表現層
  • @Service:通常用於業務層
  • @Repository:通常用於持久層

B:注入數據

@Autowired
  • 自動按類型注入,至關於XML 中配置一個 bean <property name="" ref=""> 或者 <property name="" value="">

  • 容器中有一個惟一的 bean 對象類型和注入的變量類型一致,則注入成功

    • @Autowired
      private AccountDao accountDao;
      
      @Repository("accountDao")
      public class AccountDaoImpl implements AccountDao {......}
      複製代碼
    • 好比上面的例子,Spring的IOC中容器是一個Map的結構,字符串「accountDao」 以及這個能夠認爲是 AccountDao 類型的 AccountDaoImpl 類就被以鍵值對的形式存起來,被註解 @Autowired的地方,會直接去容器的 value 部分去找 AccountDao 這個類型的類

    • 當 IoC 中匹配到了多個符合的,就會根據變量名去找,找不到則報錯:例以下面,根據 AccountDao類型匹配到了兩個類,因此根據變量名去找找到了 AccountDaoImplA 這個類

    • @Autowired
      private AccountDao accountDaoA;
      
      @Repository("accountDaoA")
      public class AccountDaoImplA implements AccountDao {......}
      
      @Repository("accountDaoB")
      public class AccountDaoImplB implements AccountDao {......}
      複製代碼
  • 能夠對類的成員變量、方法以及構造函數進行標註,完成自動裝配

  • 使用此註解能夠省略 set 方法

@Qualifier
  • 在自動按類型注入的基礎之上,按照 Bean 的 id 注入,給字段注入的時候不可以單獨使用,須要配合上面的 @Autiwire 使用,可是給方法參數注入的時候,能夠獨立使用
  • 使用時:value 值指定 bean 的 id

它有時候必須配合別的註解使用,有沒有一個標籤能夠解決這個問題呢?答案就是 @Resource

@Resource
  • 直接按照 bean 的 id 注入,不過只能注入其餘 bean 類型
  • 使用時:name 值指定 bean 的 id

前面三個都是用來注入其餘的 bean 類型的數據,下面來講一說,基本類型以及String的實現

(特別說明:集合類型的注入只能經過 XML 來實現)

@Value
  • 這個註解就是用來注入基本數據類型和 String 類型數據的
  • 使用時:value 屬性用於指定值

C:改變做用範圍

@Scope
  • 指定 bean 的做用範圍 至關於XML 中配置一個 <bean id="" class="" scope
  • 使用時:value 屬性用於指定範圍的值(singleton prototype request session globalsession)

D:生命週期相關

至關於:<bean id="" class="" init-method="" destroy-method="" />

@PostConstruct
  • 指定初始化方法
@PreDestroy
  • 指定銷燬方法

(四) XML和註解 的對比與選擇

(1) 優缺點

通常來講,咱們兩種配置方式都是有人使用的,不過我我的更習慣使用註解的方式

  • XML

    • 類之間的鬆耦合關係,擴展性強,利於更換修改
    • 對象之間的關係清晰明瞭
  • 註解:

    • 簡化配置,而且使用起來也容易,效率會高一些
    • 在類中就能找對配置,清晰明瞭
    • 類型安全

(2) 二者對比

XML配置 註解配置
建立對象 <bean id="" class=""> @Controller @Service @Repository@Component
指定名稱 經過 id 或者 name 值指定 @Controller("指定的名稱")
注入數據 <property name="" ref=""> @Autowired @Qualifier @Resource @Value
做用範圍 <bean id="" class="" scope> @Scope
生命週期 <bean id="" class="" init-method="" destroy-method=""/> @PostConstruct @PreDestroy

(五) 補充新註解

爲何要補充新註解呢? 在咱們使用註解時,在書寫代碼時,簡化了不少,可是咱們在 bean.xml 文件中 仍然須要 開啓掃描、 進行配置QueryRunner 以及 數據源,如何完全擺脫 xml 配置全面使用註解呢?

這也就是咱們將要補充的幾個新註解,做用就是讓咱們全面使用註解進行開發

(1) 註解講解

A: 配置類註解

@Configuration
  • 指定當前類是 spring 的一個配置類,至關於 XML中的 bean.xml 文件

  • 獲取容器時須要使用下列形式

  • private ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
    複製代碼

依舊使用上方的 CURD 的案例代碼進行修改,首先與cn同級建立了一個名爲 config 的包,而後編寫一個名爲 SpringConfiguration 的類,固然實際上這兩個名字無所謂的,添加註解

@Configuration
public class SpringConfiguration {
}
複製代碼

B: 指定掃描包註解

@ComponentScan

@Configuration 至關於已經幫咱們把 bean.xml 文件創立好了,按照咱們往常的步驟,應該指定掃描的包了,這也就是咱們這個註解的做用

  • 指定 spring 在初始化容器時要掃描的包,在 XML 中至關於:

  • <!--開啓掃描-->
    <context:component-scan base-package="cn.ideal"></context:component-scan>
    複製代碼
  • 其中 basePackages 用於指定掃描的包,和這個註解中value屬性的做用是一致的

具體使用:

@Configuration
@ComponentScan("cn.ideal")
public class SpringConfiguration {
}
複製代碼

C: 建立對象

@Bean

寫好了配置類,以及指定了掃描的包,下面該作的就是配置 QueryRunner 以及數據源了,在 XML 中咱們會經過書寫 bean 標籤來配置,而 Spring 爲咱們提供了 @Bean 這個註解來替代原來的標籤

  • 將註解寫在方法上(只能是方法),也就是表明用這個方法建立一個對象,而後放到 Spring 的容器中去
  • 經過 name 屬性 給這個方法指定名稱,也就是咱們 XML 中 bean 的 id

具體使用:

package config;

import com.mchange.v2.c3p0.ComboPooledDataSource;
import org.apache.commons.dbutils.QueryRunner;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;

import javax.sql.DataSource;

public class JdbcConfig {

	/** * 建立一個 QueryRunner對象 * @param dataSource * @return */
    @Bean(name = "runner")
    public QueryRunner creatQueryRunner(DataSource dataSource){
        return  new QueryRunner(dataSource);
    }


    /** * 建立數據源,而且存入spring * @return */
    @Bean(name = "dataSource")
    public DataSource createDataSource() {
        try {
            ComboPooledDataSource ds = new ComboPooledDataSource();
            ds.setUser("root");
            ds.setPassword("1234");
            ds.setDriverClass("com.mysql.jdbc.Driver");
            ds.setJdbcUrl("jdbc:mysql:///spring_day02");
            return ds;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}
複製代碼

D: 配置 properties 文件

@PropertySource

上面在建立數據源的時候,都是直接把配置信息寫死了,若是想要使用 properties 進行內容的配置,在這時候就須要,使用 @PropertySource 這個註解

  • 用於加載 .properties 文件中的配置
  • value [] 指定 properties 文件位置,在類路徑下,就須要加上 classpath
@Configuration
@ComponentScan("cn.ideal")
@PropertySource("classpath:jdbcConfig.properties")
public class SpringConfiguration {
}
複製代碼
public class JdbcConfig {

    @Value("${jdbc.driver}")
    private String driver;
    @Value("${jdbc.url}")
    private String url;
    @Value("${jdbc.username}")
    private String username;
    @Value("${jdbc.password}")
    private String password;


    /** * 建立一個 QueryRunner對象 * @param dataSource * @return */
    @Bean(name = "runner")
    public QueryRunner creatQueryRunner(DataSource dataSource){
        return  new QueryRunner(dataSource);
    }


    /** * 建立數據源,而且存入spring * @return */
    @Bean(name = "dataSource")
    public DataSource createDataSource() {
        try {
            ComboPooledDataSource ds = new ComboPooledDataSource();
            ds.setUser(username);
            ds.setPassword(password);
            ds.setDriverClass(driver);
            ds.setJdbcUrl(url);
            return ds;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}
複製代碼

E:導入其餘配置類

@Import

這樣看來一個 JdbcConfig 就基本寫好了,咱們在其中配置了 QueryRunner 對象,以及數據源,這個時候,實際上咱們原先的 bean.xml 就能夠刪掉了,可是咱們雖然寫好了 JdbcConfig 可是如何將兩個配置文件聯繫起來呢?這也就是這個註解的做用

@Configuration
@ComponentScan("cn.ideal")
@Import(JdbcConfig.class)
@PropertySource("classpath:jdbcConfig.properties")
public class SpringConfiguration {
}
複製代碼

(2) 註解獲取容器

修改獲取容器的方式後,就能夠進行測試了

private ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfiguration.class);
private AccountService as = ac.getBean("accountService", AccountService.class);
複製代碼

(五) Spring 單元測試改進

因爲咱們須要經過上面測試中兩行代獲取到容器,爲了避免每一次都寫這兩行代碼,因此咱們在前面將其定義在了成員位置,可是有沒有辦法能夠省掉這個步驟呢?

也就是說,咱們想要程序自動建立容器,可是原來的 junit 很顯然是實現不了的,由於它並不會知道咱們是否使用了 spring ,不過 junit 提供了一個註解讓咱們替換它的運行器,轉而由 spring 提供

首先須要導入 jar 包 或者說導入依賴座標

<dependency>
	<groupId>org.springframework</groupId>
	<artifactId>spring-test</artifactId>
	<version>5.0.2.RELEASE</version>
</dependency>
複製代碼

使用 @RunWith 註解替換原有運行器 而後使用 @ContextConfiguration 指定 spring 配置文件的位置,而後使用 @Autowired 給變量注入數據

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = SpringConfiguration.class)
public class AccountServiceTest {

    @Autowired
    private AccountService as;
    
}
複製代碼

(六) 總結

到這裏,這篇文章就結束了,這篇文章主要講解的內容接着咱們上一篇文章講解,上一篇更多的是從傳統按部就班的提到 Spring,更多的是幫助你們理解爲何用Spring,而這篇文章是基於上一篇的基礎,更多的提到的是如何去用 Spring,因此看起來更像是一個工具書同樣的文章,並無提到不少的思想原理,而是幫助你們快速的上手用 XML 以及註解的方式,固然大神天然不少,不敢說什麼有技術,但總歸是但願能給不太熟悉 spring 的朋友一些幫助,或者臨時當作一篇工具文來查找,再次感謝你們的訪問與贊,謝謝朋友們的支持!再次感謝!

(七) 結尾

若是文章中有什麼不足,歡迎你們留言交流,感謝朋友們的支持!

若是能幫到你的話,那就來關注我吧!若是您更喜歡微信文章的閱讀方式,能夠關注個人公衆號

在這裏的咱們素不相識,卻都在爲了本身的夢而努力 ❤

一個堅持推送原創開發技術文章的公衆號:理想二旬不止

相關文章
相關標籤/搜索