您的位置:首页 > 编程语言 > Java开发

在SpringMVC Controller中注入Request成员域

2017-11-03 11:17 357 查看

主题

  在工作中遇到1个问题....我们定义了一个Controller基类,所有Springmvc自定义的controller都继承它....在它内部定义一个@Autowired HttpServletRequest request;可不可以? 能不能从这个对象里取requestParamters和attributes? 多线程之间会不会影响?

思考

初次思考,我想这应该是不行的.为什么呢?

注入bean是在spring容器启动的时候...request的实现类是在tomcat里(我使用的servlet容器是tomcat)....我又没在spring的容器里配置这个bean.注入应该是失败的...

退一步说,就算是成功了....那注入的也就是1个对象而已.每次servlet接受到请求都会重新生成1个request...这明显和之前启动的那个对象不同吧....怎么想都不可能成功...

如果确实是这样的....那就没有这篇文章了....后来实践了一下..发现这个注入是可以的.使用起来取数据也没任何问题....

其实我那个时候debug看了一下,基本就知道为什么可以取到数据了..但是我并不知道原理和Spring(Springmvc)的处理流程...所以现在研究了一下并记录下来...

原理

首先给大家看一下在方法中注入request作为参数和在成员域中注入request的 注入的request对象之间的区别....

1     private void initContextHolders(
2             HttpServletRequest request, LocaleContext localeContext, RequestAttributes requestAttributes) {
3
4         if (localeContext != null) {
5             LocaleContextHolder.setLocaleContext(localeContext, this.threadContextInheritable);
6         }
7         if (requestAttributes != null) {
8             RequestContextHolder.setRequestAttributes(requestAttributes, this.threadContextInheritable);
9         }
10         if (logger.isTraceEnabled()) {
11             logger.trace("Bound request context to thread: " + request);
12         }
13     }


View Code
就是在这里设置到RequestContextHolder的threadlocal中去的...

小结

1.在controller中注入的request是jdk动态代理对象,ObjectFactoryDelegatingInvocationHandler的实例.当我们调用成员域request的方法的时候其实是调用了objectFactory的getObject()对象的相关方法.这里的objectFactory是RequestObjectFactory.

2.RequestObjectFactory的getObject其实是从RequestContextHolder的threadlocal中去取值的.

3.请求刚进入springmvc的dispatcherServlet的时候会把request相关对象设置到RequestContextHolder的threadlocal中去.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: