使用FindBugs产生更少的错误代码

不久前,我们的JCG合作伙伴Kees Jan的论坛上的Java监视器用户发现,尽管整体内存利用率很低,但他的系统仍在强制执行大量的完整垃圾回收。 对问题原因的粗略估计表明,正在使用的其中一个库可能对System.gc()进行了调用。 让我们看看我们的合作伙伴在澄清类似问题以减少错误代码方面要说些什么。

…我确实发现有一个工具可以解决System.gc()问题。 它被恰当地命名为FindBugs 。 实际上,有几种( PMDCheckStyle是其他类似的工具),但是FindBugs很好,因为您实际上不需要应用程序的源代码来检查它的错误。 您需要的只是JAR文件和/或类文件。 另一个重要功能是每个报告都记录得很好。 几分钟后,您不仅会收到模糊的警告,而且您会放弃这些警告,还可以在线找到每种警告解释

这是FindBugs的示例输出,可以在Java监视器的探针上运行它。

$ findbugs -textui -effort:max java-monitor-probes/build/WEB-INF/classes
The following classes needed for analysis were missing:
  javax.servlet.http.HttpServlet
  javax.servlet.Filter
  javax.servlet.http.HttpServletResponse
  javax.servlet.ServletException
  javax.servlet.ServletConfig
  javax.servlet.FilterConfig
  javax.servlet.ServletRequest
  javax.servlet.ServletResponse
  javax.servlet.FilterChain
Missing classes: 7

从该报告中,您可以发现FindBugs找不到代码本身的任何问题。 代码依赖于某些类。 这些未包括在分析中。 由于这些都是Sun提供的类,因此我认为它们没有错误。 *咳嗽*

无论如何。 让我们进行更多的分析。 这是针对著名的MySQL JDBC驱动程序运行FindBugs时的输出。 我敢肯定,今天很多人都在生产中使用它。 这段代码会产生更多结果, FindBugs需要花一些时间来分析整个程序包。 我只显示了154条警告中的几行。

$ findbugs -textui -effort:max mysql-connector-java-5.1.5-bin.jar 
  ......
H C NP: Method call in com.mysql.jdbc.profiler.ProfilerEvent.pack() passes null for unconditionally dereferenced parameter of writeBytes(byte[], byte[], int)  Method invoked at ProfilerEvent.java:[line 375]
  ......
M D NP: Possible null pointer dereference of s1 on path that might be infeasible in com.mysql.jdbc.ConnectionImpl.nullSafeCompare(String, String)  Dereferenced at ConnectionImpl.java:[line 341]
  ......
M C NP: Method call in com.mysql.jdbc.DatabaseMetaData.getInstance(ConnectionImpl, String) passes null for unconditionally dereferenced parameter of new DatabaseMetaData(ConnectionImpl, String)  Method invoked at DatabaseMetaData.java:[line 632]
  ......
H S SQL: Method com.mysql.jdbc.DatabaseMetaData.getColumnPrivileges(String, String, String, String) passes a nonconstant String to an execute method on an SQL statement  At DatabaseMetaData.java:[line 2156]
H S SQL: Method com.mysql.jdbc.DatabaseMetaData.getTablePrivileges(String, String, String) passes a nonconstant String to an execute method on an SQL statement  At DatabaseMetaData.java:[line 4638]
M S SQL: Method com.mysql.jdbc.ConnectionImpl.setSessionVariables() passes a nonconstant String to an execute method on an SQL statement  At ConnectionImpl.java:[line 5074]
  ......
M M IS: Inconsistent synchronization of com.mysql.jdbc.CallableStatement.outputParameterResults; locked 50% of time  Unsynchronized access at CallableStatement.java:[line 1948]
M M IS: Inconsistent synchronization of com.mysql.jdbc.StatementImpl.wasCancelledByTimeout; locked 83% of time  Unsynchronized access at PreparedStatement.java:[line 1756]
  ......
Warnings generated: 154
  ......

学习读取FindBugs的输出需要花费一些时间。 当我对应该编写的代码感到无聊或沮丧时,我所做的只是通过一定的错误或警告来工作。 这是我的拖延工作。 :-)

我只是挑选出了开发人员认为我有问题的东西:“为无条件取消引用的参数传递null”。 真是的 NullPointerException任何人? 当然,这很可能是测试代码,甚至是仍在开发中的未使用的代码。 怎么样:“将非常量字符串传递给SQL语句的execute方法”。 嗯 如果不加以检查,则可能是SQL注入漏洞的媒介。

我之前说过, FindBugs不需要您访问应用程序的源代码来查找其中的错误。 只是为了开怀大笑,让我们看一下Java EE应用程序服务器的基石之一:Oracle JDBC驱动程序。

$ findbugs -textui -effort:max ojdbc6.jar
  ......
M B Dm: oracle.sql.ConverterArchive.openArchiveforRead() invokes System.exit(...), which shuts down the entire virtual machine  At ConverterArchive.java:[line 375]
M B Dm: oracle.sql.ConverterArchive.closeArchiveforRead() invokes System.exit(...), which shuts down the entire virtual machine  At ConverterArchive.java:[line 390]
  ......
M B ES: Comparison of String objects using == or != in oracle.jdbc.connector.OracleConnectionRequestInfo.equals(Object)   At OracleConnectionRequestInfo.java:[line 104]
  ......
H C IL: There is an apparent infinite recursive loop in oracle.jdbc.rowset.OracleCachedRowSet.updateBlob(int, InputStream, long)  At OracleCachedRowSet.java:[line 6365]
H C IL: There is an apparent infinite recursive loop in oracle.jdbc.rowset.OracleCachedRowSet.updateClob(int, Reader, long)  At OracleCachedRowSet.java:[line 6445]
H C IL: There is an apparent infinite recursive loop in oracle.jdbc.rowset.OracleCachedRowSet.updateNClob(int, Reader, long)  At OracleCachedRowSet.java:[line 6535]
  ......
Warnings generated: 1028
  ......

该驱动程序会产生不少于1028条警告。 哇。 我并不是说Oracle JDBC驱动程序实际上是一段糟糕的代码。 我只是发现它闻起来有点香 。 :-) Oracle的开发人员可能希望破解findbugs报告的警告。 那里几乎没有什么性能和稳定性建议。

是的: findbugs检查System.gc()的使用

PS。 请注意,我使用的是FindBugs 1.3.7。 此版本的FindBugs有一个错误,该错误导致其生成误报以清理数据库资源

PPS。 我在跟谁开玩笑:我确实认为Oracle驱动程序不好。 无限循环? System.exit()? 请。

始终帮助有需要的…编码人员;-)

拜伦

相关文章:


翻译自: https://www.javacodegeeks.com/2011/02/using-findbugs-to-produce-substantially.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值