2015-12-10 121 views
3

我正在嘗試使用Mockito進行Spring + Hibernate項目的單元測試。以下是我的DAO類的實現:使用mockito進行DAO層的單元測試

@Repository 
public class EmployeeDAOImpl implements EmployeeDAO { 
    @Autowired 
    private SessionFactory sessionFactory; 

    public void setSessionFactory(SessionFactory sessionFactory) { 
     this.sessionFactory = sessionFactory; 
     System.out.println("Session factory"); 
    } 
    @Override 
    public ArrayList<Employees> getAllData() { 
     System.out.println("Inside get all data"); 
     Session session = sessionFactory.getCurrentSession(); 
     System.out.println("session created"); 
     Criteria cr = session.createCriteria(Employees.class, "employees").setResultTransformer(
       Criteria.DISTINCT_ROOT_ENTITY); 

     return (ArrayList<Employees>) cr.list(); 
    } 

} 

以下是我的測試類:

public class EmployeeDAOImplTest { 

    @Mock 
    private SessionFactory sessionFactory; 
    @Mock 
    private Session session; 
    @Mock 
    Criteria criteria; 
    @Spy 
    ArrayList<Employees> employees = new ArrayList<Employees>(); 

    private EmployeeDAO dao; 

    @Before 
    public void setUp() throws Exception { 
     MockitoAnnotations.initMocks(this); 
     dao = new EmployeeDAOImpl(); 
     dao.setSessionFactory(sessionFactory); 
     employees = getEmpDetails(); 
     Mockito.doReturn(session).when(sessionFactory).getCurrentSession(); 

    } 

    @Test 
    public void testGetAllData() { 
     Mockito.doReturn(criteria).when(session) 
       .createCriteria(ConceptModelDetails.class); 
     Mockito.doReturn(employees).when(criteria).list(); 
      assertEquals(employees, dao.getAllData()); 
    } 

    private ArrayList<Employees> getEmpDetails() { 
     ArrayList<Employees> array = new ArrayList<Employees>(); 
     Employees emp = new Employees(); 
     emp.setName("xyz"); 
     emp.setId(12); 
     array.add(cm); 
     return array; 
    } 

} 

employees是員工的僞排列列表。請所說的其實是他的問題here.When我運行這個測試時,我得到一個失敗與空指針異常的:

Criteria cr = session.createCriteria(Employees.class, "employees").setResultTransformer(
        Criteria.DISTINCT_ROOT_ENTITY); 

堆棧跟蹤:

java.lang.NullPointerException 
    at com.assignment.dao.impl.EmployeeDAOImpl.getAllData(EmployeeDAOImpl.java:77) 
    at com.assignment.DAOTest.EmployeeDAOImplTest.testGetAllData(EmployeeDAOImplTest.java:84) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) 
    at java.lang.reflect.Method.invoke(Method.java:606) 
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44) 
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15) 
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41) 
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20) 
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28) 
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:76) 
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50) 
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:193) 
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:52) 
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:191) 
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:42) 
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:184) 
    at org.junit.runners.ParentRunner.run(ParentRunner.java:236) 
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50) 
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:459) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:675) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:382) 
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:192) 
+0

始終包含堆棧跟蹤。 – chrylis

+0

(就此而言,請考慮使用Spring Data而不是手動編寫DAO。) – chrylis

+0

員工爲什麼是@Spy?爲什麼你要在聲明中實例化它? –

回答

3

EmployeeDAOImpl包含以下代碼:

Criteria cr = session.createCriteria(Employees.class, "employees").setResultTransformer(
      Criteria.DISTINCT_ROOT_ENTITY); 

您的測試有:

Mockito.doReturn(criteria).when(session) 
      .createCriteria(ConceptModelDetails.class); 

您正確地嘲笑了它正在返回的sessionFactorysession,只要我可以從您的代碼中知道。但是,您沒有正確地嘲笑session.createCriteria(Employee.class, "employees")(而是,您正在設置session.createCriteria(ConceptModelDetails.class)的返回值)。因此,模擬的返回值將是null。因此,當您立即解除引用時(呼叫setResultTransformer),您將獲得NullPointerException

爲了驗證這一點,嘗試步入調試器,或添加日誌語句EmployeeDAOImpl,即表現出sessionFactorysession的值,然後從session.createCriteria(...)結果。