【问题标题】:ContainerResponseFilter not executedContainerResponseFilter 未执行
【发布时间】:2015-03-16 16:05:09
【问题描述】:

我想用 Jax-Rs 构建一个启用 cors 的 REST-API。所以我用谷歌搜索了怎么做,发现了这个:

http://www.developerscrappad.com/1781/java/java-ee/rest-jax-rs/java-ee-7-jax-rs-2-0-cors-on-rest-how-to-make-rest-apis-accessible-from-a-different-domain/

解决方案是一个ResponseFilter,它在每个响应中添加一些头部信息,以便用户的浏览器知道,允许跨域访问。

因为当我执行任何请求(尝试 GET、POST 和 OPTIONS)时 ResponseFilter 没有被执行,我再次谷歌搜索并发现:

ContainerResponseFilter not working

@lefloh 给出了一个很好的答案,这听起来很合乎逻辑(删除注释@PreMatching)。它这样做了,但是当我执行 Http-Request 时,我的过滤器没有被调用。

这是我的代码:

import javax.ws.rs.container.ContainerRequestContext;
import javax.ws.rs.container.ContainerResponseContext;
import javax.ws.rs.container.ContainerResponseFilter;
import javax.ws.rs.ext.Provider;
import java.io.IOException;

@Provider
public class RESTServiceResponseFilter implements ContainerResponseFilter {

    @Override
    public void filter(ContainerRequestContext parContainerRequestContext, ContainerResponseContext parContainerResponseContext) throws IOException {
        parContainerResponseContext.getHeaders().add( "Access-Control-Allow-Origin", "*" );
        parContainerResponseContext.getHeaders().add( "Access-Control-Allow-Credentials", "true" );
        parContainerResponseContext.getHeaders().add( "Access-Control-Allow-Methods", "GET, POST, DELETE, PUT" );
        parContainerResponseContext.getHeaders().add( "Access-Control-Allow-Headers", "Content-Type" );
    }
}

我一直在谷歌搜索,发现我忘记将过滤器添加到 web.xml。所以我也这样做了:

<servlet>
    <display-name>webinterface.api</display-name>
    <servlet-name>JAX-RS REST Servlet</servlet-name>
    <servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class>
    <init-param>
        <param-name>com.sun.jersey.config.property.packages</param-name>
        <param-value>de.tsystems.lbus.apprestserver</param-value>
    </init-param>
    <init-param>
        <param-name>com.sun.jersey.spi.container.ContainerResponseFilters</param-name>
        <param-value>de.apprestserver.filter.RESTServiceResponseFilter</param-value>
    </init-param>
    <load-on-startup>1</load-on-startup>
</servlet>

<servlet-mapping>
    <servlet-name>JAX-RS REST Servlet</servlet-name>
    <url-pattern>/TNR/*</url-pattern>
</servlet-mapping>

我现在没有更多的想法,想问你,如果你对我有解决方案。提前致谢!

【问题讨论】:

    标签: java rest jersey jax-rs


    【解决方案1】:

    您正在使用 Jersey 1(可以通过 web.xml 中的 com.sun.jersey 来判断)。您正在使用(或向我们展示)的过滤器实现是 Jersey 2。有细微的区别,但这是一个主要区别。后者不适用于 Jersey 1。

    它甚至可以编译的事实(如果是这样的话)意味着您需要摆脱一些依赖关系。您拥有的类是 JAX-RS 2 类(接口)。您可能拥有的任何 JAX-RS/Jersey 2 依赖项都摆脱了它们。他们打得不好(也许不是问题的原因,但摆脱他们以消除任何混乱)

    • 球衣 1 == com.sun.jersey(保留)
    • 球衣 2 == org.glassfish.jersey(摆脱)
    • JAX-RS 2 api == javax.ws.rs-api(去掉)

    见here for Jersey 1 implementation and configuration

    【讨论】:

    • 我现在尝试为 Jersey 1 编写我的 ResponseFilter,就像你给我的链接一样。它仍然没有执行。现在我想以相反的方式执行此操作,以删除所有 Jersey 1 依赖项。但是我遇到了 1 个问题:当我使用 com.sum.jersey 删除所有旧依赖项时,Servlet 类 ( com.sun.jersey.spi.container.servlet.ServletContainer) 现在是什么?我在互联网上只发现了 JAX-RS2 api,只有两者混合。我觉得我走错了路,但我想了解失败。是的,除了过滤器之外,所有东西都可以编译和工作。
    • 你在使用 Maven 吗?或者至少知道如何使用它?
    • 如果是这样,请使用 mvn command 从原型创建项目,或者仅使用 Maven 坐标从 IDE 启动项目。无论哪种方式,您都将获得一个使用 JAX-RS 2 的新 Jersey webapp。如果您刚刚开始,您不妨从 JAX-RS 2 开始,因为它具有更多功能。有了这个项目,你就可以使用你在代码中提供的类,不需要额外的配置
    • 另见 here for deployment options 泽西 2
    • @peesk illet 的编辑:对不起,我不明白了,为什么要摆脱 javax.ws.rs-api?我使用 @GET、@PATH 之类的注释!你能举一个例子或教程我必须如何做到这一点?我现在尝试了几次,我从来没有遇到过异常,总是只有 404 错误或什么都没有。因此,Jax-RS 是构建 rest-api 的一个很好且干净的选择,还是我应该选择不同的东西?
    猜你喜欢
    • 2018-02-23
    • 2013-09-21
    • 1970-01-01
    • 2016-01-05
    • 1970-01-01
    • 2014-07-03
    • 1970-01-01
    • 1970-01-01
    • 2021-02-14
    相关资源
    最近更新 更多