Spring:如何将HttpServletRequest注入到请求范围的bean中?


95

我正在尝试在Spring中建立一个请求范围的bean

我已经成功设置好了,因此每个请求创建一次bean。现在,它需要访问HttpServletRequest对象。

由于该bean是每个请求创建一次的,所以我认为容器可以轻松地将请求对象注入到我的bean中。我怎样才能做到这一点 ?

Answers:


114

可以将请求范围的bean与请求对象自动连接。

private @Autowired HttpServletRequest request;

2
是否有一种老式的XML方式?
cherouvim 2010年

2
对我不起作用(Spring MVC 3.1)-也许还有更多需要做的事情吗?使用Samit的解决方案。
kldavis4

2
问题是,当您使用MockMvc测试验证器时,这种注入会出现问题。在这种情况下,可能会首选其他解决方案
Neyko

21
也可以将HttpServletRequest自动装配到非请求范围的Bean中,因为对于HttpServletRequest,Spring会生成一个代理HttpServletRequest,该代理知道如何获取请求的实际实例。因此,即使控制器是单例作用域,也可以自动连线请求。
vtor 2015年

3
对于Spring <= 3.1用户警告,自动装配将无法运行测试。
鲁本斯·马里努佐

138

Spring 通过type 的包装对象公开当前HttpServletRequest对象(以及当前HttpSession对象)。此包装器对象绑定到ThreadLocal,可以通过调用方法获得。ServletRequestAttributesstaticRequestContextHolder.currentRequestAttributes()

ServletRequestAttributes提供getRequest()获取当前请求,getSession()获取当前会话的方法以及获取存储在两个范围中的属性的其他方法。以下代码虽然有点难看,但应该可以在应用程序中的任何位置为您提供当前的请求对象:

HttpServletRequest curRequest = 
((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes())
.getRequest();

请注意,该RequestContextHolder.currentRequestAttributes()方法返回一个接口,并且需要进行类型转换以ServletRequestAttributes实现该接口。


春季Javadoc: RequestContextHolder | ServletRequestAttributes


8
注入是好的解决方案,但是我发现MockMvc测试注入HttpServletRequest的Spring验证程序存在问题。因此,如果您想同时运行模拟测试和生产代码,则应该选择该选项。
Neyko 2013年

@Neyko为什么?对于模拟测试(单元测试?),您可以注入模拟HttpServletRequest或任何您想要的..不是吗?或者我可以使用MockHttpServletRequest?
winhee

在单例作用域服务实例中使用安全吗?
晋权

2

如此处建议的那样您还可以将HttpServletRequestas作为方法参数注入,例如:

public MyResponseObject myApiMethod(HttpServletRequest request, ...) {
    ...
}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.