Migrating and Upgrading Nginx
1. Planning Nginx Version Upgrades
Upgrade Planning Steps
- Review the
CHANGELOGor release notes for the target Nginx version to identify breaking changes, deprecated features, and new capabilities. - Check compatibility of current modules (e.g.,
ngx_http_lua_module,mod_security) with the new Nginx version. - Back up the current configuration files and any custom modules or patches.
- Test the upgrade in a staging environment that mirrors production as closely as possible.
- Plan for downtime windows, especially if the upgrade requires a full restart of Nginx.
| Upgrade Phase | Description | Actions | Notes |
|---|---|---|---|
| Preparation | Assess readiness for upgrade | nginx -V to check version and modulesReview logs for errors or warnings |
Ensure all modules are compatible with the target version |
| Testing | Validate upgrade in a sandboxed environment | Deploy new version with same config Run performance and load tests |
Use nginx -t to verify config syntax |
| Rollout | Deploy to production with minimal impact | Gradually shift traffic or restart Nginx Monitor logs and metrics post-upgrade |
Have rollback plan ready in case of issues |
Note: Nginx versions follow semantic versioning. Major version upgrades (e.g., 1.20 to 1.25) may introduce breaking changes that require configuration adjustments.
2. Testing Configuration Compatibility
| Test Command | Description | Notes |
|---|---|---|
| nginx -t | Test the Nginx configuration for syntax errors | Does not check for compatibility issues with new versions |
| nginx -T | Display the full configuration including included files | Useful for debugging complex configurations |
Example: Testing Configuration
nginx -t
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful
Note: The
-t flag only checks syntax, not compatibility with newer Nginx versions.Warning: Always backup your configuration before upgrading Nginx to avoid service disruption.
Compatibility Testing Steps
- Run
nginx -tto check syntax - Review logs for any warnings or errors
- Test with a staging environment if possible
- Verify that all modules used are still supported in the new version
3. Performing Zero-downtime Upgrades
Zero-downtime upgrades allow you to upgrade Nginx without dropping any active connections. This is achieved by replacing the Nginx binary while keeping the same process running.
| Step | Description | Action |
|---|---|---|
| 1 | Prepare the new Nginx binary | Ensure the new version is built and installed in the same location as the current binary. |
| 2 | Send the signal to reload | Run kill -USR1 $(cat /var/run/nginx.pid) to initiate the upgrade process. |
| 3 | Verify the upgrade | Check that the new binary is running and all connections are handled properly. |
Note: The upgrade process will start a new Nginx master process with the updated binary, while the old worker processes continue handling existing connections until they finish.
Example: Zero-downtime upgrade command
# Send signal to upgrade Nginx without downtime
kill -USR1 $(cat /var/run/nginx.pid)
4. Migrating Configuration Between Servers
| Step | Description | Action |
|---|---|---|
| 1 | Identify configuration files to migrate | Locate nginx.conf, included config files, and any custom modules or scripts. |
| 2 | Ensure compatibility of Nginx versions | Verify that the source and target servers run compatible Nginx versions. Check for deprecated directives. |
| 3 | Backup current configuration | Archive the existing nginx.conf and any related files to a safe location. |
| 4 | Transfer configuration files | Copy the configuration files to the target server using secure methods like scp or sftp. |
| 5 | Validate configuration syntax | Run nginx -t on the target server to check for syntax errors. |
| 6 | Test configuration on target server | Use nginx -s reload to apply the new configuration without downtime. |
Example: Securely copying configuration files
# On source server<br>scp /etc/nginx/nginx.conf user@target-server:/etc/nginx/<br><br>scp -r /etc/nginx/conf.d/ user@target-server:/etc/nginx/
Note: Always test configuration changes in a staging environment before applying to production.
Warning: Ensure that all referenced paths and file permissions are valid on the target server.
5. Converting Apache to Nginx Configuration
| Apache Directive | Nginx Equivalent | Notes |
|---|---|---|
| ServerName | server_name |
Multiple names can be specified in one directive |
| DocumentRoot | root |
Defines the root directory for requests |
| DirectoryIndex | index |
Specifies the default file to serve |
| Alias | location with alias |
Maps a URL to a filesystem path |
| Redirect | return |
Can be used for 301/302 redirects |
| RewriteRule | rewrite |
Use rewrite with break or last |
| ErrorLog | error_log |
Specifies the error log file path |
| CustomLog | access_log |
Specifies the access log file path |
| AllowOverride | Not directly supported, use location blocks |
Control access to configuration directives |
| Options | location with autoindex |
Control directory listing and file access options |
Example: Basic Apache to Nginx Conversion
<VirtualHost *:80>
ServerName example.com
DocumentRoot /var/www/html
DirectoryIndex index.html
Alias /images /var/www/images
<Directory "/var/www/html">
Options Indexes
AllowOverride None
</Directory>
ErrorLog /var/log/apache2/error.log
CustomLog /var/log/apache2/access.log combined
</VirtualHost>
Example: Equivalent Nginx Configuration
server {
listen 80;
server_name example.com;
root /var/www/html;
index index.html;
location /images {
alias /var/www/images;
}
location / {
autoindex on;
}
error_log /var/log/nginx/error.log;
access_log /var/log/nginx/access.log;
}
Key Differences in Configuration Syntax
- Block Structure: Apache uses
<VirtualHost>and<Directory>, while Nginx usesserverandlocationblocks. - Directive Names: Many directives have different names (e.g.,
AllowOverridevs.locationblocks in Nginx). - Module Support: Apache uses modules for features, while Nginx has built-in support or uses
ngx_http_rewrite_modulefor URL rewrites.
Note: When converting configurations, ensure that all paths and permissions are correctly set in the new environment.
6. Handling Deprecated Directives
| Directive | Deprecated in Version | Replacement | Notes |
|---|---|---|---|
| limit_zone | 1.19.0 |
limit_req_zone |
Use limit_req_zone for rate limiting with zones |
| limit_req | 1.19.0 |
limit_req_zone |
Use limit_req_zone for rate limiting with zones |
| limit_conn | 1.19.0 |
limit_conn_zone |
Use limit_conn_zone for connection limiting with zones |
| limit_conn_zone | 1.19.0 |
limit_conn_zone |
Use limit_conn_zone for connection limiting with zones |
| limit_req_zone | 1.19.0 |
limit_req_zone |
Use limit_req_zone for rate limiting with zones |
Example: Migrating from limit_zone to limit_req_zone
# Old configuration (deprecated)
limit_zone my_zone:10m rate=1r/s;
server {
limit_req zone=my_zone burst=5 nodelay;
}
# New configuration (recommended)
limit_req_zone $binary_remote_addr zone=my_zone:10m rate=1r/s;
server {
limit_req zone=my_zone burst=5 nodelay;
}
Note: Ensure that all deprecated directives are replaced with their modern equivalents before upgrading to newer versions of Nginx.
7. Rolling Back Failed Upgrades
Example: Reverting Nginx Configuration After Failed Upgrade
sudo cp /etc/nginx/nginx.conf.backup /etc/nginx/nginx.conf
sudo systemctl restart nginx
| Action | Description | Command |
|---|---|---|
| Revert config | Restore previous working configuration | sudo cp /etc/nginx/nginx.conf.backup /etc/nginx/nginx.conf |
| Reload Nginx | Apply new config without downtime | sudo systemctl reload nginx |
| Restart service | Full restart if reload fails | sudo systemctl restart nginx |
Note: Always keep a backup of your previous configuration before upgrading.
Warning: If the rollback fails, consider restoring from a system snapshot or backup.
8. Upgrading Dynamic Modules
| Module | Upgrade Method | Notes |
|---|---|---|
| ngx_http_geo_module | Recompile with new version | Dynamic module support added in Nginx 1.25.0 |
| ngx_http_map_module | Recompile with new version | Dynamic module support added in Nginx 1.25.0 |
| ngx_http_upstream_module | Recompile with new version | Dynamic module support added in Nginx 1.25.0 |
Note: Dynamic modules must be recompiled with the new Nginx version to ensure compatibility and access to new features.
Example: Recompiling Dynamic Module
./configure --with-compat --add-dynamic-module=/path/to/module
make
make install
9. Migrating SSL Certificates
| Step | Description | Action |
|---|---|---|
| 1 | Backup existing certificates | |
| 2 | Obtain new certificate from CA or renew existing | |
| 3 | Update Nginx config with new certificate paths | |
| 4 | Test Nginx configuration | nginx -t |
| 5 | Reload Nginx to apply changes | systemctl reload nginx |
Note: Ensure the new certificate and key have correct permissions (e.g., 600) to prevent unauthorized access.
10. Testing Upgrade Impact
Example: Simulate upgrade with config test
# Test new config syntax
nginx -t -c /etc/nginx/nginx.conf
# Dry-run with new config
nginx -t -c /etc/nginx/nginx-new.conf
| Command | Description | Notes |
|---|---|---|
| nginx -t | Test configuration syntax | Exits with code 0 if valid |
| nginx -T | Print full config (debug) | Includes included files |
Note: Use
nginx -t before reloading to catch syntax errors.Example: Check module compatibility
# List loaded modules
nginx -V 2>&1 | grep --with-colon --only-matching 'modules:.*'
# Compare versions
nginx -v
nginx -V 2>&1 | grep --only-matching 'nginx version:.*'
Upgrade Testing Approaches
- Staging Environment: Mirror production setup for full impact testing
- Canary Deployment: Route small traffic to upgraded instance
- Rolling Restart: Gradually restart workers to test config changes
- Config Validation: Use
nginx -tto verify syntax and module compatibility
11. Documenting Configuration Changes
| Change Type | Description | Documentation Format | Example |
|---|---|---|---|
| Syntax | Configuration directive syntax | Directive name and parameter format | listen 80; |
| Purpose | Functionality of the directive | Short explanation of use case | Enables listening on port 80 for HTTP requests |
| Scope | Where directive can be used | Contexts: http, server, location | http, server, location |
| Default Value | Value if not specified | Default setting or behavior | listen 80; (if not specified) |
Example: Logging Configuration Changes
# Log configuration changes in a centralized file
echo "[2026-04-05 10:00:00] Updated server block to use TLS 1.3" >> /var/log/nginx/config_changes.log
Note: Use a consistent format for documenting changes to ensure easy tracking and rollback if needed.
Warning: Always backup configuration files before making changes to avoid downtime or misconfigurations.
Best Practices for Configuration Documentation
- Record all changes with timestamps and reasons
- Use version control (e.g., Git) to track configuration files
- Include rollback procedures for major changes
- Document any custom modules or third-party integrations
12. Implementing Blue-Green Deployments
Example: Blue-Green Deployment Configuration
# Upstream configuration for blue and green environments
upstream backend_blue {
server 10.0.1.10:8080;
server 10.0.1.11:8080;
}
upstream backend_green {
server 10.0.2.10:8080;
server 10.0.2.11:8080;
}
# Main server block
server {
listen 80;
server_name example.com;
# Route to blue environment by default
location / {
proxy_pass http://backend_blue;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
}
# Health check endpoint
location /health {
access_log off;
return 200 "healthy\n";
add_header Content-Type text/plain;
}
}
| Component | Description | Notes |
|---|---|---|
| upstream backend_blue | server 10.0.1.10:8080; |
Blue environment backend servers |
| upstream backend_green | server 10.0.2.10:8080; |
Green environment backend servers |
| proxy_pass | http://backend_blue |
Current active backend (blue) |
Blue-Green Deployment Workflow
- Deploy new version to green environment
- Run health checks on green servers
- Switch traffic from blue to green using Nginx config update
- Retire old blue environment after validation
Note: Requires separate backend services for each environment and a mechanism to switch traffic between them.
Warning: Ensure proper health checks are in place to avoid routing traffic to unhealthy servers.