如何在 Spring Boot 中获取静态资源(js、css)作为 ClassPathResource?

Posted

技术标签:

【中文标题】如何在 Spring Boot 中获取静态资源(js、css)作为 ClassPathResource?【英文标题】:How to get static resource (js, css) as ClassPathResource in Spring Boot? 【发布时间】:2017-05-27 02:49:56 【问题描述】:

我需要能够从 Spring Boot 模板生成 PDF。为此,我使用了一个 PDF 渲染库(FlyingSaucer),它大部分都能正确完成这项工作。但是,有一个问题:当我在页面上有“href”标签时,当 PDF 渲染器尝试渲染 html 时,它们无法正确解析。例如,如果我有以下代码:

<link rel="stylesheet" type="text/css" th:href="@/css/index.css" />

它在浏览器中正确解析,但是当我尝试使用以下代码将其作为 ClassPath 资源检索时:

new ClassPathResource("/css/index").getInputStream()

Spring Boot 说文件不存在。这对我来说很奇怪,因为我认为 Spring Boot 会将所有静态内容添加到类路径中。

以下是我的项目的文件夹结构,(我认为)遵循正确的 Spring Boot 约定:

我能否像浏览器请求它们时那样处理一些 Spring 资源(通过自动装配、应用程序上下文等)来解析这些 URL?我可以通过将“resources/static/”硬编码到 url 字符串的开头来解决这个问题,但我更喜欢更动态的解决方案。

【问题讨论】:

【参考方案1】:

使用这个:

new ClassPathResource("static/css/index.css").getInputStream();

【讨论】:

有什么方法可以不用硬编码“/static”吗? 在春季,资源的标准类路径是“src/main/resources”。所以你必须在那之后附加完整的路径。显然,您可以利用模式匹配等优势,但最终您还是必须提供它。 看我的回答。我设法通过使用一些 Spring 组件在不提供完整路径的情况下做到了这一点。我认为“src/main/resources/static”也放在类路径上。但是,如果我的理解有误,请告诉我。【参考方案2】:

在尝试了各种解决方案后,我设法想出了一个,尽管 Amant Simgh 给出了答案,但不需要我对任何路径进行硬编码。我在我的解决方案中扔了一堆东西(使用图像,部署到 tomcat 容器,运行“bootRun”,使用 webjars),它似乎在每种情况下都有效。

在内部,Spring Boot 使用 ResourceHttpRequestHandler 类来解析资源。这允许 Spring Boot 应用程序 @Autowire 一个 ResourceHttpRequestHandler bean。因此,为了从 java 代码中获取后端的静态资源,您可以执行以下操作:

@Autowired
ResourceHttpRequestHandler resourceHandler;

String uri = "/css/mycss.css";
Resource resource;
for (ResourceResolver resourceResolver : resourceHandler.getResourceResolvers())

    resource = resourceResolver.resolveResource(null, uri, resourceHandler.getLocations(), null);
    if (resource != null)
        break;

这本质上是 SpringBoot 在请求静态资源时所做的。

重要提示:如果您的应用程序有上下文路径(即,您部署“myapp”应用程序,那么上下文路径将为“/myapp/”),那么您必须从上例中的 URI 中删除上下文路径.幸运的是,这可以通过以下方式轻松完成:

ServletContext context = // get servlet context somehow
String uriWithoutContext = uri.replace(context.getContextPath(), "");

【讨论】:

以上是关于如何在 Spring Boot 中获取静态资源(js、css)作为 ClassPathResource?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Spring Boot 中将 Cache-Control 标头添加到静态资源?

Spring Boot 的静态资源处理

Spring Boot参考教程Spring Boot Jar方式读取资源文件

Spring boot 静态资源无法加载

Spring boot 静态资源无法加载

Spring Boot 读取静态资源文件