· yebor974 · Advanced Techniques, Tutorials, Troubleshooting
How to cache Livewire & static assets for Laravel / Filament app
Learn how to configure Nginx to cache static assets like CSS, JS, and images for better performance in Laravel Filament apps using Livewire.

When building high-performance Laravel applications with tools like Filament and Livewire, caching static assets such as CSS, JS, and images can drastically improve loading speed.
However, one common pitfall is Livewire’s JavaScript not being served as a physical file by default. This leads to issues where caching fails or the asset is even entirely missed by Nginx because it’s handled by Laravel’s router.
The Livewire asset problem
Out of the box, livewire/livewire
serves its JS via a route, not a static file. That means a request to /livewire/livewire.min.js
goes through Laravel and not directly through Nginx, making it hard to cache or serve properly.
To fix this, you must publish the Livewire assets into the public directory:
php artisan livewire:publish --assets
And to make sure this happens on every update (e.g. after composer install
or composer update
), you should add it to your composer.json
scripts:
"scripts": {
"post-autoload-dump": [
...
"@php artisan vendor:publish --force --tag=livewire:assets --ansi"
]
}
Optimizing Nginx Virtual Host for caching
To cache static files like .css
, .js
, .png
, .jpg
, etc., add the following to your Nginx virtual host config:
location ~* \.(svg|jpg|jpeg|png|gif|webp|css|js)$ {
add_header Cache-Control "public, must-validate, max-age=31536000";
}
This instructs the browser to cache these assets for up to one year. Don’t worry about users getting outdated versions, Laravel Mix or Vite includes hashed filenames (e.g., app.abc123.js
or app.js?v=xxxxx
) that change when the content changes.
What about other Hosting setups?
While this article uses Nginx as an example, the core concept applies no matter where you host your Laravel app:
- On Apache, you’d configure similar caching behavior via
.htaccess
or virtual host directives. - On shared hosting, you can often manage asset caching through control panels or
.htaccess
. - On Docker setups, the same Nginx configuration applies within your container.
- Using Forge, Ploi, or other deployment platforms? These tools usually expose Nginx configs directly, so you can apply the same logic.
The goal is always the same: make your static assets truly static, and ensure they’re served as efficiently as possible.
Bonus: Cross-Origin asset sharing for subdomains
If your Laravel Filament app is serving multiple subdomains (e.g., for different tenants or admin panels), you might run into CORS issues when assets are shared across subdomains.
To fix that, one common solution is to add this Nginx block:
location ~* \.(svg|jpg|jpeg|png|gif|webp|css|js)$ {
add_header Access-Control-Allow-Origin *;
add_header Cache-Control "public, must-validate, max-age=31536000";
}
This setup tells the browser:
- “You can load these assets from any domain” (via the Access-Control-Allow-Origin * header),
- “You can cache them for up to one year.”
Example of Nginx caching working correctly for static assets (served from memory):
Livewire’s JavaScript now served as a static file, allowing proper caching and avoiding Laravel routing:
Important Security Note
Using Access-Control-Allow-Origin *
is not always safe.
You should only use it when serving public, static assets (like images, CSS, or JS files that don’t contain sensitive or dynamic content). Never use this wildcard header on routes that handle authentication, APIs, or dynamic content.
If you’re dealing with credentials (cookies, tokens) or want to control which origins are allowed, it’s better to use a more restrictive rule like:
add_header Access-Control-Allow-Origin https://admin.example.com;
Final thoughts
With this Nginx configuration:
- You’ll benefit from fast and efficient asset delivery through long-term caching.
- Livewire will no longer be blocked by Laravel routing thanks to published assets :).
- You’ll be better prepared for subdomain usage (with CORS considerations clearly understood).
It’s a small tweak, but it can make a huge difference, both in app performance and developer sanity, especially when it comes to SEO.