即使不懂單元測試,會用這個工具也夠了~

2022-01-13 10:00:14

Mockito學習

Mockito是一個強大的用於Java開發的模擬測試框架,通過Mockito我們可以建立和設定Mock物件,進而簡化有外部依賴的類的測試。可以不進行外部依賴,快速進行Java的單元測試的進行。

Mock 模擬

Mock測試就是在測試過程中,對於某些不容易構造或者不容易獲取的物件,用一個虛擬的物件來建立以便測試的測試方法。

Mockito好處

無手寫 : 無需自己編寫模擬物件。

重構安全 : 重新命名介面方法名稱或重新排序引數不會破壞測試程式碼,因為Mocks是在執行時建立的。

  • 返回值支援 : 支援返回值

  • 異常支援 : 支援例外

  • 訂單檢查支援 : 支援檢查方法呼叫的順序

  • 註釋支援 : 支援使用註釋建立模擬

Mockito整合

引入依賴

   <dependency>
            <groupId>org.mockito</groupId>
            <artifactId>mockito-core</artifactId>
            <version>3.3.3</version>
            <scope>test</scope>
        </dependency>

Mockito的使用

初始化

  @Before
    public void initMocks() {
        MockitoAnnotations.initMocks(this);
    }

或者:

//引入依賴
@RunWith(MockitoJUnitRunner.class)
public class MockitoTest {
}

註解

@Mock

用於模擬物件,有助於減少重複模擬物件。

注意:@Mock註釋始終與@RunWith註釋一起使用。

@RunWith

這是一個類級別的註釋,它用於保持測試乾淨並改善偵錯,它還會檢測測試中可用的未使用的存根,並使用@Mock註釋對模擬進行初始化。

@InjectMocks

它標記應在其上執行注入的欄位或引數。

@Captor

它允許建立欄位級引數捕獲器,它與Mockito的verify()方法一起使用, 以獲取呼叫方法時傳遞的值。

@Spy

允許建立部分模擬的物件,換句話說,它允許將現場範例快速包裝在測試物件中。

建立一個範例

package com.example.sl.demospringboot;

import com.example.sl.demospringboot.dao.UserMapper;
import com.example.sl.demospringboot.model.User;
import com.example.sl.demospringboot.service.UserService;
import com.example.sl.demospringboot.service.UserServiceImpl;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.*;
import org.mockito.junit.MockitoJUnitRunner;

import java.util.List;
import java.util.Map;

import static org.mockito.Mockito.*;

//引入依賴
@RunWith(MockitoJUnitRunner.class)
public class MockitoTest {

    //初始化Mokc註解物件或者@RunWith(MockitoJUnitRunner.class)
//    @Before
//    public void initMocks() {
//        MockitoAnnotations.initMocks(this);
//    }
    //模擬一個物件
    @Mock
    private Map map;


    @InjectMocks
    private UserServiceImpl userServicei;
    @Mock
    private UserService userService;

    @Mock
    private UserMapper userMapper;

    @Test
    public void test1(){
        User user=mock(User.class);
        when(user.getUsername()).thenReturn("快樂");
        //當呼叫user.getUsername()返回「快樂」
        Assert.assertEquals("快樂",user.getUsername());
        Assert.assertTrue(map instanceof Map);
        //當呼叫user.getUsername()拋空指標
        Mockito.doThrow(new NullPointerException()).when(user.getUsername());
        //當呼叫user的時候什麼事情也不用做
        Mockito.doNothing().when(user);
        map.size();
        //verify檢測方法呼叫,這表明size方法呼叫一次
        verify(map,times(1)).size();
    }
    /**
     * 捕獲引數
     */
    @Test
    public  void  testGetParam(){
        String param="我是一個引數";
        //模擬一個List物件
        List listO=Mockito.mock(List.class);
        ArgumentCaptor<String> paramObject = ArgumentCaptor.forClass(String.class);//捕獲引數的物件

        listO.add(param);//mock物件執行add方法,將test新增進其中

        verify(listO).add(paramObject.capture());//捕獲引數

        Assert.assertEquals("我是一個引數", paramObject.getValue());//斷言驗證

    }
    /**
     * 模擬資料庫查詢一個User
     */
    @Test
    public void testGetUser(){
        User user=new User();
        user.setAge(1);
        //呼叫方法返回一個實體
        when(userServicei.findUser()).thenReturn(user);
       // System.out.println("userService.findUser().getAge() = " + userServicei.findUser().getAge());
        Assert.assertEquals("1",userServicei.findUser().getAge()+"");
        verify(userMapper).getUser();
    }
    /**
     * 呼叫介面發方法進行測試
     * 設定超時時間
     */
    @Test(timeout = 1000)
    public void testInterface() throws InterruptedException {
        User user=new User();
        user.setUsername("test");
        //呼叫userService.findUser()返回一個usaer
        when(userService.findUser()).thenReturn(user);
        Assert.assertEquals("test",userService.findUser().getUsername());
        //驗證執行幾次
        verify(userService).findUser();
    }
}

注意

@InjectMocks建立一個範例,也就是一個包含注入介面或者其他bean的一個物件。

@Mock是一個範例裡面的一個注入物件,對應的是spring的一個bean。

最後也為大家準備了一份學習資源:

這份資源整體是圍繞著【軟體測試】來進行整理的,對於軟體測試的的朋友來說應該是很全面和完整的備戰倉庫了,這個倉庫也陪伴我走過了很多坎坷的路,希望也能幫助到你。關注公眾號:程式設計師二黑,可以免費獲取了!

你想要的越多,你付出的也越多。

我是二黑,如果你不想再體驗一次自學時找不到資料,沒人解答問題,堅持幾天便放棄的感受的話,可以加入我們的軟體測試技術交流群:785128166,裡面有各種軟體測試資源和技術交流。

精彩推薦:

在職阿里6年,一個29歲女軟體測試工程師的心聲