【SpringBoot WEB系列】静态资源配置与读取

news/2025/2/25 16:12:56

【WEB系列】静态资源配置与读取

SpringWeb项目除了我们常见的返回json串之外,还可以直接返回静态资源(当然在现如今前后端分离比较普遍的情况下,不太常见了),一些简单的web项目中,前后端可能就一个人包圆了,前端页面,js/css文件也都直接放在Spring项目中,那么你知道这些静态资源文件放哪里么

I. 默认配置

1. 配置

静态资源路径,SpringBoot默认从属性spring.resources.static-locations中获取

默认值可以从org.springframework.boot.autoconfigure.web.ResourceProperties#CLASSPATH_RESOURCE_LOCATIONS获取

private static final String[] CLASSPATH_RESOURCE_LOCATIONS = { "classpath:/META-INF/resources/",
			"classpath:/resources/", "classpath:/static/", "classpath:/public/" };

/**
 * Locations of static resources. Defaults to classpath:[/META-INF/resources/,
 * /resources/, /static/, /public/].
 */
private String[] staticLocations = CLASSPATH_RESOURCE_LOCATIONS;

注意上面的默认值,默认有四个,优先级从高到低

  • /META-INF/resources/
  • /resources/
  • /static/
  • /public/

2. 实例演示

默认静态资源路径有四个,所以我们设计case需要依次访问这四个路径中的静态资源,看是否正常访问到;其次就是需要判定优先级的问题,是否和上面说的一致

首先创建一个SpringBoot web项目,工程创建流程不额外多说,pom中主要确保有下面依赖即可(本文使用版本为: 2.2.1.RELEASE)

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

在资源文件夹resources下,新建四个目录,并添加html文件,用于测试是否可以访问到对应的资源文件(主要关注下图中标红的几个文件)

a. META-INF/resources

静态文件 m.html

<html>
<title>META-INF/resource/m.html</title>
<body>
jar包内,META-INF/resources目录下 m.html
</body>
</html>

完成对应的Rest接口

@GetMapping(path = "m")
public String m() {
    return "m.html";
}

b. resources

静态文件 r.html

<html>
<title>resources/r.html</title>
<body>
jar包内,resouces目录下 r.html
</body>
</html>

对应的Rest接口

@GetMapping(path = "r")
public String r() {
    return "r.html";
}

c. static

静态文件 s.html

<html>
<title>static/s.html</title>
<body>
jar包内,static目录下 s.html
</body>
</html>

对应的Rest接口

@GetMapping(path = "s")
public String s() {
    return "s.html";
}

d. public

静态文件 p.html

<html>
<title>public/p.html</title>
<body>
jar包内,public目录下 p.html
</body>
</html>

对应的Rest接口

@GetMapping(path = "p")
public String p() {
    return "p.html";
}

e. 优先级测试

关于优先级的测试用例,主要思路就是在上面四个不同的文件夹下面放相同文件名的静态资源,然后根据访问时具体的返回来确定相应的优先级。相关代码可以在文末的源码中获取,这里就不赘述了

II. 自定义资源路径

一般来讲,我们的静态资源放在上面的四个默认文件夹下面已经足够,但总会有特殊情况,如果资源文件放在其他的目录下,应该怎么办?

1. 修改配置文件

第一种方式比较简单和实用,修改上面的spring.resources.static-locations配置,添加上自定义的资源目录,如在 application.yml 中,指定配置

spring:
  resources:
    static-locations: classpath:/out/,classpath:/META-INF/resources/,classpath:/resources/,classpath:/static/,classpath:/public/

上面指定了可以扫描/out目录下的静态资源文件,且它的优先级是最高的(上面的配置顺序中,优先级的高低从左到右)

实例演示

在资源目录下,新建文件/out/index.html

请注意在其他的四个资源目录下,也都存在 index.html这个文件(根据上面优先级的描述,返回的应该是/out/index.html

@GetMapping(path = "index")
public String index() {
    return "index.html";
}

2. WebMvcConfigurer 添加资源映射

除了上述的配置指定之外,还有一种常见的使用姿势就是利用配置类WebMvcConfigurer来手动添加资源映射关系,为了简单起见,我们直接让启动类实现WebMvcConfigure接口

@SpringBootApplication
public class Application implements WebMvcConfigurer {
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        // 请注意下面这个映射,将资源路径 /ts 下的资源,映射到根目录为 /ts的访问路径下
        // 如 ts下的ts.html, 对应的访问路径 /ts/ts
        registry.addResourceHandler("/ts/**").addResourceLocations("classpath:/ts/");
    }


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

根据上面的配置表示将/ts目录下的资源ts.html,映射到/ts/ts,而直接访问/ts会报404(这个逻辑可能有点绕,需要仔细想一想)

@GetMapping(path = "ts")
public String ts() {
    return "ts.html";
}

@GetMapping(path = "ts/ts")
public String ts2() {
    return "ts.html";
}

III. Jar包资源访问

前面描述的静态资源访问主要都是当前包内的资源访问,如果我们的静态资源是由第三方的jar包提供(比如大名鼎鼎的Swagger UI),这种时候使用姿势是否有不一样的呢?

1. classpath 与 classpath*

在之前使用SpringMVC3+/4的时候,classpath:/META-INF/resources/表示只扫描当前包内的/META-INF/resources/路径,而classpath*:/META-INF/resources/则会扫描当前+第三方jar包中的/META-INF/resources/路径

那么在SpringBoot2.2.1-RELEASE版本中是否也需要这样做呢?(答案是不需要,且看后面的实例)

2. 实例

新建一个工程,只提供基本的html静态资源,项目基本结构如下(具体的html内容就不粘贴了,墙裂建议有兴趣的小伙伴直接看源码,阅读效果更优雅)

接着在我们上面常见的工程中,添加依赖

<dependency>
    <groupId>com.git.hui.boot</groupId>
    <artifactId>204-web-static-resources-ui</artifactId>
    <version>0.0.1-SNAPSHOT</version>
</dependency>

添加对应资源的访问端点

@GetMapping(path = "ui")
public String ui() {
    return "ui.html";
}

@GetMapping(path = "out")
public String out() {
    return "out.html";
}

// 第三方jar包的 META-INF/resources 优先级也高于当前包的 /static

@GetMapping(path = "s2")
public String s2() {
    return "s2.html";
}

请注意,这个时候我们是没有修改前面的spring.resources.static-locations配置的

上面的访问结果,除了说明访问第三方jar包中的静态资源与当前包的静态资源配置没有什么区别之外,还可以得出一点

  • 相同资源路径下,当前包的资源优先级高于jar包中的静态资源
  • 默认配置下,第三方jar包中META-INF/resources下的静态资源,优先级高于当前包的/resources, /static, /public

IV. 其他

0. 项目

  • 工程:https://github.com/liuyueyi/spring-boot-demo
  • 源码:https://github.com/liuyueyi/spring-boot-demo/spring-boot/204-web-static-resources
  • https://github.com/liuyueyi/spring-boot-demo/spring-boot/204-web-static-resources-ui

1. 一灰灰Blog

尽信书则不如,以上内容,纯属一家之言,因个人能力有限,难免有疏漏和错误之处,如发现bug或者有更好的建议,欢迎批评指正,不吝感激

下面一灰灰的个人博客,记录所有学习和工作中的博文,欢迎大家前去逛逛

  • 一灰灰Blog个人博客 https://blog.hhui.top
  • 一灰灰Blog-Spring专题博客 http://spring.hhui.top

一灰灰blog


http://www.niftyadmin.cn/n/4231359.html

相关文章

XenApp_XenDesktop_7.6实战篇之九:SQL Server数据库服务器规划及部署

安装SQL Server 数据库&#xff0c;用于支持Desktop Studio 和桌面云管理台数据存储和访问。在简单的&#xff30;&#xff2f;&#xff23;测试中&#xff0c;数据库可以只配置单机&#xff1b;但数据库故障时&#xff0c;不但影响配置管理台&#xff0c;也会影响&#xff24;…

Kotlin教程学习-Why Kotlin?

2019独角兽企业重金招聘Python工程师标准>>> Kotlin是一种优雅的语言,是JetBrains公司开发的JVM语言,与Java有着极密切的联系,Kotlin有着怎样的魅力呢?我也是才开始学习Kotlin,打算记录下我学习Kotlin的点点滴滴. 今天是开始的一天,就说说我初见Kotlin时的感受吧. …

【SpringBoot WEB系列】WebFlux静态资源配置与访问

【SpringBoot WEB系列】WebFlux静态资源配置与访问 上一篇博文介绍SpringMVC的静态资源访问&#xff0c;那么在WebFlux中&#xff0c;静态资源的访问姿势是否一致呢 I. 默认配置 与SpringBoot的默认配置一样&#xff0c;WebFlux同样是classpath:/META-INF/resources/,classpat…

elasticsearch-2.1.1集群搭建初探/填坑

elasticsearch2.x发布有一段时间了&#xff0c;抽空把集群搭起来&#xff0c;做点实验-------------------------------------------------------------------------------------正文------------------------------------------------------------------------------------ela…

【SpringBoot WEB 系列】RestTemplate 之自定义请求头

【WEB 系列】RestTemplate 之自定义请求头 上一篇介绍了 RestTemplate 的基本使用姿势&#xff0c;在文末提出了一些扩展的高级使用姿势&#xff0c;本篇将主要集中在如何携带自定义的请求头&#xff0c;如设置 User-Agent&#xff0c;携带 Cookie Get 携带请求头Post 携带请求…

几个著名的Java开源缓存框架

2019独角兽企业重金招聘Python工程师标准>>> 摘要 本文网上转载。最近交流的人比较&#xff0c;三月份互联网公司都是这样&#xff0c;你来我往&#xff0c;我也不例外。交流多了&#xff0c;三人行必有我师&#xff0c;Java缓存框架就是本人第一次接触&#xff0c…

Quick-Media 中文二维码支持

Quick-Media 中文二维码支持 Quick-Media 项目提供了一些列多媒体操作的开箱即用工具类&#xff0c;比如图片编辑合成&#xff0c;markdown/html/svg渲染&#xff0c;音频处理&#xff1b;当然还有本文重点说明的二维码生成解析 QrCode-Plugin支持丰富的酷炫二维码生成&#x…

线上故障实录-一大早服务就不可用了?

线上故障实录-一大早服务就不可用了&#xff1f; 难得一个周末&#xff0c;一大早还没有睡醒就接到另外一个团队的电话&#xff0c;app 打不开了&#xff0c;所有的数据都没有了&#xff0c;睡意全无&#xff0c;赶紧起来看能不能紧急抢救一下&#xff0c;最终发现是一个关键链…