我们使用Coverity来识别Java代码中潜在的安全和质量缺陷。在我们的一个单元测试中,我们有一些涉及数据库连接代码的测试:
Connection connection = mock(Connection.class);
Statement statement = mock(Statement.class);
when(connection.createStatement()).thenReturn(statement);
Coverity抱怨潜在的资源泄漏:
CID 21920:资源泄漏(Resource_leak(4。leaked_resource:无法保存或关闭连接创建的资源.createStatement((
我对Mockito工作原理的理解是,connection.getStatement()
从未被实际调用,因此没有创建需要稍后关闭的语句。(这与数据库中需要关闭JDBC连接的典型情况相反。(
我的理解正确吗?可以公平地说,这是Coverity的虚假报告,是由getConnection()
在嘲笑背景下的非典型行为引起的吗?如果没有,请纠正我。
我认为你的理解不太正确。
在您的代码中,connection.createStatement()
确实被调用,但它不会在将在某个地方的数据库上创建资源的"真实"连接上被调用。Mockito创建的mockConnection
实现只跟踪方法被调用的情况,并返回null
。稍后,当调用thenReturn()
方法时,Mockito可以将该调用与传递给thenReturn()
的值链接到createStatement()
,以便当对其调用createStatement()
方法时,模拟Connection
可以返回模拟Statement
。
最终,这是一份来自Coverity的误报报告:这里不存在资源泄漏问题。然而,在测试代码上运行Coverity这样的扫描程序的价值存在问题。特别是,我不确定测试代码中怎么会有安全漏洞,因为它不是交互式的,也不是你发送给客户或上传到某个服务器的东西。