Nginx Web Server Installation and Configuration Guide
Table of Contents
1. [Introduction](#introduction) 2. [Prerequisites](#prerequisites) 3. [Installation Methods](#installation-methods) 4. [Basic Configuration](#basic-configuration) 5. [Directory Structure](#directory-structure) 6. [Configuration Files](#configuration-files) 7. [Virtual Hosts](#virtual-hosts) 8. [SSL/TLS Configuration](#ssltls-configuration) 9. [Performance Optimization](#performance-optimization) 10. [Security Configuration](#security-configuration) 11. [Monitoring and Logging](#monitoring-and-logging) 12. [Common Commands](#common-commands) 13. [Troubleshooting](#troubleshooting)Introduction
Nginx (pronounced "engine-x") is a high-performance web server, reverse proxy server, and load balancer. Originally developed by Igor Sysoev in 2004, Nginx has become one of the most popular web servers due to its efficiency, stability, and low resource consumption. It excels at handling concurrent connections and is particularly well-suited for serving static content, acting as a reverse proxy, and load balancing.
Key Features
| Feature | Description | |---------|-------------| | High Performance | Can handle thousands of concurrent connections with low memory usage | | Reverse Proxy | Can act as a proxy server for HTTP, HTTPS, SMTP, POP3, and IMAP protocols | | Load Balancing | Distributes incoming requests across multiple backend servers | | Static Content Serving | Efficiently serves static files like images, CSS, and JavaScript | | SSL/TLS Termination | Handles SSL encryption and decryption | | HTTP/2 Support | Supports the latest HTTP protocol for improved performance | | Modular Architecture | Extensible through modules for additional functionality |
Prerequisites
Before installing Nginx, ensure your system meets the following requirements:
System Requirements
| Component | Minimum Requirement | Recommended | |-----------|-------------------|-------------| | Operating System | Linux, FreeBSD, Solaris, macOS, Windows | Ubuntu 20.04+, CentOS 8+, RHEL 8+ | | RAM | 512 MB | 2 GB or more | | CPU | 1 core | 2+ cores | | Disk Space | 50 MB | 1 GB for logs and cache | | Network | Basic network connectivity | Static IP address |
User Privileges
You need root or sudo privileges to install and configure Nginx. Ensure you can execute administrative commands on your system.
Installation Methods
Method 1: Package Manager Installation (Recommended)
#### Ubuntu/Debian Systems
`bash
Update package repository
sudo apt updateInstall Nginx
sudo apt install nginx -yVerify installation
nginx -v`Command Explanation:
- apt update: Updates the local package repository cache
- apt install nginx -y: Installs Nginx with automatic yes confirmation
- nginx -v: Displays the installed Nginx version
#### CentOS/RHEL/Fedora Systems
`bash
For CentOS/RHEL 8+
sudo dnf install nginx -yFor older CentOS/RHEL versions
sudo yum install nginx -yEnable and start Nginx
sudo systemctl enable nginx sudo systemctl start nginxCheck status
sudo systemctl status nginx`Command Explanation:
- dnf install nginx -y: Installs Nginx using DNF package manager
- systemctl enable nginx: Enables Nginx to start automatically on boot
- systemctl start nginx: Starts the Nginx service immediately
- systemctl status nginx: Shows the current status of Nginx service
Method 2: Compiling from Source
`bash
Install build dependencies (Ubuntu/Debian)
sudo apt install build-essential libpcre3-dev libssl-dev zlib1g-devDownload Nginx source
wget http://nginx.org/download/nginx-1.24.0.tar.gz tar -xzf nginx-1.24.0.tar.gz cd nginx-1.24.0Configure build options
./configure \ --prefix=/etc/nginx \ --sbin-path=/usr/sbin/nginx \ --conf-path=/etc/nginx/nginx.conf \ --error-log-path=/var/log/nginx/error.log \ --http-log-path=/var/log/nginx/access.log \ --pid-path=/var/run/nginx.pid \ --lock-path=/var/run/nginx.lock \ --with-http_ssl_module \ --with-http_realip_module \ --with-http_addition_module \ --with-http_gzip_static_moduleCompile and install
make sudo make install`Configuration Options Explanation:
- --prefix: Sets the main directory for Nginx files
- --sbin-path: Specifies the location of the Nginx binary
- --conf-path: Sets the main configuration file location
- --with-http_ssl_module: Enables SSL/TLS support
- --with-http_gzip_static_module: Enables static file compression
Basic Configuration
Initial Service Management
`bash
Start Nginx service
sudo systemctl start nginxEnable auto-start on boot
sudo systemctl enable nginxCheck service status
sudo systemctl status nginxReload configuration without stopping service
sudo systemctl reload nginxRestart service (stops and starts)
sudo systemctl restart nginxStop service
sudo systemctl stop nginx`Firewall Configuration
`bash
Ubuntu/Debian (UFW)
sudo ufw allow 'Nginx Full' sudo ufw allow 'Nginx HTTP' sudo ufw allow 'Nginx HTTPS'CentOS/RHEL (firewalld)
sudo firewall-cmd --permanent --add-service=http sudo firewall-cmd --permanent --add-service=https sudo firewall-cmd --reloadAlternative port-based approach
sudo firewall-cmd --permanent --add-port=80/tcp sudo firewall-cmd --permanent --add-port=443/tcp sudo firewall-cmd --reload`Directory Structure
Understanding Nginx's directory structure is crucial for effective configuration and maintenance.
Default Directory Layout
| Directory/File | Purpose | Description |
|----------------|---------|-------------|
| /etc/nginx/ | Main configuration directory | Contains all configuration files |
| /etc/nginx/nginx.conf | Main configuration file | Primary Nginx configuration |
| /etc/nginx/sites-available/ | Available site configurations | Virtual host configuration files |
| /etc/nginx/sites-enabled/ | Enabled site configurations | Symbolic links to active sites |
| /etc/nginx/conf.d/ | Additional configurations | Module-specific configuration files |
| /var/www/html/ | Default document root | Default location for web files |
| /var/log/nginx/ | Log files directory | Access and error logs |
| /usr/share/nginx/html/ | Default Nginx pages | Default welcome page and error pages |
Directory Structure Visualization
`
/etc/nginx/
├── nginx.conf # Main configuration file
├── mime.types # MIME type definitions
├── fastcgi_params # FastCGI parameters
├── sites-available/ # Available virtual hosts
│ ├── default # Default site configuration
│ └── example.com # Custom site configuration
├── sites-enabled/ # Enabled virtual hosts (symlinks)
│ └── default -> ../sites-available/default
├── conf.d/ # Additional configuration files
│ └── ssl.conf # SSL-specific settings
└── modules-enabled/ # Enabled modules
└── 50-mod-http-geoip.conf
`
Configuration Files
Main Configuration File (/etc/nginx/nginx.conf)
The main configuration file controls global Nginx settings and includes other configuration files.
`nginx
Main context - global settings
user www-data; worker_processes auto; pid /run/nginx.pid; include /etc/nginx/modules-enabled/*.conf;Events context - connection processing
events { worker_connections 1024; use epoll; multi_accept on; }HTTP context - web server settings
http { # Basic Settings sendfile on; tcp_nopush on; tcp_nodelay on; keepalive_timeout 65; types_hash_max_size 2048; server_tokens off; # MIME Types include /etc/nginx/mime.types; default_type application/octet-stream; # Logging Settings access_log /var/log/nginx/access.log; error_log /var/log/nginx/error.log; # Gzip Compression gzip on; gzip_vary on; gzip_proxied any; gzip_comp_level 6; gzip_types text/plain text/css text/xml text/javascript application/json application/javascript application/xml+rss application/atom+xml image/svg+xml; # Virtual Host Configurations include /etc/nginx/conf.d/*.conf; include /etc/nginx/sites-enabled/*; }`Configuration Directive Explanations
| Directive | Context | Purpose | Example Value |
|-----------|---------|---------|---------------|
| user | main | Defines user for worker processes | www-data |
| worker_processes | main | Number of worker processes | auto |
| worker_connections | events | Max connections per worker | 1024 |
| sendfile | http, server, location | Efficient file transmission | on |
| keepalive_timeout | http, server, location | Keep connections alive duration | 65 |
| gzip | http, server, location | Enable compression | on |
| server_tokens | http, server, location | Hide Nginx version | off |
Testing Configuration Syntax
`bash
Test configuration syntax
sudo nginx -tTest configuration and dump it
sudo nginx -TTest specific configuration file
sudo nginx -t -c /etc/nginx/nginx.conf`Command Options:
- -t: Test configuration file syntax
- -T: Test configuration and dump parsed configuration
- -c: Specify configuration file path
Virtual Hosts
Virtual hosts allow you to serve multiple websites from a single Nginx server. Each virtual host has its own configuration file.
Creating a Basic Virtual Host
#### Step 1: Create Configuration File
`bash
Create new site configuration
sudo nano /etc/nginx/sites-available/example.com`#### Step 2: Basic Virtual Host Configuration
`nginx
/etc/nginx/sites-available/example.com
server { listen 80; listen [::]:80; server_name example.com www.example.com; root /var/www/example.com/html; index index.html index.htm index.nginx-debian.html; # Logging access_log /var/log/nginx/example.com.access.log; error_log /var/log/nginx/example.com.error.log; # Main location block location / { try_files $uri $uri/ =404; } # Static file caching location ~* \.(jpg|jpeg|png|gif|ico|css|js)$ { expires 1y; add_header Cache-Control "public, immutable"; } # Security headers add_header X-Frame-Options "SAMEORIGIN" always; add_header X-XSS-Protection "1; mode=block" always; add_header X-Content-Type-Options "nosniff" always; add_header Referrer-Policy "no-referrer-when-downgrade" always; }`#### Step 3: Create Document Root
`bash
Create directory structure
sudo mkdir -p /var/www/example.com/htmlCreate sample index file
sudo nano /var/www/example.com/html/index.html``html
Welcome to example.com
This is a sample page served by Nginx.
`#### Step 4: Set Proper Permissions
`bash
Set ownership
sudo chown -R www-data:www-data /var/www/example.com/htmlSet permissions
sudo chmod -R 755 /var/www/example.com`#### Step 5: Enable the Site
`bash
Create symbolic link to enable site
sudo ln -s /etc/nginx/sites-available/example.com /etc/nginx/sites-enabled/Test configuration
sudo nginx -tReload Nginx
sudo systemctl reload nginx`Advanced Virtual Host Configuration
`nginx
server {
listen 80;
server_name example.com www.example.com;
# Redirect HTTP to HTTPS
return 301 https://$server_name$request_uri;
}
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name example.com www.example.com;
root /var/www/example.com/html;
index index.html index.htm index.php;
# SSL Configuration
ssl_certificate /etc/ssl/certs/example.com.crt;
ssl_certificate_key /etc/ssl/private/example.com.key;
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-RSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384;
ssl_prefer_server_ciphers off;
# Security headers
add_header Strict-Transport-Security "max-age=63072000" always;
add_header X-Frame-Options DENY always;
add_header X-Content-Type-Options nosniff always;
# Main location
location / {
try_files $uri $uri/ /index.php?$query_string;
}
# PHP processing
location ~ \.php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/var/run/php/php8.1-fpm.sock;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params;
}
# Deny access to sensitive files
location ~ /\. {
deny all;
}
location ~ ~$ {
deny all;
}
}
`
SSL/TLS Configuration
Obtaining SSL Certificates with Let's Encrypt
`bash
Install Certbot
sudo apt install certbot python3-certbot-nginx -yObtain certificate for domain
sudo certbot --nginx -d example.com -d www.example.comTest automatic renewal
sudo certbot renew --dry-runSet up automatic renewal cron job
sudo crontab -e`Add the following line to crontab:
`bash
0 12 * /usr/bin/certbot renew --quiet
`
Manual SSL Configuration
`nginx
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name example.com www.example.com;
# SSL Certificate files
ssl_certificate /etc/ssl/certs/example.com.crt;
ssl_certificate_key /etc/ssl/private/example.com.key;
# SSL Configuration
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
ssl_prefer_server_ciphers off;
# SSL Session settings
ssl_session_cache shared:SSL:10m;
ssl_session_timeout 10m;
# OCSP Stapling
ssl_stapling on;
ssl_stapling_verify on;
ssl_trusted_certificate /etc/ssl/certs/ca-certificates.crt;
resolver 8.8.8.8 8.8.4.4 valid=300s;
resolver_timeout 5s;
# Security headers
add_header Strict-Transport-Security "max-age=63072000; includeSubDomains; preload" always;
add_header X-Frame-Options DENY always;
add_header X-Content-Type-Options nosniff always;
add_header X-XSS-Protection "1; mode=block" always;
}
`
SSL Security Best Practices
| Setting | Purpose | Recommended Value |
|---------|---------|-------------------|
| ssl_protocols | Supported SSL/TLS versions | TLSv1.2 TLSv1.3 |
| ssl_ciphers | Encryption algorithms | Modern cipher suites only |
| ssl_prefer_server_ciphers | Cipher preference | off (let client choose) |
| ssl_session_cache | Session caching | shared:SSL:10m |
| ssl_stapling | OCSP stapling | on |
Performance Optimization
Worker Process Optimization
`nginx
/etc/nginx/nginx.conf
user www-data; worker_processes auto; # Use number of CPU cores worker_rlimit_nofile 65535;events {
worker_connections 1024;
use epoll;
multi_accept on;
}
`
HTTP Optimization
`nginx
http {
# Connection settings
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
keepalive_requests 100;
# Buffer settings
client_body_buffer_size 128k;
client_max_body_size 10m;
client_header_buffer_size 1k;
large_client_header_buffers 4 4k;
output_buffers 1 32k;
postpone_output 1460;
# Timeout settings
client_header_timeout 3m;
client_body_timeout 3m;
send_timeout 3m;
# Compression
gzip on;
gzip_vary on;
gzip_min_length 10240;
gzip_proxied expired no-cache no-store private must-revalidate auth;
gzip_types
text/plain
text/css
text/xml
text/javascript
application/x-javascript
application/javascript
application/xml+rss
application/json;
}
`
Caching Configuration
`nginx
Static file caching
location ~* \.(jpg|jpeg|png|gif|ico|css|js|woff|woff2)$ { expires 1y; add_header Cache-Control "public, immutable"; add_header Vary Accept-Encoding; access_log off; }HTML file caching
location ~* \.(html|htm)$ { expires 1h; add_header Cache-Control "public"; }Proxy caching (for reverse proxy setups)
proxy_cache_path /var/cache/nginx/proxy_cache levels=1:2 keys_zone=my_cache:10m max_size=10g inactive=60m use_temp_path=off;location / {
proxy_cache my_cache;
proxy_cache_valid 200 302 10m;
proxy_cache_valid 404 1m;
proxy_cache_use_stale error timeout updating http_500 http_502 http_503 http_504;
proxy_pass http://backend;
}
`
Security Configuration
Basic Security Headers
`nginx
Security headers configuration file
/etc/nginx/conf.d/security-headers.conf
add_header X-Frame-Options "SAMEORIGIN" always;
add_header X-XSS-Protection "1; mode=block" always;
add_header X-Content-Type-Options "nosniff" always;
add_header Referrer-Policy "no-referrer-when-downgrade" always;
add_header Content-Security-Policy "default-src 'self' http: https: data: blob: 'unsafe-inline'" always;
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
`
Rate Limiting
`nginx
Rate limiting configuration
http { # Define rate limiting zones limit_req_zone $binary_remote_addr zone=login:10m rate=10r/m; limit_req_zone $binary_remote_addr zone=global:10m rate=100r/m; # Connection limiting limit_conn_zone $binary_remote_addr zone=addr:10m; }server {
# Apply rate limiting
limit_req zone=global burst=20 nodelay;
limit_conn addr 10;
# Specific location rate limiting
location /login {
limit_req zone=login burst=5 nodelay;
}
}
`
Access Control
`nginx
IP-based access control
location /admin { allow 192.168.1.0/24; allow 10.0.0.0/8; deny all; }Password protection
location /private { auth_basic "Restricted Area"; auth_basic_user_file /etc/nginx/.htpasswd; }`Create password file:
`bash
Install htpasswd utility
sudo apt install apache2-utilsCreate password file
sudo htpasswd -c /etc/nginx/.htpasswd usernameAdd additional users
sudo htpasswd /etc/nginx/.htpasswd another_user`Monitoring and Logging
Log Configuration
`nginx
Custom log format
http { log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; log_format json_combined escape=json '{' '"time_local":"$time_local",' '"remote_addr":"$remote_addr",' '"remote_user":"$remote_user",' '"request":"$request",' '"status": "$status",' '"body_bytes_sent":"$body_bytes_sent",' '"request_time":"$request_time",' '"http_referrer":"$http_referer",' '"http_user_agent":"$http_user_agent"' '}'; access_log /var/log/nginx/access.log main; error_log /var/log/nginx/error.log warn; }`Status Module Configuration
`nginx
Enable status module
server { listen 80; server_name localhost; location /nginx_status { stub_status on; access_log off; allow 127.0.0.1; allow ::1; deny all; } }`Log Rotation
`bash
Configure logrotate
sudo nano /etc/logrotate.d/nginx``
/var/log/nginx/*.log {
daily
missingok
rotate 52
compress
delaycompress
notifempty
create 644 www-data adm
sharedscripts
prerotate
if [ -d /etc/logrotate.d/httpd-prerotate ]; then \
run-parts /etc/logrotate.d/httpd-prerotate; \
fi \
endscript
postrotate
invoke-rc.d nginx rotate >/dev/null 2>&1
endscript
}
`
Common Commands
Service Management Commands
| Command | Purpose | Usage Example |
|---------|---------|---------------|
| systemctl start nginx | Start Nginx service | sudo systemctl start nginx |
| systemctl stop nginx | Stop Nginx service | sudo systemctl stop nginx |
| systemctl restart nginx | Restart Nginx service | sudo systemctl restart nginx |
| systemctl reload nginx | Reload configuration | sudo systemctl reload nginx |
| systemctl status nginx | Check service status | sudo systemctl status nginx |
| systemctl enable nginx | Enable auto-start | sudo systemctl enable nginx |
| systemctl disable nginx | Disable auto-start | sudo systemctl disable nginx |
Configuration Testing Commands
`bash
Test configuration syntax
sudo nginx -tTest and display configuration
sudo nginx -TTest specific configuration file
sudo nginx -t -c /path/to/nginx.confShow Nginx version and configuration
nginx -VShow loaded modules
nginx -V 2>&1 | grep -o with-[a-z_]*`Process Management Commands
`bash
Send signals to Nginx master process
sudo nginx -s reload # Reload configuration sudo nginx -s reopen # Reopen log files sudo nginx -s stop # Fast shutdown sudo nginx -s quit # Graceful shutdownKill Nginx processes (emergency)
sudo pkill -f nginxShow Nginx processes
ps aux | grep nginx`Troubleshooting
Common Issues and Solutions
| Issue | Symptoms | Solution |
|-------|----------|----------|
| Configuration syntax error | Nginx fails to start/reload | Run nginx -t to identify syntax errors |
| Permission denied | 403 Forbidden error | Check file permissions and ownership |
| Port already in use | Bind error on startup | Check for conflicting services on ports 80/443 |
| SSL certificate issues | SSL/TLS errors | Verify certificate paths and validity |
| High memory usage | Server performance issues | Optimize worker processes and connections |
Diagnostic Commands
`bash
Check listening ports
sudo netstat -tlnp | grep nginx sudo ss -tlnp | grep nginxCheck Nginx processes
ps aux | grep nginxCheck system resources
top -p $(pgrep nginx | tr '\n' ',' | sed 's/,$//')Check error logs
sudo tail -f /var/log/nginx/error.logCheck access logs
sudo tail -f /var/log/nginx/access.logTest connectivity
curl -I http://localhost curl -I https://localhost`Debug Configuration
`nginx
Enable debug logging
error_log /var/log/nginx/debug.log debug;Debug specific client connections
events { debug_connection 192.168.1.100; debug_connection 192.168.1.0/24; }`Performance Monitoring
`bash
Monitor Nginx status
curl http://localhost/nginx_statusMonitor system performance
iostat -x 1 vmstat 1 sar -u 1Monitor network connections
netstat -an | grep :80 | wc -l ss -s`This comprehensive guide covers the essential aspects of installing and configuring Nginx web server. The configuration examples provided serve as starting points that can be customized based on specific requirements. Regular monitoring and maintenance ensure optimal performance and security of your Nginx installation.