springboot 资源resource文件加载优先级

1.问题

在通过spring项目官网生成的springboot
project项目中,通常我们知道,resource目录是存放项目的静态资源的目录,如在很久以前,项目开发没有采用前后端分离的时候,那么大量的js文件和html都将放到resource目录。
但是我们可以看到,这个自动生成的目录中有个static目录:
image.png

这不仅引起了我的好奇,什么情况下的文件需要放置道static目录?

2.springboot的资源目录优先级

这一查询不要紧,原来与springboot配置文件加载的目录类似,resources文件同样也可以放置在多个目录,但是具有不同的优先级。
resources支持的目录如下:

classpath:/public/
classpath:/resources/
classpath:/static/
classpath:/META-INF/resources/

  
  
  • 1
  • 2
  • 3
  • 4

我们知道resources目录在默认情况下编译之后会直接将资源放置到jar文件中,即classpath。那么我们分别在这些目录中配置相同的文件,1.html,其内容分别对应为其所在的目录。
image.png

我们访问http://127.0.0.1:8084/1.html,可以看到其结果:
image.png

classpath:/META-INF/resources/目录的静态资源文件具有最高的优先级。那么我们将这个目录中的1.html删除,再次访问:
image.png

现在访问到的是classpath:/resources/目录中的资源文件,我们将resources中的文件删除。再次访问:
image.png

现在访问到的是classpath:/static/目录中的资源文件,我们将static中的文件删除。再次访问:
image.png

最后才是classpath:/public目录的文件。

因此得到上述资源路径的优先级为:

目录优先级
classpath:/META-INF/resources/最高
classpath:/resources/其次
classpath:/static/第三
classpath:/public/最低

可见,spring官网创建的目录static,默认是第三优先级的。
我们可以在这些资源目录中放置我们所需的静态资源,这些资源都可以在tomcat启动之后在浏览器访问的url下面访问到。

3.相关源码

查看springboot源码,基于springboot 2.4.2的源码:
在WebMvcAutoConfiguration类中有一个方法:

@Override
protected void addResourceHandlers(ResourceHandlerRegistry registry) {
	super.addResourceHandlers(registry);
	if (!this.resourceProperties.isAddMappings()) {
		logger.debug("Default resource handling disabled");
		return;
	}
	ServletContext servletContext = getServletContext();
	addResourceHandler(registry, "/webjars/**", "classpath:/META-INF/resources/webjars/");
	addResourceHandler(registry, this.mvcProperties.getStaticPathPattern(), (registration) -> {
		registration.addResourceLocations(this.resourceProperties.getStaticLocations());
		if (servletContext != null) {
			registration.addResourceLocations(new ServletContextResource(servletContext, SERVLET_LOCATION));
		}
	});
}

  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16

可以看到,这个类首先会判断resourceProperties有没有被修改,也就是说,我们有没有自定义配置文件的加载顺序,如果没有被修改,那么会通过默认配置来实现,也就是上文中的顺序。
而在webProperities类中。
内部类Resources可以看到这个顺序:

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

CLASSPATH_RESOURCE_LOCATIONS树组即为我们定义的顺序,这个树组的顺序和前面我们测试的结果一致。

3. webjars

另外,在看前面代码的过程中,发现了一个有趣的webjars。

	addResourceHandler(registry, "/webjars/**", "classpath:/META-INF/resources/webjars/");

 
 
  • 1

webjars是什么呢?
我们可以看其官网:
https://www.webjars.org/
这是一个将前端资源变成jar包的工具库。这样一来可以将前端的各种依赖都通过maven进行管理。
image.png

其支持各种前端类库。
image.png

我们以jquery为例,在build.gradle中加入:

	compile 'org.webjars:jquery:3.5.1'

 
 
  • 1

可以看到,前端资源就这样被gradle当作jar包加载进来了。
image.png

我们可以访问:
http://127.0.0.1:8084/webjars/jquery/3.5.1/jquery.js
就能请求到jquery的js文件了。
image.png

这样我们可以理解,实际上META-INFO.resources是专门用来给前端资源文件使用的。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: Spring Boot可以通过以下方式获取resource文件: 1. 使用ResourceLoader 可以使用Spring Boot提供的ResourceLoader来获取resource文件,代码如下: ``` @Autowired private ResourceLoader resourceLoader; public void getResource() throws IOException { Resource resource = resourceLoader.getResource("classpath:config.properties"); InputStream inputStream = resource.getInputStream(); // 处理inputStream } ``` 2. 使用ClassPathResource 也可以使用ClassPathResource来获取resource文件,代码如下: ``` Resource resource = new ClassPathResource("config.properties"); InputStream inputStream = resource.getInputStream(); // 处理inputStream ``` 3. 使用@Value注解 在Spring Boot中,可以使用@Value注解来获取resource文件中的属性值,代码如下: ``` @Value("${config.property}") private String property; ``` 其中,config.property是resource文件中的属性名。 总之,Spring Boot提供了多种获取resource文件的方式,可以根据具体情况选择合适的方式。 ### 回答2: Spring Boot 是一个快速开发 Spring 应用程序的框架,相比于传统的 Spring 框架而言,它更简单、易用、快速。在 Spring Boot 中获取 resource 文件相对简单,下面我们来介绍一下其具体实现。 在 Spring Boot 项目中,resource 文件夹(或目录)常用来存放一些静态文件,如配置文件、图片、音频等等。获取 resource 文件的方式有很多种,下面介绍其中比较常用的两种方式:ClassPathResourceResourceLoader。 1. ClassPathResource ClassPathResource 是 Spring 框架中提供的一个类,用来表示 classpath 中的资源。通过它的构造方法可以获得一个 Resource 对象,示例如下: ```java Resource resource = new ClassPathResource("application.yml"); ``` 这里的 "application.yml" 即为 resource 文件的路径,它默认会在 classpath 目录下查找,如果要获取子目录下的文件,则需要指定完整路径。在获取到 Resource 对象后,可以通过其 getInputStream 方法来获取文件字节流,示例如下: ```java InputStream inputStream = resource.getInputStream(); ``` 2. ResourceLoader ResourceLoader 是 Spring 框架中提供的另一个类,它可以通过 getPath、getResource 和 getResourceAsStream 等方法获取到 resource 文件ResourceLoader 还支持获取多个 resource 文件,通过 Ant 风格的文件匹配模式来获取。示例如下: ```java ResourceLoader resourceLoader = new DefaultResourceLoader(); // 获取单个文件 Resource resource = resourceLoader.getResource("classpath:application.yml"); // 获取多个文件 Resource[] resources = resourceLoader.getResources("classpath:*.yml"); ``` 值得注意的是,在 Spring Boot 中也可以使用 @Value("${}") 来获取 resource 文件中的值,例如: ```java @Value("${application.name}") private String name; ``` 在使用 @Value 获取时需要在 application.yml 中定义对应的值。 从上述介绍可以看出,在 Spring Boot 中获取 resource 文件的方法非常简单,只需要使用 ClassPathResourceResourceLoader 即可。而在实际开发中,可以视情况而定,选择合适的方式来获取 resource 文件。 ### 回答3: Spring Boot是一种用于构建和部署Web应用程序的框架,具有自带的容器,便于开发者进行快速开发。在应用程序中,我们通常需要使用一些配置文件、模板文件或者其他资源文件,这些资源文件存放在src/main/resources目录下,Spring Boot提供了方便的方式来获取这些资源文件。 获取resource文件的方式: 1. 使用ClassPathResource ClassPathResource是Spring Framework中提供的类,它可以获取位于Classpath下的文件资源,比如我们经常使用的xml配置文件、properties配置文件等。示例代码如下: ``` ClassPathResource resource = new ClassPathResource("application.properties"); InputStream inputStream = resource.getInputStream(); Properties properties = new Properties(); properties.load(inputStream); ``` 这个代码片段读取了application.properties文件了其中的数据到properties对象中。 2. 使用ResourceLoader ResourceLoader是Spring Framework中提供的接口,它可以获取位于Classpath下的文件资源,也可以获取位于文件系统、网络等其他位置的文件资源。我们可以在Spring中使用ResourceLoader接口来获取资源,具体代码如下: ``` @Autowired private ResourceLoader resourceLoader; private Resource getResource(String location) { return resourceLoader.getResource(location); } public void loadResource(String location) throws IOException { Resource resource = getResource(location); InputStream inputStream = resource.getInputStream(); Properties properties = new Properties(); properties.load(inputStream); } ``` 这个代码片段中的getResource方法会根据传入的location返回一个Resource对象,而loadResource方法则是演示通过Resource对象获取文件的InputStream并数据到properties对象中的过程。 3. 使用@Value注解 Spring Boot还提供了一个简单的方式来获取配置文件中的属性值。只需要在代码中使用@Value注解并指定属性名即可获取属性值。示例代码如下: ``` @Value("${my.param}") private String myParam; ``` 这个代码片段中使用了Spring Expression Language(SpEL)的语法,my.param的值会被替换成application.properties配置文件中的对应属性的值。 综上所述,Spring Boot提供了多种方便的方式来获取resource文件,开发者可以根据需要选择适合自己的方式。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值