java Spring-Boot Jersey:允许 Jersey 提供静态内容

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/29658240/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-02 15:41:14  来源:igfitidea点击:

Spring-Boot Jersey: allow Jersey to serve static content

javamavenspring-bootjersey-2.0

提问by Rolf

The application uses JDK 8, Spring Boot & Spring Boot Jersey starter and is packaged as a WAR (although it is locally run via Spring Boot Maven plugin).

该应用程序使用 JDK 8、Spring Boot 和 Spring Boot Jersey 启动器并打包为 WAR(尽管它通过 Spring Boot Maven 插件在本地运行)。

What I would like to do is to get the documentation I generate on the fly (at build time) as a welcome page.

我想要做的是将我即时生成的文档(在构建时)作为欢迎页面。

I tried several approaches:

我尝试了几种方法:

  1. letting Jersey serving the static contents by configuring in application.propertiesthe proper init parameteras described here
  2. introduce a metadata-complete=falseweb.xmlin order to list the generated HTML document as a welcome-file.
  1. 让泽西通过配置在服务内容静application.properties正确初始化参数描述这里
  2. 引入 ametadata-complete=falseweb.xml以将生成的 HTML 文档列为欢迎文件。

None of that worked out.

这些都没有奏效。

I would like to avoid having to enable Spring MVC or creating a Jersey resource just for serving a static file.

我想避免启用 Spring MVC 或仅为提供静态文件而创建 Jersey 资源。

Any idea?

任何的想法?

Here is the Jersey configuration class (I unsuccessfully tried to add a ServletProperties.FILTER_STATIC_CONTENT_REGEXthere):

这是 Jersey 配置类(我尝试在ServletProperties.FILTER_STATIC_CONTENT_REGEX那里添加一个没有成功):

@ApplicationPath("/")
@ExposedApplication
@Component
public class ResourceConfiguration extends ResourceConfig {

   public ResourceConfiguration() {
      packages("xxx.api");
      packages("xxx.config");
      property(ServerProperties.BV_DISABLE_VALIDATE_ON_EXECUTABLE_OVERRIDE_CHECK, true);
      property(ServerProperties.BV_SEND_ERROR_IN_RESPONSE, true);
   }
}

And here is Spring Boot application class (I tried adding an application.propertieswith spring.jersey.init.jersey.config.servlet.filter.staticContentRegex=/.*htmlbut it didn't work, I'm not exactly sure what the property key should be here):

这是 Spring Boot 应用程序类(我尝试添加一个application.propertieswithspring.jersey.init.jersey.config.servlet.filter.staticContentRegex=/.*html但它没有用,我不确定这里的属性键应该是什么):

@SpringBootApplication
@ComponentScan
@Import(DataConfiguration.class)
public class Application extends SpringBootServletInitializer {

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(Application.class);
    }

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }
}

回答by Paul Samsotha

Let me just first state, that the reason the static content won't be served is because of the default servlet mapping of the Jersey servlet, which is /*, and hogs up all the requests. So the default servlet that serves the static content can't be reached. Beside the below solution, the other solution is to simply change the servlet mapping. You can do that by either annotating your ResourceConfigsubclass with @ApplicationPath("/another-mapping")or set the application.propertiesproperty spring.jersey.applicationPath.

首先让我声明,无法提供静态内容的原因是 Jersey servlet 的默认 servlet 映射,即/*,并占用所有请求。因此无法访问提供静态内容的默认 servlet。除了下面的解决方案,另一个解决方案是简单地更改 servlet 映射。您可以通过ResourceConfig使用@ApplicationPath("/another-mapping")或设置application.properties属性来注释子类来做到这一点spring.jersey.applicationPath



In regards to your first approach, take a look at the Jersey ServletProperties. The property you are trying to configure is FILTER_STATIC_CONTENT_REGEX. It states:

关于您的第一种方法,请查看 Jersey ServletProperties。您尝试配置的属性是FILTER_STATIC_CONTENT_REGEX. 它指出:

The property is only applicable when Jersey servlet container is configured to run as a Filter, otherwise this property will be ignored

该属性仅在 Jersey servlet 容器配置为作为过滤器运行时适用,否则该属性将被忽略

Spring Boot by default configures the Jersey servlet container as a Servlet (as mentioned here):

春天开机默认配置了泽西servlet容器为一个Servlet(如提到这里):

By default Jersey will be set up as a Servlet in a @Beanof type ServletRegistrationBeannamed jerseyServletRegistration. You can disable or override that bean by creating one of your own with the same name. You can also use a Filter instead of a Servlet by setting spring.jersey.type=filter(in which case the @Beanto replace or override is jerseyFilterRegistration).

默认情况下,新泽西州将被设置为在一个Servlet@Bean类型的ServletRegistrationBean命名jerseyServletRegistration。您可以通过创建自己的同名 bean 来禁用或覆盖该 bean。您还可以通过设置使用过滤器而不是 Servletspring.jersey.type=filter(在这种情况下,@Bean要替换或覆盖的是jerseyFilterRegistration)。

So just set the property spring.jersey.type=filterin your application.properties, and it should work. I've tested this.

所以只需spring.jersey.type=filter在您的 中设置属性application.properties,它应该可以工作。我已经测试过了。

And FYI, whether configured as Servlet Filter or a Servlet, as far as Jersey is concerned, the functionality is the same.

而且仅供参考,无论是配置为Servlet Filter还是Servlet,就Jersey而言,功能都是一样的。

As an aside, rather then using the FILTER_STATIC_CONTENT_REGEX, where you need to set up some complex regex to handle all static files, you can use the FILTER_FORWARD_ON_404. This is actually what I used to test. I just set it up in my ResourceConfig

顺便说一句,FILTER_STATIC_CONTENT_REGEX您需要设置一些复杂的正则表达式来处理所有静态文件,而不是使用FILTER_FORWARD_ON_404. 这实际上是我用来测试的。我只是在我的ResourceConfig

@Component
public class JerseyConfig extends ResourceConfig {

    public JerseyConfig() {
        packages("...");
        property(ServletProperties.FILTER_FORWARD_ON_404, true);
    }
}

回答by mnd

For anyone who still can't get this to work, I followed the answer provided by @peeskillet, and had to make an additional change.

对于仍然无法使其正常工作的任何人,我遵循了@peeskillet 提供的答案,并且必须进行额外的更改。

Previously I had created the following method in Application.java.

以前我在Application.java.

@Bean
public ServletRegistrationBean jerseyServlet() {
    ServletRegistrationBean registration = new ServletRegistrationBean(new ServletContainer(), "/*");
    registration.addInitParameter(ServletProperties.JAXRS_APPLICATION_CLASS, JerseyConfig.class.getName());
    return registration;
}

The problem is that this registered the servlet for the /*path, and then setup the Jersey ResourceConfigconfiguration file.

问题是这为/*路径注册了 servlet ,然后设置 JerseyResourceConfig配置文件。

Once I removed the above method, and placed the @Configurationannotation on my ResourceConfigclass, I noticed the static resource could be retrieved via Spring Boot.

一旦我删除了上述方法,并将@Configuration注解放在我的ResourceConfig类上,我注意到可以通过 Spring Boot 检索静态资源。

For completeness, this is a snippet of my ResourceConfignow.

为了完整起见,这是我ResourceConfig现在的一个片段。

@Configuration
public class JerseyConfig extends ResourceConfig {
    public JerseyConfig() {
        // Application specific settings
        property(ServletProperties.FILTER_FORWARD_ON_404, true);
    }
}

This blog postwas helpful in determining the difference approach for the ResourceConfig.

这篇博文有助于确定ResourceConfig.

回答by Niraj Sonawane

Below setup worked for me

以下设置对我有用

Set

spring .jersey.type: filter

setFILTER_FORWARD_ON_404

设置FILTER_FORWARD_ON_404

@Configuration 
        public class MyResourceConfig extends ResourceConfig  {

            public MyResourceConfig () {
                try {
                    register(XXX.class);
                    property(ServletProperties.FILTER_FORWARD_ON_404, true);

                } catch (Exception e) {
                    LOGGER.error("Exception: ", e);                   
                }
            }       

        } 

Note: Use @Configurationinstead of @component

注意:使用@Configuration而不是@component