之前想要拿到当前线程中的请求,直接在工具类中放了个ThreadLocal作为容器,当时候的需求只需要拿到request即可,所以那个方式是可以的。

关于ThreadLocal相关知识,可以参考我的这篇博文——>https://zhanglong.blog.csdn.net/article/details/120698432

但现在不一样了,我们在做的这个系统中需要更多的东西,比如会把用户对象放到session中,在判断是否为当前用户这种情况下就比较常用,那之前的代码就不太适合了,因为作为容器的ThreadLocal中只能将request作为参数set进去,session是进不去的。

一种解决方案是修改工具类中的容器,改用RequestContextHolder中的ServletRequestAttributes来存放「用于存放用户信息的session」。

改进后的代码:

    public static HttpSession getSession(){ServletRequestAttributes ra = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();HttpServletRequest request = ra.getRequest();HttpSession session = request.getSession();return session;}

1. RequestContextHolder类

文档描述:

Holder class to expose the web request in the form of a thread-bound RequestAttributes object.,简单翻译下,这个类的作用是通过操作RequestAttributes请求属性这个对象(绑定了线程)来间接处理请求相关的一些东西。
所以你可以看到代码中首先拿到了RequestAttributes对象,当然这里要转成Servlet类型。


2. ServletRequestAttributes类

如果不转型,那个attributes类是无法方便操作request、session这些原生servlet相关的对象或者属性的,因为本身Java Web最原始的实现就是servlet形式的,Spring框架当然会为其做特定的一些封装,也就是这个类的来源。

代码中首先通过属性拿到了HttpServletRequest对象,然后通过请求对象拿到session。
这里有个小问题,那就是既然里面已经有一个getSession(boolean allowCreate)方法了,那为啥不直接获取session对象呢?

我简单回去看了下源码,这个方法上带了一个布尔类型的参数,含义是是否允许创建session,在方法逻辑内部也调用了这个方法,然后也会发现在对于attribute的操作方法,如setAttribute+removeAttribute+getAttributeNames+updateAccessedSessionAttributes中都调用了getSession,然后根据不同的逻辑传入true或者false,也就是说,这个getSessioin本身不是为我们所写,它的存在是为了完善这一套的逻辑,建立起请求、回话、属性之间的前后逻辑。所以我们不直接调用它,因为你不知道该传true还是false。


3. NamedThreadLocal

最后一个关键点就是,RequestContextHolder如何绑定线程,说白了,它也是组合了ThreadLocal,在setAttribute中本质上也是把value放到ThreadLocalMap中,相关源码如下:

private static final ThreadLocal<RequestAttributes> requestAttributesHolder =new NamedThreadLocal<RequestAttributes>("Request attributes");
public void set(T value) {Thread t = Thread.currentThread();ThreadLocalMap map = getMap(t);if (map != null)map.set(this, value);elsecreateMap(t, value);}

复制代码当然在逻辑上,它会判断参数是否为空、是否为可继承的等等等等。


4. 小结

因此你也看到了,出现新的需求都是找得到解决方案的,顺便看了下源码,加深了一些印象跟理解。这时候可能过程比结果重要。

ServletRequestAttributes用法详解——Spring系列学习笔记相关推荐

  1. spring RestTemplate用法详解

    spring RestTemplate用法详解 spring 3.2.3 框架参考有说明 21.9 Accessing RESTful services on the Client 转载于:https ...

  2. Ext.Net学习笔记22:Ext.Net Tree 用法详解

    上面的图片是一个简单的树,使用Ext.Net来创建这样的树结构非常简单,代码如下: <ext:TreePanel runat="server"><Root> ...

  3. spring boot模板引擎thymleaf用法详解

    spring boot模板引擎thymleaf用法详解 Spring-boot支持FreeMarker.Thymeleaf.jsp.veocity 但是对freemarker和thymeleaf的支持 ...

  4. linux getline函数用法,Linux文本处理三剑客之awk学习笔记05:getline用法详解

    getline用法详解 在默认情况下,awk支持从文件或者STDIN中读取数据.我们也可以使用getline来灵活读取数据,例如在main代码块执行过程中读取某个非待处理文件的数据,或者从某个读取某个 ...

  5. 《算法笔记》学习日记——6.1 vector的常见用法详解

    目录 6.1 vector的常见用法详解 问题 A: Course List for Student (25) 问题 B: Student List for Course (25) 小结 6.1 ve ...

  6. Python中self用法详解

    Python中self用法详解 https://blog.csdn.net/CLHugh/article/details/75000104 首页 博客 学院 下载 图文课 论坛 APP 问答 商城 V ...

  7. java配置文件实现方式_java相关:详解Spring加载Properties配置文件的四种方式

    java相关:详解Spring加载Properties配置文件的四种方式 发布于 2020-4-29| 复制链接 摘记: 一.通过 context:property-placeholder 标签实现配 ...

  8. php theme_path,PHP_Yii2主题(Theme)用法详解,本文实例讲述了Yii2主题(Theme) - phpStudy

    Yii2主题(Theme)用法详解 本文实例讲述了Yii2主题(Theme)用法.分享给大家供大家参考,具体如下: 首先看看主要的配置方式: 'components' => [ 'view' = ...

  9. PowerShell攻防进阶篇:nishang工具用法详解

    PowerShell攻防进阶篇:nishang工具用法详解 导语:nishang,PowerShell下并肩Empire,Powersploit的神器. 开始之前,先放出个下载地址! 下载地址:htt ...

最新文章

  1. C中常用字符串处理函数
  2. 用递归合并两个排序的链表
  3. jquery让页面滚动到底部
  4. Loj#6039-「雅礼集训 2017 Day5」珠宝【四边形不等式,dp】
  5. python怎么换行继续写脚本_python怎么换行继续写脚本
  6. CGI与JSP联系与区别
  7. Java 实验五 王奕开
  8. Affymetrix基因芯片小总结
  9. js获取引用的css样式,js获取css样式方法
  10. secoclient免积分下载
  11. OpenCASCADE VS2010 SP1编译
  12. unity 画球面_Unity实现球面行走
  13. 写好一份数据分析报告需要注意的13个要点
  14. 2012, PPSN,Geometric Semantic Genetic Programming,GSGP
  15. cocos恭喜喜庆粒子特效
  16. win10桌面文件丢失的处理总结
  17. 【工具-AWVS】AWVS安装与使用
  18. 学习笔记:C++进阶【继承、多态、二叉树进阶、map和set、哈希、C++11、异常、智能指针、特殊类设计、C++的类型转换】
  19. 思维导图的分类 利用思维导图绘制学习知识方法介绍
  20. 【Java基础】Java入门(一)

热门文章

  1. 2_4 FacadeMode.cpp 外观模式
  2. Kafka分区分配策略(4)——分配的实施
  3. 通过 Go 语言来实现 DDD 分层设计,美滋滋!
  4. 改来改去把微服务改成了分布式单体
  5. shell之常用工具的使用
  6. 关于如何升级gcc版本及相关的标准库问题
  7. 没有他,就没有我们现在的WebRTC
  8. 【主题演讲】探讨视频行业与技术的更多挑战与机会
  9. 「递归」第5集 | 从网瘾少年到极客大神:没有什么是一段代码解决不了的
  10. AI繁荣下的隐忧——Google Tensorflow安全风险剖析