子线程获取 Request
有时候在进行业务处理时对于一些对于业务不那么重要且对于返回结果无关的情况会开启一个新的线程进行处理,但是在开启新线程进行处理时发现无法从 RequestContextHolder 中获取到当前的请求,取出来是 null
这是因为 RequestContextHolder 中的信息都是存储在 ThreadLocal 中的,而 ThreadLocal 中的数据是使用线程进行查找的,不是该线程存储的,是无法查找到的
private static final ThreadLocal<RequestAttributes> requestAttributesHolder =
new NamedThreadLocal<RequestAttributes>("Request attributes");
private static final ThreadLocal<RequestAttributes> inheritableRequestAttributesHolder =
new NamedInheritableThreadLocal<RequestAttributes>("Request context");
复制代码
但是有时候子线程就是需要获取到当前请求怎么办呢?
<!-- more -->
此时就需要将 RequestAttributes 对象设置为子线程共享的,在开启子线程之前
// 主线程先获取到请求信息
RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();
// 设置子线程共享
RequestContextHolder.setRequestAttributes(requestAttributes,true);
复制代码
这是什么原理?
public static void setRequestAttributes(RequestAttributes attributes, boolean inheritable) {
if (attributes == null) {
resetRequestAttributes();
}
else {
if (inheritable) { // 如果为true,则将信息存储在inheritableRequestAttributesHolder中
inheritableRequestAttributesHolder.set(attributes);
requestAttributesHolder.remove();
}
else {
requestAttributesHolder.set(attributes);
inheritableRequestAttributesHolder.remove();
}
}
}
复制代码
可以看到 NamedInheritableThreadLocal 重写了 getMap 方法
ThreadLocalMap getMap(Thread t) {
return t.inheritableThreadLocals;
}
复制代码
技术前沿拓展
前端开发,你的认知不能仅局限于技术内,需要发散思维了解技术圈的前沿知识。细心的人会发现,开发内部工具的过程中,大量的页面、场景、组件等在不断重复,这种重复造轮子的工作,浪费工程师的大量时间。
介绍一款程序员都应该知道的软件JNPF快速开发平台,很多人都尝试用过它,它是功能的集大成者,任何信息化系统都可以基于它开发出来。
这是一个基于 Java Boot/.Net Core 构建的简单、跨平台快速开发框架。前后端封装了上千个常用类,方便扩展;集成了代码生成器,支持前后端业务代码生成,实现快速开发,提升工作效率;框架集成了表单、报表、图表、大屏等各种常用的 Demo 方便直接使用;后端框架支持 Vue2、Vue3。如果你有闲暇时间,可以做个知识拓展。
看完本文如果觉得有用,记得点个赞支持,收藏起来说不定哪天就用上啦~
评论