0

I'm moving a project to use Docker with Nginx, which previously used Apache. It's a simple PHP project, but I can't get the rewriting to work like it did on Apache. The old .htaccess is simple;

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.+)$ index.php?page=$1 [L,QSA]

It redirects all page requests to the index.php file with a page parameter, which is then parsed in index.php with a custom PageController. I can't however get this to work with Nginx rewrites and it's confusing me a lot.

The goal is to rewrite URLs like index.php?page=forgot_password to forgot_password.

My current nginx.conf is

server {
    listen 80 default_server;
    root /app/app;

    index index.php index.html index.htm;

    location ~ \.php$ {
        fastcgi_pass php:9000;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
    }
}

which obviously doesn't work since there's no rewrite rules.

I've tried a few other configurations, for example the Nginx configuration in the Symfony documentation, which redirects all pages to index.php but doesn't provide the page query parameter.

I've tried other configurations like

location ~ \.php$ {
    fastcgi_pass php:9000;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    include fastcgi_params;
}

location / {
   if (!-e $request_filename){
     rewrite ^(.+)$ /index.php?page=$1 break;
   }
}

which causes Firefox to prompt me to download the forgot_password file.

I've had other attempts (which I can't remember sadly) that did seem to work the way I wanted, but caused JS, CSS and other resources to no longer work.

How can I get this working? I feel like I'm missing something simple.

  • Nginx uses the `try` directive instead of "file exists". So using a [standard WordPress setup](https://www.nginx.com/resources/wiki/start/topics/recipes/wordpress/), Nginx would try the URL literally (static content), then try the URL with a slash on it (checking for a folder) and then fall back to the index.php with [`$args`](https://nginx.org/en/docs/http/ngx_http_core_module.html#var_args) passed. This effectively maps one-to-one with the default htaccess version – Chris Haas Jun 28 '21 at 19:29
  • The Wordpress example (with some modifications) work in the way the URL is rewritten, but the `$args` are still not passed through so the wrong page is shown, and I don't understand why. Set `cgi.fix_pathinfo` to 0 in my `php.ini` as well, still nothing. – lolwut147258369 Jun 28 '21 at 21:11
  • What I linked to is pretty much the official config, even WP's main documentation recommends it, so I'd start there. I'd grab [WP-CLI](https://wp-cli.org/) if you don't have it already and run `wp rewrite flush` just to make sure that nothing is getting cached. (_That is the same as clicking Save Permalinks, just easier sometimes._) Make sure you have the `fastcgi` stuff, too – Chris Haas Jun 28 '21 at 21:32

1 Answers1

0

For the nginx configuration , EITHER rewrite the index as follows:

location / {
  if (!-e $request_filename){
    rewrite ^(.+)$ /index.php?page=$1 break;
  }
}

or Alternatively:

server {
    server_name yourdomain.com;
    location ~ "^/(.+)$" {
        try_files $uri $uri/ /index.php?page=$1;
    }
}
Ken Lee
  • 6,985
  • 3
  • 10
  • 29
  • I'm still severely confused, neither of these options individually work, both of them result into Firefox prompting me to download the file. – lolwut147258369 Jun 28 '21 at 20:54
  • what about other browsers - say chrome ? (I ask this because I suspect that your firefox may have problems ? please try clearing the cache or re-install it) – Ken Lee Jun 28 '21 at 21:01
  • Chrome does the same, I'm genuinely confused. This is my current nginx.conf file; https://pastebin.com/kcUE2wRn – lolwut147258369 Jun 28 '21 at 21:15
  • Just wonder -did u restart ngnix after changing the config file? – Ken Lee Jun 28 '21 at 21:22
  • I've been stopping and starting the docker container after every change, and changes to take effect between different attempts. – lolwut147258369 Jun 28 '21 at 21:24
  • Thanks. Do u have another ngnix server ? It is strange that the server is forcing diwnload – Ken Lee Jun 28 '21 at 21:34
  • I have some Laravel projects running on Sail which all work fine, but even copying those `nginx.conf` files doesn't fix it. They work to the point the URLs get rewritten, but no query params are being passed through. – lolwut147258369 Jun 28 '21 at 21:52
  • Does this solve your problem ? [link](https://stackoverflow.com/questions/25591040/nginx-serves-php-files-as-downloads-instead-of-executing-them) – Ken Lee Jun 29 '21 at 01:17