4

I'm using nginx:1.16.0-alpine image of Docker for serve react app (which is built before) and I want to redirect to index.html page in any cases (in what URL is got)

nginx.conf file has the following content:

user  nginx; worker_processes  auto;

error_log  /var/log/nginx/error.log warn; pid       
/var/run/nginx.pid;

events {
    worker_connections  1024; }

http {
    include       /etc/nginx/mime.types;
    default_type  application/octet-stream;

    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

    access_log  /var/log/nginx/access.log  main;

    sendfile        on;
    #tcp_nopush     on;

    keepalive_timeout  65;

    #gzip  on;

    include /etc/nginx/conf.d/*.conf;

    server {
        location / {
            try_files $uri $uri/ /index.html;
        }

        location ~ ^/$ {
            rewrite  ^.*$  /index.html  last;
        }
    }
}

Actually the server section is added and the other lines are default!

Dockerfile content is as below as well:

FROM nginx:1.16.0-alpine

COPY ./build /usr/share/nginx/html
COPY nginx.conf /etc/nginx/nginx.conf

EXPOSE 80

CMD ["nginx", "-g", "daemon off;"]

For making sure, after building the container from the image and going to the shell inside that, the file /etc/nginx/nginx.conf has the above content.

But the problem is: When I browse the url http://localhost:3000/login (for example), it doesn't redirect to http://localhost:3000/index.html. It shows:

404 Not Found nginx/1.16.0

(Docker container is run on output port 3000 and local port on 80)

Does anybody know why it is not working!?
(I also searched the similar ways, but no success!)

UPDATED:
The page React-router and nginx doesn't solve the problem.

Siyavash Hamdi
  • 2,764
  • 2
  • 21
  • 32

1 Answers1

4

Comment the following line

# include /etc/nginx/conf.d/*.conf;

Why? Due to the line

include /etc/nginx/conf.d/*.conf;

The default.conf is loaded and your server config is ignored.

In addition, you need to include the root information in your server (which previously was provided by default.conf


How to reproduce

put the following 2 files in the same folder and execute

docker build -t test . && docker run --rm -p 8080:80 test

Dockerfile

FROM nginx:1.16.0-alpine

# COPY ./build /usr/share/nginx/html
COPY nginx.conf /etc/nginx/nginx.conf

EXPOSE 80

CMD ["nginx", "-g", "daemon off;"]

nginx.conf

user nginx; worker_processes auto;

error_log /var/log/nginx/error.log warn; pid
/var/run/nginx.pid;

events { worker_connections 1024; }

http { include /etc/nginx/mime.types; default_type application/octet-stream;

log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                  '$status $body_bytes_sent "$http_referer" '
                  '"$http_user_agent" "$http_x_forwarded_for"';

access_log  /var/log/nginx/access.log  main;

sendfile        on;
#tcp_nopush     on;

keepalive_timeout  65;

#gzip  on;

#include /etc/nginx/conf.d/*.conf;

    server {
    location / {
        root   /usr/share/nginx/html;
        index  index.html index.htm;
        try_files $uri $uri/ /index.html;
    }

    location ~ ^/$ {
        rewrite  ^.*$  /index.html  last;
    }
    listen       80;
    server_name  localhost;

    # redirect server error pages to the static page /50x.html
    #
    error_page   500 502 503 504  /50x.html;
    location = /50x.html {
        root   /usr/share/nginx/html;
    }
}
}
ckaserer
  • 4,827
  • 3
  • 18
  • 33
  • Thanks for your response, but it doesn't work. the error message changed to "500 Internal Server Error - nginx/1.16.0" – Siyavash Hamdi Jan 07 '20 at 09:38
  • This seems to be the correct answer - including the default server config will surely mess with the server config you have added. You should do one or the other - more typical would be to add your server config to `conf.d/default.conf`. In any case, if you are now getting a `500`, you need to check the logs and find out why. – Don't Panic Jan 07 '20 at 10:24
  • To avoid `500`, add `root /usr/share/nginx/html;` under `server` directive (taken from a more advanced configuration: https://gkedge.gitbooks.io/react-router-in-the-real/content/nginx.html). – yurloc Jan 07 '20 at 10:59
  • @Don'tPanic, This is the log after going to localhost:3000/login: `2020/01/07 11:49:33 [error] 6#6: *2 rewrite or internal redirection cycle while internally redirecting to "/index.html", client: 172.17.0.1, server: , request: "GET /login HTTP/1.1", host: "localhost:3000"` `172.17.0.1 - - [07/Jan/2020:11:49:33 +0000] "GET /login HTTP/1.1" 500 579 "-" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.88 Safari/537.36" "-"` – Siyavash Hamdi Jan 07 '20 at 11:51
  • @SiyavashHamdi, I've updated the answer to take the missing root into account – ckaserer Jan 07 '20 at 12:25
  • 1
    @SiyavashHamdi, great! I recommend, that you put the server definition into a dedicated file copy it into `/etc/nginx/conf.d/` as `default.conf` and leave the original `nginx.conf` as is. e.g. do not copy `nginx.conf` into your container, but `default.conf` into `/etc/nginx/conf.d/` containing only the server section. If you need help a hand with that, let me know. – ckaserer Jan 07 '20 at 13:01