Vite builds with VITE_BASE_URL=/kiwi so assets are referenced as
/kiwi/assets/... in index.html. When accessed via Caddy at the /kiwi
path, Caddy strips the prefix and nginx gets /assets/... correctly.
When accessed directly at localhost:8515, nginx had no /kiwi/ route
so the JS/CSS 404'd and the SPA never booted (blank page on hard refresh).
Add location ^~ /kiwi/ { alias ...; } — ^~ prevents the regex
\.(js|css|...)$ location from intercepting /kiwi/ paths first.
43 lines
1.5 KiB
Text
43 lines
1.5 KiB
Text
server {
|
|
listen 80;
|
|
server_name _;
|
|
|
|
root /usr/share/nginx/html;
|
|
index index.html;
|
|
|
|
# Proxy API requests to the FastAPI container via Docker bridge network.
|
|
location /api/ {
|
|
proxy_pass http://api:8512;
|
|
proxy_set_header Host $host;
|
|
proxy_set_header X-Real-IP $remote_addr;
|
|
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
|
proxy_set_header X-Forwarded-Proto $http_x_forwarded_proto;
|
|
# Forward the session header injected by Caddy from cf_session cookie.
|
|
proxy_set_header X-CF-Session $http_x_cf_session;
|
|
# Allow image uploads (barcode/receipt photos from phone cameras).
|
|
client_max_body_size 20m;
|
|
}
|
|
|
|
# When accessed directly (localhost:8515) instead of via Caddy (/kiwi path-strip),
|
|
# Vite's /kiwi base URL means assets are requested at /kiwi/assets/... but stored
|
|
# at /assets/... in nginx's root. Alias /kiwi/ → root so direct port access works.
|
|
# ^~ prevents regex locations from overriding this prefix match for /kiwi/ paths.
|
|
location ^~ /kiwi/ {
|
|
alias /usr/share/nginx/html/;
|
|
try_files $uri $uri/ /index.html;
|
|
}
|
|
|
|
location = /index.html {
|
|
add_header Cache-Control "no-cache, no-store, must-revalidate";
|
|
try_files $uri /index.html;
|
|
}
|
|
|
|
location / {
|
|
try_files $uri $uri/ /index.html;
|
|
}
|
|
|
|
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg|woff2?)$ {
|
|
expires 1y;
|
|
add_header Cache-Control "public, immutable";
|
|
}
|
|
}
|