Linux Notes: Nginx (moving from Apache httpd to Nginx)

  1. The information presented here is intended for educational use by qualified computer technologists.
  2. The information presented here is provided free of charge, as-is, with no warranty of any kind.
Edit: 2026-09-25
back to: my Linux Notes (index)

Overview

Moving from Apache httpd to Ngnix (2026-09-16)

Step-1 (installing Nginx on AlmaLinux-9.8)

Step-2 (enabling CGI on AlmaLinux-9.8)

Step-3 (enabling autoindex and fancyindex on AlmaLinux-9.8)

Step-4 (enabling password protection of one folder on AlmaLinux-9.8)

Caveat:

Creating/populating a password file:

Now update the config file

Step-5 (forward http requests to https)

    server {
        listen       80;
      # listen       [::]:80;
        server_name  neilrieck.net *.neilrieck.net;
      # root         /usr/share/nginx/html;
        root         /var/www/html;                     # my Apache files live here

# Load configuration files for the default server block. include /etc/nginx/default.d/*.conf; # redirect http to httpd # note: 301 means permanently moved return 301 https://$host$request_uri;
}

My current conf (2026-09-24)

# ============================================================================
# For more information on configuration, see:
#   * Official English Documentation: http://nginx.org/en/docs/
#   * Official Russian Documentation: http://nginx.org/ru/docs/
# ============================================================================
# 1) 2026-09-14: changes to get CGI working with fastcgi / fcgi.
# 2) 2026-09-14: enabled autoindex
# 3) 2026-09-15: switched over to fancyindex (an optional package that might
#      not be on your system). On AlmaLinux-9 you need to do this first:
#         sudo dnf install nginx-mod-fancyindex.x86_64
# 4) 2026-09-16: enabled password protection on one folder
# 5) 2026-09-19: added an expires directive (two places)
# 6) 2026-09-20: concated my cert + intermediate certs into a bundle (all
#      browsers work properly but python-based test scripts failed; oops!)
# 7) 2026-09-22: tweaks to fancyindex_css_href
# 8) 2026-09-24: now redirect all http requests to httpd (but I will leave all
#                port 80 directives in place in case I change my mind)
# ============================================================================

user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log;
pid /run/nginx.pid;

# Load dynamic modules. See /usr/share/doc/nginx/README.dynamic.
include /usr/share/nginx/modules/*.conf;

events {
    worker_connections 1024;
}

http {
    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;
    access_log  /var/log/nginx/access.log  main buffer=8k flush=1m;

    sendfile            on;
    tcp_nopush          on;
    tcp_nodelay         on;
    keepalive_timeout   65;
    types_hash_max_size 4096;

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

    # Load modular configuration files from the /etc/nginx/conf.d directory.
    # See http://nginx.org/en/docs/ngx_core_module.html#include
    # for more information.
    include /etc/nginx/conf.d/*.conf;

    server {
        listen       80;
      # listen       [::]:80;
        server_name  neilrieck.net *.neilrieck.net;
      # root         /usr/share/nginx/html;
        root         /var/www/html;                     # my Apache files live here

        # Load configuration files for the default server block.
        include /etc/nginx/default.d/*.conf;

        #error_page 404 /404.html;
        #location = /404.html {
        #}

        #error_page 500 502 503 504 /50x.html;
        #location = /50x.html {
        #}

        # redirect http to httpd
        # note: 301 means permanently moved
        return 301 https://$host$request_uri;

        location ~ ^/mira/ {
            auth_basic "Restricted Access";
          # auth_basic_user_file /etc/nginx/.htpasswd;
            auth_basic_user_file /etc/nginx/passwd-folder-mira;
            # "autoindex" is built into nginx
            # autoindex on;
            # autoindex_exact_size off;
            # ------------------------------------
            # "fancyindex" is not built into nginx
            fancyindex on;
            fancyindex_default_sort name;
            fancyindex_directories_first on;
            fancyindex_case_sensitive off;
            fancyindex_exact_size off;
            fancyindex_time_format "%Y-%m-%d %H:%M";
            fancyindex_css_href /css/nsr-folder-default.css;
            try_files $uri $uri/ =404;
        }
        location / {
            expires 3600;                               # this affects cache-contol, etc.
            # "autoindex" is built into nginx
            # autoindex on;
            # autoindex_exact_size off;
            # ------------------------------------
            # "fancyindex" is not built into nginx
            fancyindex on;
            fancyindex_default_sort name;
            fancyindex_directories_first on;
            fancyindex_case_sensitive off;
            fancyindex_exact_size off;
            fancyindex_time_format "%Y-%m-%d %H:%M";
            fancyindex_css_href /css/nsr-folder-default.css;
        }
        location /cgi-bin/ {
            # Disable gzip so script outputs stream properly if needed
            gzip off;

            # The root directory where your 'cgi-bin' folder lives
            # e.g., if files are in /var/www/html/cgi-bin/, set root to /var/www/html
            root /var/www/html;                         # my Apache files live here

            # Pass requests to the fcgiwrap Unix socket
            # fastcgi_pass unix:/var/run/fcgiwrap.socket;
            fastcgi_pass unix:/run/fcgiwrap/fcgiwrap-nginx.sock;

            # Include standard Nginx FastCGI parameters
            include fastcgi_params;

            # Map the exact script filename to be executed
            fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        }
    }

# Settings for a TLS enabled server.
#
    server {
        listen       443 ssl http2;
      # listen       [::]:443 ssl http2;
        server_name  neilrieck.net *.neilrieck.net;
      # root         /usr/share/nginx/html;
        root         /var/www/html;                     # my Apache files live here

        # caveat: unlike Apache, Nginx has no provision for intermediate certs (eg. chain file) so you
        #         must create a bundle file which is a concat of the host cert file with the intermediate
        #         certs file file like so:
        #         1) cd /etc/pki/tls/certs
        #         2) cp host-file.crt chain-file.crt > bundle-file.crt
        #         3) now use an editor to ensure that the file is in PEM format
        #           (a) the file does not contain any blank likes or
        #           (b) the certs in the file stop/start on new lines
        #
      # ssl_certificate      "/etc/pki/nginx/server.crt";
      # ssl_certificate      "/etc/pki/tls/certs/neilrieck.net-20251022.cer";
        ssl_certificate      "/etc/pki/tls/certs/neilrieck.net-20251022-bundle.cer";
        #
      # ssl_certificate_key  "/etc/pki/nginx/private/server.key";
       ssl_certificate_key  "/etc/pki/tls/private/neilrieck.net-20251022.key";
        ssl_session_cache shared:SSL:1m;
        ssl_session_timeout  10m;
        ssl_ciphers PROFILE=SYSTEM;
        ssl_prefer_server_ciphers on;

        # Load configuration files for the default server block.
        include /etc/nginx/default.d/*.conf;

        #error_page 404 /404.html;
        #    location = /40x.html {
        #}

        #error_page 500 502 503 504 /50x.html;
        #    location = /50x.html {
        #}
        #
        #    password protected folder
        #    1) this special folder is password protected so needs to be encountered first
        #    2) this folder needs to have its own autoindex directives, or fancyindex directives.
        #       A common location entry (like the one 17-lines below) will not work here.
        #
        location ~ ^/mira/ {
            expires 3600;                               # this affects cache-contol, etc.
            auth_basic "Restricted Access";
          # auth_basic_user_file /etc/nginx/.htpasswd;
            auth_basic_user_file /etc/nginx/passwd-folder-mira;
            # "autoindex" is built into nginx
            # autoindex on;
            # autoindex_exact_size off;
            # ------------------------------------
            # "fancyindex" is not built into nginx
            fancyindex on;
            fancyindex_default_sort name;
            fancyindex_directories_first on;
            fancyindex_case_sensitive off;
            fancyindex_exact_size off;
            fancyindex_time_format "%Y-%m-%d %H:%M";
            fancyindex_css_href /css/nsr-folder-default.css;
            try_files $uri $uri/ =404;
        }
        #
        #    this declaration affects all subseqent folders
        #
        location / {
            expires 3600;                               # this affects cache-contol, etc.
            # "autoindex" is built into nginx
            # autoindex on;
            # autoindex_exact_size off;
            # ------------------------------------
            # "fancyindex" is not built into nginx
            fancyindex on;
            fancyindex_default_sort name;
            fancyindex_directories_first on;
            fancyindex_case_sensitive off;
            fancyindex_exact_size off;
            fancyindex_time_format "%Y-%m-%d %H:%M";
            fancyindex_css_href /css/nsr-folder-default.css;
        }
        location /cgi-bin/ {
            # Disable gzip so script outputs stream properly if needed
            gzip off;

            # The root directory where your 'cgi-bin' folder lives
            # e.g., if files are in /var/www/html/cgi-bin/, set root to /var/www/html
            root /var/www/html;

            # Pass requests to the fcgiwrap Unix socket
            # fastcgi_pass unix:/var/run/fcgiwrap.socket;
            fastcgi_pass unix:/run/fcgiwrap/fcgiwrap-nginx.sock;

            # Include standard Nginx FastCGI parameters
            include fastcgi_params;

            # Map the exact script filename to be executed
            fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        }
     }
}

 Back to Home
Neil Rieck
Waterloo, Ontario, Canada.