java业务代码,随时取出登录用户信息的思路

方法一,使用继承controller的方式,baseController封装了公共的方法:

1.新建一个BaseController,里面写好公共方法,这些方法可以从springContextHoder取出当前线程绑定的请求信息,例如request和response,在这些方法里对request进行取出或者分析操作,例如header里的token。

2.其他controller则继承BaseController,调用父类的方法,则可以随时取出当前登录用户信息。

注意:因为spring默认是单例的,所以BaseController中不要写成员变量,要取东西直接由方法返回即可

 

方法二,使用ThreadLocal的方式:

1.新建一个工具类,用来保存用户信息

public class ThreadLocalTool {

    private ThreadLocalTool(){}

    private static final ThreadLocal<Student> LOCAL = new ThreadLocal<>();

    public static void put(Student sysUser){
        LOCAL.set(sysUser);
    }

    public static Student get(){
        return LOCAL.get();
    }

    public static void remove(){
        LOCAL.remove();
    }

}

 

2.在过滤器或拦截器获取到用户信息后,调用该工具类put方法,将用户信息存入

我这里就随便用个controller模拟已经登录成功了,然后把数据放进去,使用完毕后一定要remove,把threadloacl清除掉,不然会有内存泄漏风险(听说的,我也没试过)

@RestController
@RequestMapping("/test")
public class TestController {

    private static Logger logger = Logger.getLogger(TestController.class);

    @Resource(name = "testServiceImpl")
    private TestService testServiceImpl;

    @GetMapping("/getUser111")
    public String getUser111(String id) throws InterruptedException {
     //保存用户信息 ThreadLocalTool.put(
new com.aaa.pojo.Student(id,0,""));
     //模拟执行业务 testServiceImpl.getUser();
     //清除用户信息 ThreadLocalTool.remove();
return "success了";

 

3.接口我就省略了,直接看实现类,实现类里用了睡眠,模拟处理业务数据的耗时

@Service(value = "testServiceImpl")
public class TestServiceImpl implements TestService {

@Override
public String getUser() throws InterruptedException {
Student student = ThreadLocalTool.get();
System.out.println("第一次取出来用户 = " + Thread.currentThread().getName() + ": " + student.getName());
Thread.sleep(10000);
System.out.println("第二次取出来用户 = " + Thread.currentThread().getName() + ": " +student.getName());
return null;

}
}

 

3.用postman准备好多个接口,快速连续发送请求,我这里用了五个

 

 4.看结果吧,可以看到,五次请求分别存进去了5个不同的用户,后面存进去的用户并没有把前面的用户顶掉,每个线程取出来的都是独立的,可见threadlocal是有线程隔离性的

 

posted @ 2023-04-09 22:30  黄大虾  阅读(279)  评论(0编辑  收藏  举报