nginx/Passenger: Servindo um arquivo em cache somente se um parâmetro não estiver na solicitação

nginx/Passenger: Servindo um arquivo em cache somente se um parâmetro não estiver na solicitação

Para um determinado padrão de URL ( /scripts/.*\.meta\.js), gostaria de ter o seguinte comportamento:

  • Se a URL contiver um parâmetro específico ( version), forneça a solicitação ao Passageiro para tratar.
  • Se o URL não contiver esse parâmetro específico e existir um arquivo em cache, forneça-o.
  • Se a URL não contiver esse parâmetro específico e um arquivo em cache não existir, forneça a solicitação para o Passenger tratar.

Estou fazendo isso para melhorar o desempenho, evitando que o Passenger e o aplicativo Rails por trás dele tenham que lidar com a maioria das solicitações para esse caminho.

Meu arquivo conf nginx é:

server {

  listen 80;
  server_name my.site;

  root /path/to/rails/public;
  passenger_enabled on;
  rails_env development;
  passenger_min_instances 1;

  client_max_body_size 5m;

  location ~* /scripts/.*\.meta\.js {

    error_page 418 = @noparams;

    if ( $arg_version = '' ) {
      return 418;
    }
  }

  location @passenger {
    root /path/to/rails/public;
    proxy_set_header X-Forwarded-Proto http;
    passenger_enabled on;
  }

  location @noparams {
    try_files  /a$uri @passenger =401;
  }

}

Coloquei os arquivos de teste em /path/to/rails/public/a. Isso dá o seguinte comportamento:

  • ✓ Se a URL contiver um parâmetro específico ( version), entregue a solicitação ao Passageiro para tratar.
  • ✓ Se o URL não contiver esse parâmetro específico e existir um arquivo em cache, forneça-o.
  • ❌ Se a URL não contiver esse parâmetro específico e não existir um arquivo em cache, forneça a solicitação para o Passageiro tratar.Comportamento real: HTTP 401.

Parece que o que tenho não é a maneira correta de fazer referência ao Passenger no arquivo try_files. O que preciso fazer para que isso funcione?

Responder1

Fiquei com a impressão de que try_filesé uma lista de "coisas" para tentar, e você pode colocar um local nomeado em qualquer posição. Como Michael Hampton observa num comentário, isto está incorreto. Locais nomeados e códigos HTTP só podem estar na última posição try_files; qualquer coisa que não esteja na última posição deve ser um caminho de arquivo. Então try_files /a$uri @passengerfunciona como eu pretendo.

Também não é necessário repetir a configuração interna, @passengerpois ela é herdada do serverbloco. Portanto, uma configuração funcional é:

server {

  listen 80;
  server_name my.site;

  root /path/to/rails/public;
  passenger_enabled on;
  rails_env development;
  passenger_min_instances 1;

  client_max_body_size 5m;

  location ~* /scripts/.*\.meta\.js {

    error_page 418 = @noparams;

    if ( $arg_version = '' ) {
      return 418;
    }
  }

  location @passenger { }

  location @noparams {
    try_files  /a$uri @passenger;
  }

}

informação relacionada