3

我正在尝试使用Resteasy Docs中描述的嵌入式 Netty 实例测试带有 Resteasy 的资源。

注入路径参数和查询参数就像一个魅力,但后来我尝试测试注入HttpServletRequestHttpServletResponse来自上下文的资源,如下所示:

@GET
@Path("/")
public void example(@Context HttpServletResponse response, 
                    @Context HttpServletRequest request) { ... }

Resteasy 在上下文中找不到HttpServletRequest并抛出以下异常:

5105 [r #1] DEB o.j.resteasy.core.SynchronousDispatcher  - PathInfo: /auth
5201 [r #1] ERR c.s.f.v.s.r.e.ApplicationExceptionMapper - Unhandled application exception: Unable to find contextual data of type: javax.servlet.http.HttpServletRequest
org.jboss.resteasy.spi.LoggableFailure: Unable to find contextual data of type: javax.servlet.http.HttpServletRequest

我尝试按照RESTEasy Mock vs. Exception Mapper vs. Context中的建议将请求和响应的模拟版本放在上下文中,但它也不起作用,因为上下文数据是 ThreadLocal 并且 Netty 为每个请求生成一个新线程。

关于如何解决这个问题的任何想法?

4

2 回答 2

0

在我的案例中起作用的是注入 org.jboss.seam.mock.HttpServletRequest,因为我在我的应用程序中使用了 seam。您应该尝试一些模拟框架,例如 spring.test 或 mockito。

这是我的代码的样子:

import org.jboss.resteasy.core.Dispatcher;
import org.jboss.resteasy.mock.MockDispatcherFactory;
import org.jboss.resteasy.mock.MockHttpRequest;
import org.jboss.resteasy.mock.MockHttpResponse;
import org.jboss.resteasy.plugins.server.resourcefactory.POJOResourceFactory;
import org.jboss.resteasy.spi.ResteasyProviderFactory;
import org.jboss.seam.mock.MockHttpServletRequest;
import org.jboss.seam.mock.DBUnitSeamTest;

public class Test extends DBUnitSeamTest{   

    @Test
    public void test() throws Exception {

        Dispatcher dispatcher = MockDispatcherFactory.createDispatcher();

        POJOResourceFactory noDefaults = new POJOResourceFactory(ClasstoBeTested.class);        dispatcher.getRegistry().addResourceFactory(noDefaults);
        MockHttpRequest request = MockHttpRequest.get("/serviceToBeTested/1961");
        MockHttpResponse response = new MockHttpResponse();

        HttpServletRequest servletRequest = new MockHttpServletRequest(getSession());
        ResteasyProviderFactory.getContextDataMap().put(HttpServletRequest.class, servletRequest);

        dispatcher.invoke(request, response);

        Assert.assertEquals(HttpServletResponse.SC_OK, response.getStatus());
        Assert.assertTrue(response.getContentAsString().contains("1961")); 

    }
}
于 2015-06-18T15:29:41.213 回答
0

我刚刚在另一个项目上再次受到打击,并决定再次调查。

问题是在使用 Netty 的模拟请求中,没有HttpServletRequest可用的。如果您查看NettyJaxrsServer相关类的来源,Reasteasy 使用自己的抽象来处理未实现的 http 请求HttpServletRequest

如果我更改我的实现以使用这些抽象,我可以访问我的资源中的请求和响应。

import org.jboss.resteasy.spi.HttpRequest;
import org.jboss.resteasy.spi.HttpResponse;

@GET
@Path("/")
public void example(@Context HttpResponse response, 
                    @Context HttpRequest request) { ... }

这并不完美,因为它使我的资源依赖于 Resteasy 接口,但我决定暂时使用它来支持多部分数据的模拟测试。

于 2016-12-11T18:01:23.173 回答