您的位置:首页 > 编程语言 > Java开发

ServletActionContext.getServletContext()方法不是什么时候都能用的

2012-10-17 17:19 567 查看
1.当时我是这么建立这个类的

Java代码 



public class StaticAction
extends ActionSupport { 
    static { 
        logDir = ServletActionContext.getServletContext().getRealPath("/");
//在这里打个断点 
    } 
 


2.在com.opensymphony.xwork2.DefaultActionInvocation 类下大约第362行

Java代码 



private void init()
throws Exception { 
        Map contextMap = createContextMap(); 
 
        createAction(contextMap); //在这个方法打个断点,该方法会去创建你所调用的Action。详情可以看看它里面的objectFactory.buildAction(proxy.getActionName(), proxy.getNamespace(), proxy.getConfig(), contextMap);这一句 

 
        if (pushAction) { 
            stack.push(action); 
        } 
 
        invocationContext = new ActionContext(contextMap);
//注意你所调用的Action,它的ActionContext在这里才会创建。 
        invocationContext.setName(proxy.getActionName()); 
 
        // get a new List so we don't get problems with the iterator if someone changes the list 

        List interceptorList = new ArrayList(proxy.getConfig().getInterceptors()); 

        interceptors = interceptorList.iterator(); 
    } 

好了。调试运行。因为StaticAction有静态代码块,而objectFactory在创建action实例时,使用的是Class.forName(String cls)方式,它的具体实现如下:

Java代码 



java.lang.Class.java 
 
    public static Class<?> forName(String className)  

                throws ClassNotFoundException { 

        return forName0(className,
true, ClassLoader.getCallerClassLoader()); 
    } 

看到forName0的第二个参数设置为true了吗?表示该类被JVM装载后,要不要立即初始化,如果设置成false,表示在将初始化的工作推迟到了newInstance的时候进行.所以,当方法createAction(contextMap)被调用时,要执行的StaticAction的静态代码块肯定会被调用的。

当运行到ServletActionContext.getServletContext().getRealPath("/")这一句时,继续查看ServletActionContext.getServletContext()的来源:

org.apache.struts2.ServletActionContext.java 大概第137行

Java代码 



public static ServletContext getServletContext() { 

    return (ServletContext) ActionContext.getContext().get(SERVLET_CONTEXT); 



可以看到其实调用的是ActionContext.getContext().get(SERVLET_CONTEXT);过来的,而咱们在最开始也看到了createAction(contextMap);方法在 invocationContext = new ActionContext(contextMap); 方法执行之前,是无法正常得到SERVLET_CONTEXT的,所以,就会出空指针异常了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
相关文章推荐