Home > Net >  About @InjectMocks and @Mock
About @InjectMocks and @Mock

Time:11-17

I want to test requestListServiceImpl this class.It contains requestListDao.

RequestListServiceImpl Code

@Override
    public PageInfo<RequestList> getAllRequest(int startPage, int pageSize, String accountName,String userName) {
        PageHelper.startPage(startPage, pageSize);
        List<RequestList> list=requestListDao.getAllRequest(accountName,userName);
        for(RequestList requestList:list) {
            switch (requestList.getStatus()) {
            case "0":
                requestList.setStatus("Waiting");
                break;
            case "1":
                requestList.setStatus("Closed");        
                break;
            case "2":
                requestList.setStatus("Cancel");
                break;
            default:
                requestList.setStatus("NAN");
                break;
            }
        }
        PageInfo<RequestList> pageInfo = new PageInfo<RequestList>(list);
        return pageInfo;
    }

@Override
    public void createRequest(RequestList requestList) {
        Integer coount=requestListDao.getTime(requestList.getCreateName());
//      AWSSnsUtil.sendMassageToSns(requestList.getAccountName());
        requestList.setTime(  coount);
        requestListDao.createRequest(requestList);
    }

Test Code:

    @InjectMocks
    RequestListServiceImpl requestListServiceImpl;
    @Mock
    RequestListDao requestListDao;

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


    @Test  //it's ok 
    public void testGetAllRequest() throws Exception {
        RequestList r=new RequestList();
        r.setStatus("0");
        when(requestListDao.getAllRequest(anyString(), anyString())).thenReturn(Arrays.<RequestList>asList(r));
        PageInfo<RequestList> res=requestListServiceImpl.getAllRequest(1,1,"1","1");
        Assert.assertNotNull(res);


    }

 @Test   //this test is error, the error is requestListServiceImpl is not mock.
    public void testCreateRequest() throws Exception {
        when(requestListDao.getTime(anyString())).thenReturn(0);
        RequestList r=new RequestList();
        r.setCreateName("demo");
        requestListServiceImpl.createRequest(r);
        verify(requestListServiceImpl).createRequest(r);

    }

Error info

org.mockito.exceptions.misusing.NotAMockException: 
Argument passed to verify() is of type RequestListServiceImpl and is not a mock!
Make sure you place the parenthesis correctly!
See the examples of correct verifications:
    verify(mock).someMethod();
    verify(mock, times(10)).someMethod();
    verify(mock, atLeastOnce()).someMethod();

When i change @InjectMocks to @Mock, The second test it's ok ,but first test it's error. I need add to a stubbing when(requestListServiceImpl.getAllRequest(anyInt(),anyInt(),anyString(),anyString())).thenReturn(new PageInfo<>());

I don't know how to do it,

Is injectmocks necessary?

CodePudding user response:

Here:

verify(requestListServiceImpl)

And

@InjectMocks
RequestListServiceImpl requestListServiceImpl;

The message is pretty clear: you verify mock objects that Mockito created for you.

@InjectMocks does not create mocks. It rather injects mocks that you have in your test class into a real object.

So, what is necessary here: read the manual or a tutorial. Meaning: don't start with Mockito by applying it immediately to your project. Instead, step back, and look at simple examples to understand how it is supposed to be used.

In your current setup: requestListServiceImpl is a real object. So you should check if that class offers you methods to verify its internal status. You triggered some action on it, but because it is a real object, Mockito doesn't know what you did. But how to actually solve this depends on YOUR code base.

CodePudding user response:

You want to test requestListServiceImpl you should use @InjectMocks so mockito calls the real method on requestListServiceImpl. When you use @Mock, the method will by default not be invoked. @InjectMocks will be the same as if you create it yourself with new requestListServiceImpl(mock(requestListDao))

When you use verify(mock).someMethod(); you have to pass a mock to that method, not @InjectMocks. You want to verify if a certain method is called on a mock inside your class under test(requestListServiceImpl).

Instead of @InjectMocks there is also @Spy, which will kinda do both, you can mock methods in requestListServiceImpl but also call the real method.

  • Related