私は次のnginx設定を持っています:
server {
listen 8080;
root /site_root/web;
index index.html;
server_name www.mysite.com;
location / {
try_files $uri @rewriteapp;
}
location @rewriteapp {
rewrite ^(.*)$ /app.php/$1 last;
}
# add headers to static files
location ~* \.(?:ico|css|js|gif|jpe?g|png|svg|woff|ttf|eot)$ {
expires 365d;
add_header Pragma public;
add_header Cache-Control "public";
}
location ~ \.php {
fastcgi_split_path_info ^(.+\.php)(/.*)$;
include fastcgi_params;
fastcgi_param PATH_TRANSLATED $document_root$fastcgi_path_info;
fastcgi_param PATH_INFO $fastcgi_path_info;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param HTTPS $https;
fastcgi_pass unix:/var/run/php-fpm-www.sock;
}
}
Issueこれは、フロントコントローラーといくつかの静的アセット(js/cssなど)がファイルシステム上のファイルとして存在する標準のphpアプリケーションです(引数として、これらのファイルの場所は '/ site_root/web/assetsです) ')。
上記の構成の目的は、これらの静的ファイルに「max-age」ヘッダーを追加して、ブラウザーがそれらをキャッシュできるようにすることです。これは、ファイルシステムに存在するすべてのファイルに対して機能します。 ただし動的に生成され、phpを通過する必要があるアセットがいくつかあります( '/site_root/web/assets/dynamic/file.uk.js'、'/site_root/web/assets/dynamic/ file.us.js '、' /site_root/web/assets/variable/variable.uk.js ')。
問題は、locationディレクティブ「静的ファイルにヘッダーを追加する」を含めると、それらの動的ファイルが404になることです。どうすればよいですか(各ソリューションの望ましい順序で)。
サーバーに存在しないファイルを除外するようにlocationディレクティブを変更します(try_files/internal?を使用)
一致するパスを除外するように場所ディレクティブを変更します(ホワイトリスト、たとえば「動的|変数」)
これは、 nginxは1つのロケーションブロックのみを使用する という事実に帰着します。 otherロケーションブロック内のすべてが無視されます。質問では、ファイルが存在するかどうかに関係なく、「静的ファイル」ロケーションブロックに一致するリクエストは、そのロケーションブロックによってのみ処理されます。曖昧な点があるときはいつでも、デバッグに役立つテクニックを見つけます。
location /something-else {
add_header "section" "something else location";
# ^ if this location block is used, that header is in the output
...
}
応答のヘッダーには、一致したブロックから追加されたヘッダーが含まれます。
$ curl -I "http://nginx.h5bp.dev/something"
...
section: something location # <- like so
多くの解決策があり、あなたは この参照資料 を読むのに役立つかもしれません。覚えておくべきことの1つは、nginxがプレフィックスルーティングで使用されることを目的としていることです。これにより、nginxとあなたにとっては簡単になります。
だから、あなたがこれを行うことができれば:
location ~ ^/(css|images|js)/ {
expires 365d;
add_header Pragma public;
add_header Cache-Control "public";
}
location ~ \.php {
...
}
それが最適なソリューションです。ネストされたロケーションブロックを使用する拡張機能も、必要に応じて使用できます。
location ~ ^/(css|images|js)/ {
location ~* \.(?:whatever|ext)$ {
expires 365d;
add_header Pragma public;
add_header Cache-Control "public";
}
}
location ~ \.php {
...
}
質問では、ロケーションブロックが1つあります。したがって、Michealが述べたように、これは明らかな代替手段です。
location ~* \.(?:ico|css|js|gif|jpe?g|png|svg|woff|ttf|eot)$ {
try_files $uri @rewriteapp; # <- added
expires 365d;
add_header Pragma public;
add_header Cache-Control "public";
}
location ~ \.php {
...
}
ただし、複数のロケーションブロックがある場合、これはかなり退屈になります(ただし、nginxを設計どおりに使用していないこともおそらく示しています)。
ロケーションブロックがどのように見えるかに関係なく、常に機能するセットアップは、404フロントコントローラーを使用することです。あなたの場合、これは意味します:
server {
listen 8080;
root /site_root/web;
index index.html;
server_name www.mysite.com;
try_files $uri $uri/ @rewriteapp;
error_page 404 = @rewriteapp
location @rewriteapp {
rewrite ^ /app.php/$request_uri last;
}
# add headers to static files
location ~* \.(?:ico|css|js|gif|jpe?g|png|svg|woff|ttf|eot)$ {
expires 365d;
add_header Pragma public;
add_header Cache-Control "public";
}
location ~ \.php {
fastcgi_split_path_info ^(.+\.php)(/.*)$;
include fastcgi_params;
fastcgi_param PATH_TRANSLATED $document_root$fastcgi_path_info;
fastcgi_param PATH_INFO $fastcgi_path_info;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param HTTPS $https;
fastcgi_pass unix:/var/run/php-fpm-www.sock;
}
}
または類似。自分に合った最も簡単なソリューションを選択してください。
それらをアプリケーションに渡してみませんか?
location ~* \.(?:ico|css|js|gif|jpe?g|png|svg|woff|ttf|eot)$ {
try_files $uri @rewriteapp;
#...everything else