java – 在过滤器中修改Jersey InputStream.无法弄清楚如何在Jersey资源中访问修改后的inputStream

正如 How to use Jersey interceptors to get request body

中所讨论的,我正在修改ContainerRequestFilter中的EntityInputStream.

public filter(ContainerRequest request){
     ByteArrayOutputStream out = new ByteArrayOutputStream();
     InputStream in = request.getEntityInputStream(); 
     try{
           Readerwriter.writeTo(in, out);
           byte[] requestEntity = out.toByteArray();

           // DO SOMETHING WITH BYTES HERE

           request.setEntityInputStream(new ByteArrayInputStream(requestEntity));

      }/// error handling code here  
}

但是,后来我无法弄清楚如何访问修改后的InputStream.我可以在资源中获取ServletContext,但我无法弄清楚如何获取我在过滤器中实际修改的对象ContainerRequest.

我可以这样做吗?当我尝试这个时,泽西岛无法启动:

@Post
@Path("/test")
public Response test(@Context ContainerRequest cr){
     // blah blah
     return....
}

泽西岛错误:

方法public javax.ws.rs.core.Response example.TestController.test(com.sun.jersey.spi.container.ContainerRequest)缺少依赖性,用资源的POST注释,类example.TestController,不被识别为有效资源方法.

我被困在一个旧版本的球衣,1.8,所以我不确定这是否是问题的一部分.

您需要做的就是接受一个I​​nputStream作为资源方法中的实体主体.如果你想要ByteArrayInputStream只是强制转换它.

@POST
public Response post(InputStream in) {
    ByteArrayInputStream bin = (ByteArrayInputStream)in;
}

如果你还不知道,Jersey如何将请求流(对于请求体)转换为Java类型(例如JSON到POJO)的时间
MessageBodyReader

s.您可以在 JAX-RS Entity Providers
阅读更多相关信息.

Jersey已经附带了一些易于转换类型的标准阅读器,例如String.大多数内容类型都可以转换为String.同样,它有一个处理InputStream的阅读器.这可能是最简单的转换,因为请求已经作为InputStream进入,所以读者真正需要做的就是返回原始流,这就是传递给我们方法的内容.

如果我们查看实现
InputStreamProvider

,我们可以看到实际发生的情况. 0700 3.由于过滤器发生在读者之前,读者只需返回我们设置的流.

这是一个使用 Jersey Test Framework
的完整示例

public class StreamFilterTest extends JerseyTest {

    public static class InputStreamFilter implements ContainerRequestFilter {

        @Override
        public ContainerRequest filter(ContainerRequest request) {
            try {
                ByteArrayOutputStream out = new ByteArrayOutputStream();
                InputStream in = request.getEntityInputStream();
                ReaderWriter.writeTo(in, out);

                byte[] requestBytes = out.toByteArray();
                byte[] worldBytes = " World".getBytes(StandardCharsets.UTF_8);
                byte[] newBytes = new byte[requestBytes.length + worldBytes.length];
                System.arraycopy(requestBytes, 0, newBytes, 0, requestBytes.length);
                System.arraycopy(worldBytes, 0, newBytes, requestBytes.length, worldBytes.length);

                request.setEntityInputStream(new ByteArrayInputStream(newBytes));
            } catch (IOException ex) {
                Logger.getLogger(InputStreamFilter.class.getName()).log(Level.SEVERE, null, ex);
                throw new RuntimeException(ex);
            }

            return request;
        }
    }

    @Path("stream")
    public static class StreamResource {

        @POST
        public String post(InputStream in) throws Exception {
            ByteArrayInputStream bin = (ByteArrayInputStream) in;
            StringWriter writer = new StringWriter();
            ReaderWriter.writeTo(new InputStreamReader(bin), writer);
            return writer.toString();
        }
    }

    public static class AppConfig extends DefaultResourceConfig {
        public AppConfig() {
            super(StreamResource.class);
            getContainerRequestFilters().add(new InputStreamFilter());
        }
    }

    @Override
    public WebAppDescriptor configure() {
        return new WebAppDescriptor.Builder()
                .initParam(WebComponent.RESOURCE_CONFIG_CLASS,
                        AppConfig.class.getName())
                .build();
    }

    @Test
    public void should_return_hello_world() {
        String response = resource().path("stream").post(String.class, "Hello");
        assertEquals("Hello World", response);
    }
}

这是测试依赖

<dependency>
    <groupId>com.sun.jersey.jersey-test-framework</groupId>
    <artifactId>jersey-test-framework-grizzly2</artifactId>
    <version>1.17.1</version>
    <scope>test</scope>
</dependency>

翻译自:https://stackoverflow.com/questions/32632342/jersey-inputstream-is-modified-in-filter-unable-to-figure-out-how-to-access-mod

原文 

https://codeday.me/bug/20190111/503967.html

本站部分文章源于互联网,本着传播知识、有益学习和研究的目的进行的转载,为网友免费提供。如有著作权人或出版方提出异议,本站将立即删除。如果您对文章转载有任何疑问请告之我们,以便我们及时纠正。

PS:推荐一个微信公众号: askHarries 或者qq群:474807195,里面会分享一些资深架构师录制的视频录像:有Spring,MyBatis,Netty源码分析,高并发、高性能、分布式、微服务架构的原理,JVM性能优化这些成为架构师必备的知识体系。还能领取免费的学习资源,目前受益良多

转载请注明原文出处:Harries Blog™ » java – 在过滤器中修改Jersey InputStream.无法弄清楚如何在Jersey资源中访问修改后的inputStream

赞 (0)
分享到:更多 ()

评论 0

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址