ThreadLocal 总结

threadLocal可以避免在多线程程序中使用大量的synchronied同步锁,因为这样会降低性能,将会有多线程安全问题的变量放到threadLocal中就ok了
Spring控制的service层 dao层对象都是单例的,spring用threadlocal的方式将所有成员变量管理起来,所以不存在多线程问题


-------------------------
在web应用中,将用户信息存放在session中,只有Action层才能拿到用户信息,service层,DB层, DB Interceptor层 要取得用户信息的话,适合使用ThreadLocal。

ThreadLocal的机制是将浏览器发送的request线程 和 本地线程做绑定。以取得数据共享。

GlobalDate 是一个带有ThreadLocal的容器。
GlobalData 最好放在 过滤器中, 而不是放在BaseAction的构造方法中
因为如果action是单例的话, 不会每次request请求 都调用其构造方法
DWR 查询请求也是request请求,也会经过过滤器, 所以用过滤器的方式可行。


package cia.common.base.bean;

import java.io.Serializable;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;

import org.apache.log4j.Logger;

import cia.common.base.constants.Constants;
import cia.common.base.exception.DomainException;


public class GlobalData implements Serializable {
	private static final long serialVersionUID = 1L;
	private static ThreadLocal session = new ThreadLocal();

    private BaseUserInfo baseUserInfo;
    private String ip;

    public String getIp() {
		return ip;
	}

	public void setIp(String ip) {
		this.ip = ip;
	}

	public BaseUserInfo getBaseUserInfo() {
		return baseUserInfo;
	}

	public void setBaseUserInfo(BaseUserInfo baseUserInfo) {
		this.baseUserInfo = baseUserInfo;
	}


    public static  GlobalData getCurrentInstance() throws DomainException {
        GlobalData gi = (GlobalData) session.get();
        return gi;
    }

    public static  GlobalData getCurrentInstanceWithoutException() {
        GlobalData gi = (GlobalData) session.get();
        return gi;
    }

    public static  void setCurrentInstance(GlobalData gi) {
        session.set(gi);
    }


    public static GlobalData getFromRequest(HttpServletRequest request) throws DomainException{
        HttpSession httpSession = request.getSession(false);
        GlobalData globalInfo = (GlobalData) httpSession
                .getAttribute(Constants.GLOBAL_DATA);
        return globalInfo;
    }

}


BaseAction中将request和GlobalData做绑定。
public BaseAction(){
		try {
			HttpServletRequest request = ServletActionContext.getRequest();
			GlobalData globalInfo = GlobalData.getFromRequest(request);
			GlobalData.setCurrentInstance(globalInfo);
		} catch(NullPointerException e){
			//不处理该异常
			logger.info(""+e.getMessage());
		} catch (Exception e) {
			logger.error("异常:"+e.getMessage(),e);
		}

	}


Service层使用的时候,从GlobalData中拿数据。
		GlobalData globalInfo = GlobalData.getCurrentInstance();
		BaseUserInfo userInfo = globalInfo.getBaseUserInfo();



猜你喜欢

转载自tristan-s.iteye.com/blog/1021924