1

For the love of nginx, I can't wrap my head around this issue.

Desired: I want two simple php projects (wordpress in the long haul) in two sub locations under one server block. Side note: These projects reside in two different directories on the server deployed with capistrano.

Problem: I either end up with a 404, 403 or a direct octet stream download of the index.php. On the latter I seem to hit the correct index.php but it is not passed to the php-fpm block. php-fpm is working and not the issue (tested in other serverblock without sublocations)

I have looked all over the web and have tried gazillions of "working" configs, but its not coming together.

Plan: Below you see a working nginx vhost, hitting the right index.html files in the correct alias directories. Thus I am halfway there.

With your help I would like to adapt the config below, to change the index to index.php and get php working on location /staging and /production.

In the location /production you see one config (commented out) how I tried to get php working.

server {
  listen 82;
  listen [::]:82;

  server_name nginx-web.ch;

  access_log /var/log/nginx/nginx-web_access.log;
  error_log /var/log/nginx/nginx-web_error.log;

  location  /staging {
    alias /var/www/nginx-web1/current;
    index index.html
    add_header X-debug-message "Location web1";
  }

  location /production {
    alias /var/www/nginx-web/current;
    index index.html
    add_header X-debug-message "Location web";

    #try_files $uri $uri/ /production/index.php;

    #location ~ \.php$ {
      # add_header X-debug-message "Location ~ php";
      # try_files $uri =404;
      # fastcgi_split_path_info ^(.+\.php)(/.+)$;
      # fastcgi_pass unix:/var/run/php5-fpm.sock;
      # fastcgi_index index.php;
      # include fastcgi_params;
      # fastcgi_param  SCRIPT_FILENAME $document_root$fastcgi_script_name;
    #}
  }
}

Here is a working server block it tried to adapt for sublocations, without success :(

server {
  listen 80;
  listen [::]:80;

  server_name testdev;

  access_log /var/log/nginx/wp_access.log;
  error_log  /var/log/nginx/wp_error.log;

  root /var/www;
  index index.php;

  location / {
    try_files $uri $uri/ /index.php?$args; 
  }

  location ~ \.php$ {
    try_files $uri =404;
    fastcgi_split_path_info ^(.+\.php)(/.+)$;
    fastcgi_pass unix:/var/run/php5-fpm.sock;
    fastcgi_index index.php;
    include fastcgi_params;
  }
}

UPDATE with WORKING CONFIG (gotta <3 serverfault/stackoverflow):

Here is the final working configuration, many thanks to @RichardSmith

server {
    listen 82;
    listen [::]:82;

    server_name nginx-web.ch;

    access_log /var/log/nginx/nginx-web_access.log;
    error_log /var/log/nginx/nginx-web_error.log;

    index index.php;

    location ^~ /staging/ {
      alias /var/www/nginx-web1/current/;

      if (!-e $request_filename) { rewrite ^ /staging/index.php last; }

      location ~ \.php$ {
       if (!-f $request_filename) { return 404; }

       include fastcgi_params;
          fastcgi_param  SCRIPT_FILENAME $request_filename;
          fastcgi_pass unix:/var/run/php5-fpm.sock;
       }
    }

    location /production {
      alias /var/www/nginx-web/current;

      if (!-e $request_filename) { rewrite ^ /production/index.php last; }

      location ~ \.php$ {
        if (!-f $request_filename) { return 404; }

        include fastcgi_params;
          fastcgi_param  SCRIPT_FILENAME $request_filename;
          fastcgi_pass unix:/var/run/php5-fpm.sock;
        }
    }
}
mahatmanich
  • 2,794
  • 3
  • 21
  • 23

1 Answers1

1

This pattern works:

location ^~ /prefix/ {
    alias /path/to/root/;
    if (!-e $request_filename) { rewrite ^ /prefix/index.php last; }

    location ~ \.php$ {
        if (!-f $request_filename) { return 404; }

        include        fastcgi_params;
        fastcgi_param  SCRIPT_FILENAME $request_filename;
        fastcgi_pass   ...;
    }
}

Use the ^~ prefix to avoid other regular expression location blocks taking precedence. See this document.

The value of the location and the alias both end with / or neither end with /. See this document.

Avoid using alias and try_files together due to this issue and see this caution on the use of if.

Use $request_filename as the computed value of SCRIPT_FILENAME (as it works with both alias and root).

Always set fastcgi_param after including the fastcgi_params file, to avoid the latter silently overwriting the local value.

Richard Smith
  • 11,859
  • 2
  • 18
  • 26
  • Hi Richard, I have it all setup as you wrote, but I am hitting this: nginx and php-fpm “Primary script unknown” https://serverfault.com/questions/734935/nginx-and-php-fpm-primary-script-unknown since I don't have a root set on the server and I am using $request_filename how can that be? – mahatmanich Nov 24 '17 at 12:23
  • Current config try for staging: https://pastebin.com/WWsAnYhd – mahatmanich Nov 24 '17 at 12:25
  • That should be `rewrite ^ /staging/index.php last;` - the rewrite target is a URI not a file path. – Richard Smith Nov 24 '17 at 12:29
  • 1
    Use `fastcgi_param SCRIPT_FILENAME $request_filename;` instead of `fastcgi_param SCRIPT_FILENAME $fastcgi_script_name;` - the latter is the URI and not the path to the file. – Richard Smith Nov 24 '17 at 12:30
  • 1
    And FYI, the `fastcgi_split_path_info` and `fastcgi_index` statements are redundant, as they have no effect on URIs that end with `.php`. – Richard Smith Nov 24 '17 at 12:33
  • Great, staging is now working. Do you have a link to the doc of the fastcgi params? – mahatmanich Nov 24 '17 at 12:34
  • 1
    They are all [documented here](http://nginx.org/en/docs/http/ngx_http_fastcgi_module.html). – Richard Smith Nov 24 '17 at 12:35
  • fastcgi_split_path_info and fastcgi_index are not needed? Even if I use URIs with ?$args (wordpress) later – mahatmanich Nov 24 '17 at 12:38
  • 1
    That is correct. The query string is not part of the *normalized URI* which is used to evaluate locations, rewrites and the request filename. – Richard Smith Nov 24 '17 at 12:40
  • Thanks a lot for your time! You have been immensely helpful! – mahatmanich Nov 24 '17 at 12:41