如何使用Mockito测试我的DAO方法?

时间:2018-06-05 09:10:31

标签: java unit-testing junit mockito dao

我试图为我的DAO写一些测试。我在这里已经学过一些教程/答案,但大多数都不适用于我的DAO。

示例代码:尝试根据给定的选择器(<或>)从数据库中获取选举。

public class AdminDaoImpl extends DaoImpl implements AdminDao {

    private final Logger LOGGER = Logger.getLogger(getClass().getName());

    @Override
    public ElectionListResponse getElections(char selector) {
        ElectionListResponse electionListResponse = new ElectionListResponse();

        String query = NamedQueries.GET_ELECTIONS_BEGIN + selector + NamedQueries.GET_ELECTIONS_END;

        try {
            con = sqlConnection.getConnection();
            stmt = con.prepareStatement(query);
            rs = stmt.executeQuery();

            DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm");

            while (rs.next()) {
                Election election = new Election();
                election.setElectionID(rs.getInt("id"));
                election.setElectionName(rs.getString("name"));
                election.setStartDate(df.format(rs.getDate("startDate")));
                election.setEndDate(df.format(rs.getDate("endDate")));
                electionListResponse.addElection(election);
            }
            return electionListResponse;
        } catch (SQLException e) {
            LOGGER.log(Level.SEVERE, "Cant get elections. ", e);
        } finally {
            closeConnection();
        }
        return null;
    }

这是上面代码扩展的DAO:

public abstract class DaoImpl implements Dao {

    private final Logger LOGGER = Logger.getLogger(getClass().getName());

    @Inject
    public SQLConnection sqlConnection;

    public Connection con;
    public PreparedStatement stmt;
    public ResultSet rs;

    public void closeConnection() {
        try {
            if (con != null) con.close();
            if (stmt != null) stmt.close();
            if (rs != null) con.close();
        } catch (SQLException e) {
            LOGGER.log(Level.SEVERE, "Can't close connection with database. ", e);
        }
    }
}

我试图应用一些我在网上找到的代码,这就是我现在拥有的代码:

@RunWith(MockitoJUnitRunner.class)
public class AdminDaoImplTest {

    @Mock
    DataSource mockDataSource;
    @Mock
    Connection mockConn;
    @Mock
    PreparedStatement mockPreparedStmnt;
    @Mock
    ResultSet mockResultSet;

    @BeforeClass
    public static void setUpClass() throws Exception {
    }

    @AfterClass
    public static void tearDownClass() {
    }

    @Before
    public void setUp() throws SQLException {
        when(mockDataSource.getConnection()).thenReturn(mockConn);
        when(mockDataSource.getConnection(anyString(), anyString())).thenReturn(mockConn);
        doNothing().when(mockConn).commit();
        when(mockConn.prepareStatement(anyString(), anyInt())).thenReturn(mockPreparedStmnt);
        doNothing().when(mockPreparedStmnt).setString(anyInt(), anyString());
        when(mockPreparedStmnt.executeQuery()).thenReturn(mockResultSet);
        when(mockResultSet.next()).thenReturn(Boolean.TRUE, Boolean.FALSE);
    }

    @After
    public void tearDown() {
    }

    @Test
    public void testCreateWithNoExceptions() throws SQLException {

        ElectionListResponse electionListResponse = new ElectionListResponse();

        AdminDaoImpl instance = new AdminDaoImpl();
        instance.getElections('>' );

        //verify and assert
        verify(mockConn, times(1)).prepareStatement(anyString(), anyInt());
        verify(mockPreparedStmnt, times(1)).execute();
        verify(mockConn, times(1)).commit();
        verify(mockResultSet, times(2)).next();
        verify(mockResultSet, times(1)).getInt("id");
        verify(mockResultSet, times(1)).getString("name");
        verify(mockResultSet, times(1)).getDate("startDate");
        verify(mockResultSet, times(1)).getDate("endDate");
    }


}

我该如何测试?你能生产一些代码样本吗?提前谢谢!

空指针:

java.lang.NullPointerException
    at org.han.ica.oose.sneeuwklokje.database.admin.AdminDaoImpl.getElections(AdminDaoImpl.java:28)
    at org.han.ica.oose.sneeuwklokje.database.admin.AdminDaoImplTest.testGetElectionsNoExceptions(AdminDaoImplTest.java:77)
    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)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:27)
    at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:27)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
    at org.mockito.internal.runners.JUnit45AndHigherRunnerImpl.run(JUnit45AndHigherRunnerImpl.java:37)
    at org.mockito.runners.MockitoJUnitRunner.run(MockitoJUnitRunner.java:62)
    at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
    at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:68)
    at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47)
    at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242)
    at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70)

1 个答案:

答案 0 :(得分:1)

您应该在测试中添加以下字段:

@InjectMocks
private AdminDaoImpl

这会在你的课堂上注入嘲笑,让你进行测试。

您获得的NullPointerException可以通过这种方式修复(在测试类中):

@Mock
private SQLConnection mockSqlConnection;

在setup方法中添加:

when(mockSqlConnection.getConnection()).thenReturn(mockConn);