Spring Boot project with static content generates 404 when running jar
Master System Design with Codemia
Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.
Introduction
A Spring Boot application may serve static assets correctly in development but return 404 when packaged as an executable jar. The root cause is usually resource placement, packaging configuration, or URL mapping conflicts. A repeatable diagnostic workflow can resolve this quickly.
Core Sections
Where Spring Boot Looks for Static Resources
By default, Spring Boot serves static content from classpath locations such as static, public, and META-INF/resources. The common path for web assets is:
src/main/resources/static
If files are placed under src/main/webapp, behavior can differ depending on packaging mode and build setup. For jar packaging, classpath resource directories are the safest default.
Confirm Assets Are Packaged into the Jar
Before changing code, inspect the built artifact and verify assets exist where runtime expects them.
For Gradle:
If files are missing, check build excludes, incorrect source directories, or accidental profile-specific filtering.
Correct Project Layout and Access Paths
A minimal layout that works reliably:
Then run the jar and test with direct URLs.
If your app uses server.servlet.context-path=/app, static resources move under that prefix, so the URL becomes /app/css/app.css.
Avoid Controller Mapping Collisions
A broad controller mapping can steal requests from static resource handlers.
If this returns a view name that does not exist, you may see 404 and assume static mapping failed. Keep API routes under /api and let static paths remain unmapped unless customization is intentional.
Explicit Resource Handler Configuration
When custom behavior is needed, configure resource handlers directly.
This is useful when migrating legacy URLs or serving assets under a custom prefix. Verify that rewritten paths in frontend HTML match this mapping.
Troubleshoot Jar Runtime Versus IDE Runtime
IDE launches may include directories that differ from final jar classpath. Always validate with the actual packaged jar.
Debug output helps confirm handler mappings and active profiles. If profiles alter static path properties, a jar started without expected profile can produce a false 404 signal.
SPA Fallback Strategy
For single-page applications, direct navigation to a frontend route may return 404 unless fallback routing is configured. Add a controller that forwards unknown non-file routes to index.html.
This keeps API routes separate while allowing client-side routing frameworks to own route resolution.
Verify Resource Caching and MIME Types
A response can still appear broken even when files are found, especially if MIME type or cache headers are incorrect. Verify static responses directly at runtime.
Expect 200 and correct content types such as application/javascript and text/css. Also confirm cache policy aligns with release strategy, especially if file names are fingerprinted. Correct packaging plus proper headers prevents both 404 issues and stale frontend assets after deployment.
Common Pitfalls
- Storing static files outside classpath resource directories for jar builds.
- Verifying only IDE runtime and not checking packaged jar contents.
- Forgetting context-path prefixes when testing static URLs.
- Using broad controller mappings that intercept static resource requests.
- Enabling SPA routes without a server-side fallback to
index.html.
Summary
- Put static files under
src/main/resources/staticfor reliable jar serving. - Inspect built jar contents before debugging application code.
- Validate URLs with context-path and profile settings applied.
- Keep controller mappings from colliding with static handlers.
- Add explicit resource handlers or SPA fallback only when needed.

