我们有像
这样的单件控制器@Controller
class C {
@Autowire MyObject obj;
public void doGet() {
// do something with obj
}
}
MyObject是在过滤器/拦截器中创建的,并放入HttpServletRequest属性中。然后它在@Configuration:
中获得@Configuration
class Config {
@Autowire
@Bean @Scope("request")
MyObject provideMyObject(HttpServletRequest req) {
return req.getAttribute("myObj");
}
}
一切都在主代码中运行良好,但在测试中却没有:当我从集成测试中运行它时:
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("/web-application-config_test.xml")
class MyTest {
@Autowired
C controller;
@Test
void test() {
// Here I can easily create "new MockHttpServletRequest()"
// and set MyObject to it, but how to make Spring know about it?
c.doGet();
}
}
它抱怨NoSuchBeanDefinitionException: No matching bean of type [javax.servlet.http.HttpServletRequest]
。 (首先,它抱怨请求范围不活跃,但我使用CustomScopeConfigurer和SimpleThreadScope解决了它,如建议here)。
如何让Spring注入了解我的MockHttpServletRequest?或直接MyObject?
答案 0 :(得分:1)
临时工作,但它看起来是正确的方法:在Config中,而不是req.getAttribute("myObj")
,写
RequestAttributes requestAttributes = RequestContextHolder.currentRequestAttributes();
return (MyObject) requestAttributes.getAttribute("myObj", RequestAttributes.SCOPE_REQUEST);
因此它不再需要HttpServletRequest实例。并填写测试:
MockHttpServletRequest request = new MockHttpServletRequest();
request.setAttribute("myObj", /* set up MyObject instance */)
RequestContextHolder.setRequestAttributes(new ServletWebRequest(request));