`
ghsea
  • 浏览: 111889 次
  • 性别: Icon_minigender_1
  • 来自: 武汉
社区版块
存档分类
最新评论

一次收获甚多的调试经历

阅读更多
//LoginAction.java
package netstore.web.security;
import org.apache.struts.action.Action;
import javax.servlet.ServletContext;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.action.ActionForm;
import javax.servlet.http. HttpServletRequest;
import javax.servlet.http. HttpServletResponse;

import netstore.dao.CustomerDAO;
import netstore.dao.impl.hibernate.CustomerDAOImpl;
import netstore.framework.NetstoreBaseAction;
import netstore.model.service.INetstoreService;
import netstore.model.businessobjects.Customer;
import netstore.framework.SessionContainer;
import netstore.framework.exceptions.InvalidLoginException;
import netstore.framework.util.IConstants;
/** 如果此用户不存在,则customer为null,即用户验证失败,此时应该返回给登陆页面
*但是此时的返回值却没有体现这一点??????????????
*
*该类的基类NetstoreBaseAction是何时如何初始化的?????????????
*/
public class LoginAction extends NetstoreBaseAction {

public ActionForward execute(ActionMapping mapping,ActionForm form,
HttpServletRequest request,
HttpServletResponse response)throws Exception{
String email=((LoginForm)form).getEmail();
String password=((LoginForm)form).getPassword();
INetstoreService service=this.getNetstoreService();

//获取servlet上下文
ServletContext servlet=this.getServlet().getServletContext();
SessionContainer container=getSessionContainer(request);
//CustomerDAO test=new CustomerDAOImpl();
//Customer customer= test.findCustomer("ghsea@126.com","fish");**********1/
System.out.println(email);
System.out.println(password);
// Customer customer= test.findCustomer(email, password);************2/
if(service==null){
System.out.println("The Service is NULL;");
}
Customer customer=service.authenticate(email, password);***********3/
/* 只是利用适配器模式改变了接口,为什么利用原始的接口验证用户能够正常进行,改变接口后却
* 查找不到用户?问题出在哪里?
*/
//如果customer为null,容器将会抛出InvalidLoginException(),path="/security/signin.jsp"
//如果此用户不存在,则customer为null,即用户验证失败,此时应该返回给登陆页面
//但是此时的返回值却没有体现这一点??????????????,这一点在struts-config.xml
//中配置实现了一个全局异常,但是这个功能现在并没有正常运行???
//将该用户保存到SessionContainer
container.setCustomer(customer);
return mapping.findForward(IConstants.SUCCESS_KEY);
}
}
Customer customer=service.authenticate(email, password);是最初的验证用户的方法,authenticate(email, password)这个接口适配了findCustomer(email, password);这个接口。奇怪的是,单独对findCustomer( )进行测试时
能够验证出用户(ghsea@126.com,fish),但是方法2和方法3却找不到这个用户,只有方法1可以找到这个用户。方法1可以找到用户方法2不能找到用户,那么只有一种可能,方法2中的两个参数并不是(ghsea@126.com,fish),这两个参数是以signin.jsp->LoginForm->LoginAction这样的流程传过来的,LoginForm只是简单将jsp页面传来的数据封闭,应该不会有问题,那么问题应该出在signin.jsp,这个页面中的两个数据通过一个text,一个password输入框提供参数,由于每次测试时,只是简单的从抛出异常的页面退回到signin.jsp没有重新输入数据就提交数据,这个页面提交的并不是第一次输入的正确数据,而是默认数据(password框有一个默认值),因此方法2找不到正确的用户。那么方法3的问题出在哪儿呢?
观查Tomcat,里面打印出了ghsea@126.com,fish这样的正确信息,那么方法3的两个参数是没有错误的,方法3这个接口里面封装的一个利用Hibernate查找用户的接口,但是运行这个方法后Tomcat里面竟然没有任何Hibernate的执行过程,那么
方法3是否执行过就值得怀疑了,页面抛出的异常指示方法3这一行抛出了NullPointerException,于是该怀疑是不是由于
service本身就是null,其实早就该怀疑是这个问题,但是此前却一直考虑这个异常是由authenticate( )方法内部抛出的,这是不应该的,因为通过分析authenticate( )方法所封闭的方法findCustomer(email, password)的源码很容易发现,这个方法内部根本不会抛出空指针异常,充其量只是抛出一些自定义异常。OK,为了验证这个异常是不是由service本身就是null造成的,添加一行if(service==null){System.out.println("The Service is NULL;");}测试一下,结果tomcat下果然显示了The Service is NULL;,由此可以确定问题的根源INetstoreService service=this.getNetstoreService();这一行抛出了空指针异常,整个应用的初始化出现了问题。
查找这个问题的根源花费了几个小时,这其中还包括返回去,测试DAO层的findCustomer(email, password);这样的基础方法,结果表明这个方法最初也是不能正常执行的(非方法本身的问题,是其他DAO层的问题造成的)。在确信DAO层的这些方法能够正常执行后,再来分析这些WEB层的流程,就可以把分析的范围大大缩小,否则这些程序一层包一层,整个执行流程历经多个层,你如何能找得出问题的根源出在哪里,唯一的方法是“各个击破”。因此,这个经历该使自己重视应用开发过程中的测试了吧,即使只是写一些简单的包含main()方法的test类或者是像这个程序里面打印一些信息那样,不管怎么样,你自己要确信整个应用中哪些地方是不会出问题的(或者说基本不会有问题的),这样,在出现新问题,你去查找问题的根源时才会有的放矢,并且拥有一定的信心,否则,你只能放弃整个应用的进一步调试,因为你根本不可能找出问题所在。
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics