Nginx HTTPS Redirect Loop with no fix

June 22, 2017 2.1k views
Nginx Caching LEMP DigitalOcean PHP Ubuntu 16.04

Hi all,

I set up ssl certificate for my website recently and it was working but i messed up somewhere in the config.

I've replaced all my actual website link with *******.com

I run Ubuntu 16.04
Nginx 1.10
PHP7
MySql

Every time i visit my website on chrome, i get the error:

This page isn’t working

*******.com redirected you too many times.
Try clearing your cookies.
ERRTOOMANY_REDIRECTS

My config file is as follows:

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

        server_name *******.com;
        return 301 $scheme://*******.com$request_uri;

        root /var/www/html;
        index index.html index.htm;

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

    location ~ [^/]\.php(/|$) {
        fastcgi_split_path_info ^(.+?\.php)(/.*)$;
        fastcgi_pass unix:/run/php/php7.1-fpm.sock;
        fastcgi_index index.php;

        include /etc/nginx/config/php/fastcgi_params;
    }

server {
        listen 443 ssl http2;
        listen [::]:443 ssl http2;
        server_name *******.com;

        root /var/www/html;
        index index.html index.htm;

        ssl on;
        ssl_certificate /etc/ssl/*******.com.certchain.crt;
        ssl_certificate_key /etc/ssl/*******.com.key;

        ssl_session_cache shared:SSL:20m;
        ssl_session_timeout 60m;

        ssl_prefer_server_ciphers on;
        ssl_ciphers ECDH+AESGCM:ECDH+AES256:ECDH+AES128:DHE+AES128:!ADH:!AECDH:!MD5;

        ssl_dhparam /etc/ssl/certs/dhparam.pem;

        ssl_protocols TLSv1 TLSv1.1 TLSv1.2;

        ssl_stapling on;
        ssl_stapling_verify on;
        ssl_trusted_certificate /etc/ssl/certs/trustchain.crt;
        resolver 8.8.8.8 8.8.4.4;

        add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
}

I've tried many solutions but havent come up with anything.

Plsease help me out!

2 Answers

@shaansuleman,

Your real goal appears to be redirecting all HTTP traffic to HTTPS. First off, always use 302 redirects until you get things working; 301s are a PITA to clear from your browser.

Your problem is in the redirect URL. $scheme refers to "ftp://", "http://" etc. Your redirect rule catches all http traffic and says to go to the same URL, because you used $scheme, which places the "http://" right back in. There's your loop. The correct redirect for your purpose is:

return 302 https://*******.com$request_uri;

(remember, 302 until you're sure it works, then change it to 301)

@shaansuleman

The main issue I see is with the port 80 server block. I would condense it down as the location blocks and related directives are not needed if you are simply wanting to redirect traffic from port 80 to 443.

You'd also want to move some of the config from the port 80 server block to the port 443 server block.

What I would recommend using is:

server {
    listen 80;
    listen [::]:80;
    server_name *******.com;

    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name *******.com;

    root /var/www/html;
    index index.html index.htm;

    ssl on;
    ssl_certificate /etc/ssl/*******.com.certchain.crt;
    ssl_certificate_key /etc/ssl/*******.com.key;

    ssl_session_cache shared:SSL:20m;
    ssl_session_timeout 60m;

    ssl_prefer_server_ciphers on;
    ssl_ciphers ECDH+AESGCM:ECDH+AES256:ECDH+AES128:DHE+AES128:!ADH:!AECDH:!MD5;

    ssl_dhparam /etc/ssl/certs/dhparam.pem;

    ssl_protocols TLSv1 TLSv1.1 TLSv1.2;

    ssl_stapling on;
    ssl_stapling_verify on;
    ssl_trusted_certificate /etc/ssl/certs/trustchain.crt;
    resolver 8.8.8.8 8.8.4.4;

    add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;

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

    location ~ [^/]\.php(/|$) {
        fastcgi_split_path_info ^(.+?\.php)(/.*)$;
        fastcgi_pass unix:/run/php/php7.1-fpm.sock;
        fastcgi_index index.php;

        include /etc/nginx/config/php/fastcgi_params;
    }
}
Have another answer? Share your knowledge.