在无法单步调试的情况下找Bug的技巧

时间:2022-06-19 16:43:45

比如说你有一个大的模块A,其组成部分有B,C,D这3个小的模块,现在A出了一个BUG,因为某种原因的限制你无法单步调试。怎么较快地定位BUG发生的根源?

这里记录一下刚才我在找BUG的时候采用的思路,为了具体化,我就以这篇文章提到的问题为例http://www.cnblogs.com/qrlozte/p/3515836.html

  login.jsp >>> 用户输入id和密码

  LoginServlet >>> 数据库查询,验证,如果验证通过,在session中保存用户id,然后跳转到welcome.jsp,否则跳转到login.jsp显示错误信息

  welcome.jsp >>> 根据session中的用户id显示相应的信息

  BUG:在LoginServlet中,用户id保存在session中,但是在没有关闭浏览器的情况下session中的用户id就丢失了,症状是session.getAttribute(用户id)返回null

我的思路如下,总之就是复杂问题简单化,瘦身法!:

  1、数据库验证这一块是没有问题的,因为数据库验证的代码在别的地方也使用过并且功能正常。

    >>> 删掉数据库验证以及根据验证结果进行逻辑判断的代码,LoginServlet只做一件事:把用户id保存到session中,然后跳转到welcome.jsp

    >>> 测试,问题仍然存在,说明BUG的确跟数据库验证的代码无关

  2、welcome.jsp是没有问题的,因为我即便不让LoginServlet跳转到welcome.jsp,session中的用户id照样会丢失

    >>> 删掉welcome.jsp,LoginServlet不跳转到welcome.jsp,仅仅把用户id保存到session中

    >>> 测试,问题仍然存在,说明BUG的确跟welcome.jsp无关

  3、因为LoginServlet只做了2件事,request.getParameter,request.getSession().setAttribute(),不能再瘦身了,我基本上可以确认LoginServlet是没有问题的

    >>> 确认LoginServlet的正确性

那么现在问题只可能出在login.jsp身上了,经过同样的思路,很快就把问题聚焦到了action那里,也就找到了BUG的根源所在

 

实际上,跟上面所谓的“瘦身法”对应的另一种方法也很高效,“问题还原法”:先根据你出BUG模块的基本逻辑框架(比如这里的提交->验证->跳转),搭建一个尽可能精简的模块,扔掉一切多余的代码。在这种情况下,因为代码很精简,你很可能发现BUG不见了,但是你也不知道BUG究竟源自哪里,没关系,慢慢添加代码,把你的精简版模块慢慢地还原为完整版的模块,这个过程其实也就是还原问题的过程,一旦你找到了BUG消失和BUG出现的那个临界点,你实际上就找到BUG的根源所在。