Mockito测试错误。通缉但没有调用异常

时间:2016-09-02 16:40:38

标签: java unit-testing mocking mockito

我是Mockito的新手,无法理解什么是问题。你能说我,如何正确地做Mockito单位,因为我真的无法理解它们! 更新错误和测试类

我有下一个例外:

  

显示java.lang.NullPointerException       at ua.khpi.shapoval.autostation.service.MySqlUsersService.getUserIdByLogin(MySqlUsersService.java:49)       at ua.khpi.shapoval.autostation.dao.UsersServiceTest.testGetUserByLogin(UsersServiceTest.java:57)       at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)       at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)       at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)       at java.lang.reflect.Method.invoke(Method.java:498)       在org.junit.runners.model.FrameworkMethod $ 1.runReflectiveCall(FrameworkMethod.java:50)       在org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)       在org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)       在org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)       在org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)       在org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)       在org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)       在org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)       在org.junit.runners.ParentRunner $ 3.run(ParentRunner.java:290)       在org.junit.runners.ParentRunner $ 1.schedule(ParentRunner.java:71)       在org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)       在org.junit.runners.ParentRunner.access $ 000(ParentRunner.java:58)       在org.junit.runners.ParentRunner $ 2.evaluate(ParentRunner.java:268)       在org.junit.runners.ParentRunner.run(ParentRunner.java:363)       在org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:86)       在org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)       在org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:459)       在org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:675)       在org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:382)       在org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:192)

这是我的DAO课程:

  public class MySqlUsersDao implements UsersDao {
        /** Logger. */
        private static final Logger LOG = Logger.getLogger(MySqlUsersDao.class);

        /*
         * (non-Javadoc)
         * 
         * @see
         * ua.khpi.shapoval.autostation.dao.UsersDao#getUserIdByLogin(java.lang.
         * String)
         */
        @Override
        public int getUserIdByLogin(String login) {
            Connection connection = null;
            PreparedStatement stmt = null;
            ResultSet rs = null;
            try {
                connection = DbConnector.getConnection();
                stmt = connection.prepareStatement(Constants.UsersDao.SELECT_USER_ID_BY_LOGIN);
                stmt.setString(1, login);
                rs = stmt.executeQuery();
                while (rs.next()) {
                    return rs.getInt(1);
                }

            } catch (SQLException e) {
                LOG.error(e.getMessage());
                return 0;
            } finally {
                DbConnector.close(connection, stmt, rs);
            }
            return 0;
        }


    }

这是我的服务类

   public class MySqlUsersService implements UsersService {

    private UsersDao usersDao;
    private TransactionManager transactionManager;

    public MySqlUsersService(UsersDao usersDao, TransactionManager transactionManager) {
        this.usersDao = usersDao;
        this.transactionManager = transactionManager;
    }

    @Override
    public int getUserIdByLogin(String login) {
        return this.transactionManager.execute(() -> this.usersDao.getUserIdByLogin(login));
    }

}

这是我的Mockito测试课

public class UsersServiceTest {
    @InjectMocks
    private MySqlUsersService mockedUsersService;

    @Mock
    private static TransactionManager transactionManager;

    @Mock
    private static UsersDao usersDao;

    @Mock
    private static Users user1;

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

    }

    @Test public void testGetUserByLogin() {
        when(usersDao.getUserByLogin("user1")).thenReturn(user1);
        assertEquals(user1, mockedUsersService.getUserIdByLogin("user1")); 
        verify(transactionManager).execute(()->usersDao.getUserIdByLogin("user1"));

    }
}

2 个答案:

答案 0 :(得分:1)

如果我在

中正确理解了你的问题
verify(transactionManager).execute(()->usersDao.getUserByLogin("user1"));

之所以发生这种情况是因为函数是通过引用进行比较的,而您在测试中传递的是函数,而在实现中传递的是不同的实例。

我建议您使用ArgumentCaptor捕获函数。调用捕获的函数并验证它是否符合您的预期。

答案 1 :(得分:0)

错误消息告诉您,UtteranceProgressListener中没有执行验证语句。

我认为您的实际问题是测试类应该在测试类中使用@InjectMocks进行注释。这个注释告诉Mockito哪个类可以注入模拟:

testGetUserByLogin()

我会这样重写你的测试:

@InjectMocks
private MySqlUsersService mockedUsersService