You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot加载CSS/JPG静态资源失败,求排查问题

Fixing Static Resource Access in Your Spring Boot App

Hey there, let's work through this static resource issue—you're really close, just a few small tweaks will get it working! Here are the key problems and fixes:

1. Wrong Thymeleaf Expression for Resource Paths

This is the biggest culprit! You're using message expressions (#{...}) for your CSS link, but Thymeleaf requires URL expressions (@{...}) to reference static resources. Message expressions are meant for internationalized text, not file paths.

Fix your index.html:

Change this line:

<link th:href="#{/css/main.css}" rel="stylesheet" >

To:

<link th:href="@{/css/main.css}" rel="stylesheet" >

Also, for your image, add a leading slash to avoid relative path issues (especially if your page is served from a subpath):

<img th:src="@{/img/img.jpg}"/>

2. Redundant (and Potentially Conflicting) Static Resource Config

Spring Boot automatically maps classpath:/static/ as a static resource directory by default. Your spring.resources.static-locations=classpath:static setting is unnecessary, and even has a small mistake (it should be classpath:/static/ with a leading slash if you do use it). Just delete this line from application.properties—the default behavior works perfectly.

3. Clean Up Your Security Config

You've got overlapping rules in your SecurityConfig that might cause confusion:

  • You're allowing access to /static/**, /css/**, /img/** in HttpSecurity
  • You're also ignoring /static/** in WebSecurity

web.ignoring() tells Spring Security to completely skip processing those paths, which is ideal for static resources (it's more efficient than permitAll()). Let's simplify this:

Updated SecurityConfig:

@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter{
    @Autowired
    private UtilisateurUserDetailsService userService;

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // @formatter:off
        http.authorizeRequests()
                .antMatchers("/","/index","/page1","/open/**").permitAll()
                .anyRequest().authenticated()
                .and()
                .formLogin()
                .loginPage("/login")
                .defaultSuccessUrl("/secure/page1")
                .failureUrl("/login?error=true")
                .permitAll()
                .and()
                .logout()
                .logoutUrl("/logout")
                .logoutSuccessUrl("/index")
                .permitAll();
        // @formatter:on
    }

    @Override
    public void configure(WebSecurity web) throws Exception {
        // Ignore all static resource paths completely
        web.ignoring().antMatchers("/css/**", "/img/**", "/js/**");
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(userService);
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }
}

Notice I changed the web.ignoring() to target the specific subdirectories (/css/**, /img/**) instead of /static/**—this matches how you're referencing them in your HTML (you don't include /static/ in the URL, since Spring maps those paths directly to the static folder).

Final Check

Make sure your static resources are in the correct directory structure:

src/main/resources/
└── static/
    ├── css/
    │   └── main.css
    └── img/
        └── img.jpg

That's it! With these changes, your CSS and images should load properly.

内容的提问来源于stack exchange,提问作者pikameuh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.08 18:18:16