How to Mock "DriverManager.getConnection"

4,360 views
Skip to first unread message

Christian Schneider

unread,
Jul 25, 2013, 6:57:43 AM7/25/13
to moc...@googlegroups.com
Hi,
I need to test an existing class that gets a connection by calling the static method DriverManager.getConnection(...).

Any ideas how to mock that?


Example Class:
public class Query implements Runnable {

private final String statement;
private Connection connection;
// ...

@Override
public void run() {
Statement jdbcStatement = null;
try {
this.connection = DriverManager.getConnection("jdbc:hive2://" + this.hiveHost + ":" + this.hivePort + "/default", "hive", "");
jdbcStatement = this.connection.createStatement();

final boolean resultSetAvailable = jdbcStatement.execute(constructStatementWithKey());

if (resultSetAvailable)  {
this.resultSet = jdbcStatement.getResultSet();
// ...
}
else {
closeQuery();
}
}
catch (final SQLException e) {
// ...
}
// ...
}
}

Example Test:
public class QueryTest {

Query cut =  new Query(null, null, "1", "SELECT * FROM foo", 1);

@Before
public void setup()
{
// somehow inject a mock for DriverManager.getConnection(.*);
}

@Test
public void shouldRunWithoutException() throws SQLException
{
this.query.run();
}
}


Best Regards,
Christian.

Eric Lefevre-Ardant

unread,
Jul 25, 2013, 9:50:18 AM7/25/13
to moc...@googlegroups.com
You need to wrap your static method and get it called from a class that is instantiable, or some equivalent solution.

There have been a few discussions on this on the mailing list. See
or
  https://groups.google.com/forum/#!topicsearchin/mockito/static/mockito/1Z1p6LrXpb0 (your problem is similar to mocking the call to a constructor).

Apparently, there are other mock-related projects that can mock static methods (PowerMockito, maybe ?), but from what I remember they are much to cumbersome to use.



--
You received this message because you are subscribed to the Google Groups "mockito" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mockito+u...@googlegroups.com.
To post to this group, send email to moc...@googlegroups.com.
Visit this group at http://groups.google.com/group/mockito.
For more options, visit https://groups.google.com/groups/opt_out.
 
 

KARR, DAVID

unread,
Jul 25, 2013, 12:28:43 PM7/25/13
to moc...@googlegroups.com

As another responder indicated, you either have to change your CUT (class under test) to accommodate this, or you have to use PowerMockito.  Here’s some documentation: http://code.google.com/p/powermock/wiki/MockitoUsage13.  It’s definitely more complicated than plain Mockito, but mocking a single static method is about as simple as it gets.  It can get quite a bit more complicated.  Generally, when you have to use PowerMock, it indicates a design problem in your CUT, implying that you’ve given it multiple (too many) responsibilities.  For instance, if you have code that directly accesses a database, put only the direct database access code into a DAO class, with very little conditional logic, and put the logic that depends on what you get from the database (or decides what to put there), in a separate class.

 

If you’re going to do this, however, A basic outline of what’s required is this:

 

@RunWith(PowerMockRunner.class)

@PrepareForTest(DriverManager.class) // Need this for any classes with static methods that need to be mocked.

public class MyClass {

...

    <method signature> {

        ...

        Connection connection = mock(Connection.class);

        PowerMockito.mockStatic(DriverManager.class);

        PowerMockito.when(DriverManager.getConnection(anyString(), anyString(), anyString()).thenReturn(connection);

 

 

--

Reply all
Reply to author
Forward
0 new messages