Hi, I'm testing a simple DAO layer with mockito but I found a problem, basically a hard to test interface and I was wondering if you could give me some insight...
This is the method I want to test:
public Person getById(UserId id) {
final Person person = new PersonImpl();
gateway.executeQuery(GET_SQL + id.getUserId(), new ResultSetCommand(){
public int work(ResultSet rs) throws SQLException {
if(rs.next()){
person.getName().setGivenName(rs.getString("name"));
person.getName().setFamilyName(rs.getString("last_name"));
}
return 0;
}
});
return person;
}
I use a DatabaseGateway that is my interface between java code and SQL, and that method accepts an anonymous class, this is the method executeQuery of the gateway:
public int executeQuery(String sql, ResultSetCommand cmd) {
try{
Connection cn = createConnection();
PreparedStatement st = cn.prepareStatement(sql);
int result = cmd.work(st.executeQuery());
cn.close();
return result;
}catch(Exception e){
throw new RuntimeException("Cannot Create Statement for sql " + sql,e);
}
}
The thing is that, because of that anonymous class, It's getting harder to test PersonDAO.
I can refactor the whole code, even remove the anonymous class if someone suggest a better design (I'm sure there's a simpler one, but I just can't seem to find it).
Thanks everyone for the suggestions.
PD: if you need further information, feel free to ask
EDIT: Test that's hard to do
public void testGetPersonById(){
DatabaseGateway gateway = mock(DatabaseGateway.class);
when(gateway.executeQuery(anyString(),any(ResultSetCommand.class)));
PersonDAO person_dao = new PersonDAOImpl(gateway);
Person p = person_dao.getById(new UserId(Type.viewer,"100"));
}
See? ResultCommand is part of the mock, and I'm interested in testing that code too... should I do a separate test for that specific command?