SpringBoot 静态资源访问(图片/JS/CSS)配置详解

在 SpringBoot 项目开发中,静态资源访问 是前端页面、图片上传、富文本、后台管理系统必备的功能。

很多同学经常遇到:图片上传成功但访问 404、JS/CSS 加载失败、自定义目录不生效、线上环境无法访问等问题。

今天就来讲讲 SpringBoot 静态资源的默认规则、自定义配置、本地映射、外部路径、权限放行、打包部署


一、什么是静态资源?

  • • 图片:jpg、png、gif、webp

  • • 样式:css、less、scss

  • • 脚本:js、ts

  • • 静态页面:html、ico、font

  • • 上传文件:Excel、PDF、视频

SpringBoot 对这些资源提供自动映射 ,也支持高度自定义


二、SpringBoot 默认静态资源规则(自动生效)

默认 5 个静态资源路径(优先级从高到低):

    1. META-INF/resources
    1. resources/
    1. static/(最常用)
    1. public/
    1. webapp/

默认访问规则:

直接访问资源名即可,不需要加目录前缀。

示例:

go 复制代码
src/main/resources/static/images/logo.png

访问地址:

go 复制代码
http://localhost:8080/images/logo.png

三、最常用场景:自定义静态资源映射

实际项目中,我们会把用户上传的图片/文件 存放在服务器外部路径,避免项目重新打包文件丢失。

这时候必须用:SpringMVC 资源映射

1. 编写配置类

go 复制代码
package com.demo.config;

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

/**
 * 静态资源配置
 */
@Configuration
public class WebMvcConfig implements WebMvcConfigurer {

    /**
     * 静态资源映射
     * 访问路径 /uploads/xxx.jpg  →  映射到本地 D:/uploads/xxx.jpg
     */
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        // 1. 访问 URL 规则
        registry.addResourceHandler("/uploads/**")
                // 2. 本地真实路径(末尾必须加 /)
                .addResourceLocations("file:D:/uploads/");

        // 2. 也可以配置相对路径
        registry.addResourceHandler("/static/**")
                .addResourceLocations("classpath:/static/");
    }
}

2. 访问示例

本地文件:

go 复制代码
D:/uploads/avatar.jpg

访问地址:

go 复制代码
http://localhost:8080/uploads/avatar.jpg

四、application.yml 配置静态资源

如果你不想写配置类,可以直接在 yml 中配置:

go 复制代码
spring:
  web:
    resources:
      # 自定义静态资源路径
      static-locations: classpath:/static/,classpath:/public/,file:./uploads/

⚠️ 注意:
配置后会覆盖默认路径,不是追加,所以要把需要的路径都写上。


五、静态资源放行(解决 Shiro/Security 拦截 404)

如果项目集成了 Shiro/Spring Security,静态资源会被登录拦截,必须手动放行:

1. Shiro 放行配置

go 复制代码
filterMap.put("/static/**", "anon");
filterMap.put("/uploads/**", "anon");
filterMap.put("/**.js", "anon");
filterMap.put("/**.css", "anon");
filterMap.put("/**.png", "anon");
filterMap.put("/**.jpg", "anon");
filterMap.put("/**.ico", "anon");

2. Security 放行配置

go 复制代码
http.authorizeRequests()
    .antMatchers("/static/**","/uploads/**","/**.js","/**.css").permitAll()
    .anyRequest().authenticated();

六、自定义 favicon.ico(网站图标)

只需要把 favicon.ico 放到:

go 复制代码
resources/static/favicon.ico

SpringBoot 自动加载,无需任何配置。


七、SpringBoot 静态资源缓存(生产优化)

go 复制代码
registry.addResourceHandler("/static/**")
        .addResourceLocations("classpath:/static/")
        // 浏览器缓存 10 天
        .setCachePeriod(864000);

八、图片上传 + 回显完整实战

1. 上传接口

go 复制代码
@PostMapping("/upload")
public Result upload(MultipartFile file) throws IOException {
    // 上传目录
    String path = "D:/uploads/";
    File dir = new File(path);
    if (!dir.exists()) dir.mkdirs();

    // 文件名
    String fileName = UUID.randomUUID() + file.getOriginalFilename().substring(file.getOriginalFilename().lastIndexOf("."));
    file.transferTo(new File(path + fileName));

    // 返回可访问的 URL
    String url = "http://localhost:8080/uploads/" + fileName;
    return Result.success(url);
}

2. 配置映射

go 复制代码
registry.addResourceHandler("/uploads/**")
        .addResourceLocations("file:D:/uploads/");

九、Linux 服务器部署路径写法

go 复制代码
registry.addResourceHandler("/uploads/**")
        .addResourceLocations("file:/usr/local/uploads/");

十、静态资源 404 常见原因

    1. 路径末尾缺少 /

    错误:/uploads

    正确:/uploads/**

    1. 本地路径末尾缺少 /

    错误:file:D:/uploads

    正确:file:D:/uploads/

    1. 被拦截器/权限框架拦截

    需要放行静态资源

    1. Windows 与 Linux 路径格式不一致

    Windows:D:/uploads/

    Linux:/usr/local/uploads/

    1. 目录权限不足

    Linux 需要给目录读写权限


十一、SpringBoot 静态资源核心总结

    1. 默认路径:static 文件夹直接访问
    1. 外部文件:用 addResourceHandler 映射
    1. 图片上传:必须用外部路径,避免打包丢失
    1. 权限拦截:一定要放行静态资源
    1. 路径格式:末尾必须加 /
    1. 生产环境:配置缓存提升性能

掌握这些,所有静态资源问题全部解决!


结尾互动

大家在开发中有没有遇到过静态资源 404、图片无法访问的问题?

都是怎么解决的?欢迎评论区留言交流!


相关推荐
Soofjan2 小时前
Go 内存管理(3):内存分配源码
后端
oh LAN2 小时前
RuoYi-Vue-master:Spring Boot 4.x (JDK 17+) (环境搭建)
java·vue.js·spring boot
ch.ju2 小时前
Java程序设计(第3版)第二章——java的数据类型:小数
java
m0_738120722 小时前
渗透基础知识ctfshow——Web应用安全与防护(第一章)
服务器·前端·javascript·安全·web安全·网络安全
持续前行2 小时前
通过 npm 下载node_modules 某个依赖 ;例如 下载 @rollup/rollup-linux-arm64-gnu
前端·javascript·vue.js
Advancer-2 小时前
RedisTemplate 两种序列化实践方案
java·开发语言·redis
元宝骑士2 小时前
深度解析 ROW_NUMBER() 窗口函数:从入门到实战避坑指南
后端·mysql
java1234_小锋2 小时前
Java高频面试题:MyBatis如何实现动态数据源切换?
java·开发语言·mybatis
Embrace9243 小时前
React Native + Realm 离线方案处理
javascript·react native·react.js·realm