首页 > 编程语言 > 详细

JAVA 线程基本知识汇总--ThreadLocal 和 InheritableThreadLoc

时间:2015-10-03 08:24:30      阅读:339      评论:0      收藏:0      [点我收藏+]
package org.test;

public class ThreadLocalTest {
	public static void main(String[] args) {
		User user = new User(new ThreadLocal<String>());
		Book book = new Book();
		Thread t1 = new Thread(new UnSafeRunnable(user, "pat", book));
		Thread t2 = new Thread(new UnSafeRunnable(user, "zhenglong", book));
		t1.start();
		t2.start();
	}
}

class Book {
	private String name;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

}

class User {
	private ThreadLocal<String> name;

	public User(ThreadLocal<String> name) {
		this.name = name;
	}

	public String getName() {
		return name.get();
	}

	public void setName(String names) {
		name.set(names);
	}

}

class UnSafeRunnable implements Runnable {
	private User user;
	private String name;
	private Book book;

	public UnSafeRunnable(User user, String name, Book book) {
		this.user = user;
		this.name = name;
		this.book = book;
	}

	@Override
	public void run() {
		user.setName(name);
		book.setName(name);
		try {
			Thread.sleep(1000);
		} catch (InterruptedException e) {
			Thread.currentThread().interrupt();
		}
		System.err.println(user.getName() + "user");
		System.err.println(book.getName() + "book");
	}
}

    我的工具类: 在拦截起中间 将属性保存到ThreadLocal中间去,确保在单个线程中间的全部流程中都可以获取到我们复制的属性 这也是ThreadLocal的最大的用途

  

package com.chelement.core.common;

import com.chelement.core.common.vo.ChannelUserTokenDetailVO;
import com.chelement.core.common.vo.ChelementUserTokenDetailVO;
import com.chelement.core.common.vo.CustomerTokenDetailVO;

/**
 * 权限工具类for 缓存
 * 
 * @author pat
 * 
 */
public class AccessControllerUtil {

	private static ThreadLocal<ChannelUserTokenDetailVO> threadLocal_channel_user = new ThreadLocal<ChannelUserTokenDetailVO>();

	private static ThreadLocal<ChelementUserTokenDetailVO> threadLocal_chelement_user = new ThreadLocal<ChelementUserTokenDetailVO>();

	private static ThreadLocal<CustomerTokenDetailVO> threadLocal_customer_user = new ThreadLocal<CustomerTokenDetailVO>();

	private AccessControllerUtil() {
	}

	public static ChannelUserTokenDetailVO getChannelUserDetailFromThreadLocal() {
		return threadLocal_channel_user.get();
	}

	public static void setChannelUserDetailFromThreadLocal(ChannelUserTokenDetailVO newValue) {
		threadLocal_channel_user.set(newValue);
	}

	public static void removeChannelUserDetailFromThreadLocal() {
		threadLocal_channel_user.remove();
	}

	public static ChelementUserTokenDetailVO getChelementUserDetailFromThreadLocal() {
		return threadLocal_chelement_user.get();
	}

	public static void setChelementUserDetailFromThreadLocal(ChelementUserTokenDetailVO newValue) {
		threadLocal_chelement_user.set(newValue);
	}

	public static void removeChelementUserDetailFromThreadLocal() {
		threadLocal_chelement_user.remove();
	}

	public static CustomerTokenDetailVO getCustomerDetailFromThreadLocal() {
		return threadLocal_customer_user.get();
	}

	public static void setCustomerDetailFromThreadLocal(CustomerTokenDetailVO newValue) {
		threadLocal_customer_user.set(newValue);
	}

	public static void removeCustomerDetailFromThreadLocal() {
		threadLocal_customer_user.remove();
	}
}

  

package com.chelement.core.common;

import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;

import com.alibaba.fastjson.JSON;
import com.chelement.business.enums.permission.SysRoleEnum;
import com.chelement.core.channelManagement.dal.domain.Channel;
import com.chelement.core.channelManagement.dal.domain.ChannelUser;
import com.chelement.core.channelManagement.service.ChannelService;
import com.chelement.core.channelManagement.service.ChannelUserService;
import com.chelement.core.common.vo.BaseTokenDetailVO;
import com.chelement.core.common.vo.ChannelUserTokenDetailVO;
import com.chelement.core.common.vo.ChelementUserTokenDetailVO;
import com.chelement.core.common.vo.CustomerTokenDetailVO;
import com.chelement.core.customerManagement.service.CustomerService;
import com.chelement.core.exceptions.BizException;
import com.chelement.core.houseManagement.dal.domain.Community;
import com.chelement.core.houseManagement.service.CommunityService;
import com.chelement.core.sysManagement.service.ChelementUserService;
import com.chelement.core.utils.PermissionUtil;
import com.chelement.core.web.common.ResultData;

/**
 * 
 * @author pat super
 */
public class CoreAccessControllerFilter extends HandlerInterceptorAdapter {

	@Autowired
	private ChannelUserService channelUserService;

	@Autowired
	CustomerService customerService;

	@Autowired
	ChelementUserService chelementUserService;

	@Autowired
	CommunityService communityService;

	@Autowired
	ChannelService channelService;

	@Override
	public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
		String token = request.getHeader("token");
		if (StringUtils.isNotBlank(token)) {
			String result = PermissionUtil.exiteToken(token);
			if (result != null && result.equals("true")) {
				String type = token.substring(0, 1);
				BaseTokenDetailVO detailVO = PermissionUtil.getTokenDetailByToken(token);
				String accountId = detailVO.getAccountId();
				switch (type) {
				case "1":
					ChannelUserTokenDetailVO channelUserTokenDetailVO = new ChannelUserTokenDetailVO(detailVO);
					ChannelUser channelUser = channelUserService.selectChannelUserWithCommunityIds(accountId);
					String channelId = channelUser.getChannelId();
					channelUserTokenDetailVO.setChannelId(channelId);
					if (detailVO.getRoleName().equals(SysRoleEnum.经纪人.getValue())) {
						List<String> communityIds = channelUser.getCommunityIds();
						channelUserTokenDetailVO.setCommunityIds(communityIds);
					} else if (detailVO.getRoleName().equals(SysRoleEnum.管理员.getValue()) || detailVO.getRoleName().equals(SysRoleEnum.会计师.getValue())) {
						Community queryCommunity = new Community();
						queryCommunity.setChannelId(channelId);
						List<Community> communities = communityService.selectList(queryCommunity);
						List<String> communityIds = new ArrayList<String>();
						for (Community community : communities) {
							communityIds.add(community.getId());
						}
						channelUserTokenDetailVO.setCommunityIds(communityIds);
					}
					AccessControllerUtil.setChannelUserDetailFromThreadLocal(channelUserTokenDetailVO);
					break;
				case "2":
					CustomerTokenDetailVO customerTokenDetailVO = new CustomerTokenDetailVO(detailVO);
					AccessControllerUtil.setCustomerDetailFromThreadLocal(customerTokenDetailVO);
					break;
				case "3":
					ChelementUserTokenDetailVO chelementUserTokenDetailVO = new ChelementUserTokenDetailVO(detailVO);
					Channel query = new Channel();
					query.setChelementUserId(accountId);
					List<Channel> channels = channelService.selectList(query);
					List<String> channelIds = new ArrayList<String>();
					for (Channel channel : channels) {
						channelIds.add(channel.getId());
					}
					chelementUserTokenDetailVO.setChannelIds(channelIds);
					AccessControllerUtil.setChelementUserDetailFromThreadLocal(chelementUserTokenDetailVO);
					break;
				default:
					throw new BizException("账户类型不存在!");
				}
				return true;
			}
			ResultData data = getResultData();
			response.setCharacterEncoding("utf-8");
			response.setContentType("text/html;charset=UTF-8");
			OutputStream out = response.getOutputStream();
			PrintWriter pw = new PrintWriter(new OutputStreamWriter(out, "utf-8"));
			// 返回json格式的提示
			pw.println(JSON.toJSON(data));
			pw.flush();
			pw.close();
			return false;
		}
		return false;
	}

	@Override
	public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
		AccessControllerUtil.removeChannelUserDetailFromThreadLocal();
	}

	private ResultData getResultData() {
		ResultData data = new ResultData();
		data.setSuccess(false);
		data.setDescription("Token 无效");
		return data;
	}
}

   至于

InheritableThreadLocal

则是将可见扩张到子类: 

package org.test;

public class ThreadLocalTest {
	public static void main(String[] args) {
		User user = new User(new ThreadLocal<String>(),
				new InheritableThreadLocal<String>());
		Book book = new Book();
		Thread xx = new Thread(new SonUnsafeThread(new UnSafeRunnable(user,
				"pat1", book)));
		xx.start();
	}
}

class Book {
	private String name;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

}

class User {
	private ThreadLocal<String> name;

	private InheritableThreadLocal<String> test;

	public User(ThreadLocal<String> name, InheritableThreadLocal<String> test) {
		this.name = name;
		this.test = test;
	}

	public String getName() {
		return name.get();
	}

	public void setName(String names) {
		name.set(names);
	}

	public String getTest() {
		return test.get();
	}

	public void setTest(String names) {
		test.set(names);
	}

}

class UnSafeRunnable implements Runnable {
	private User user;
	private String name;
	private Book book;

	public UnSafeRunnable(User user, String name, Book book) {
		this.user = user;
		this.name = name;
		this.book = book;
		user.setName(name);
		book.setName(name);
		user.setTest(name);
	}

	@Override
	public void run() {

		try {
			Thread.sleep(1000);
		} catch (InterruptedException e) {
			Thread.currentThread().interrupt();
		}
		System.err.println(user.getTest() + "test");
	}

	public User getUser() {
		return user;
	}

	public void setUser(User user) {
		this.user = user;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public Book getBook() {
		return book;
	}

	public void setBook(Book book) {
		this.book = book;
	}

}

/**
 * 
 * @author patzheng 597439394@163.com
 *
 */
class SonUnsafeThread implements Runnable {
	private UnSafeRunnable thread;

	public SonUnsafeThread(UnSafeRunnable thread) {
		this.thread = thread;
	}

	@Override
	public void run() {
		System.err.println(thread.getUser());
		System.err.println(thread.getUser().getName() + "ThreadLocal");
		System.err.println(thread.getUser().getTest() + "sonThreadLocal");
	}
}


JAVA 线程基本知识汇总--ThreadLocal 和 InheritableThreadLoc

原文:http://my.oschina.net/payzheng/blog/513276

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!