Site icon GetPageSpeed

The Pitfalls of add_header in NGINX: Solving Inheritance Issues with more_set_headers

📅 Updated: January 28, 2026 (Originally published: September 15, 2023)

When it comes to NGINX configuration, the devil is often in the details. One common pitfall is the add_header directive’s inheritance behavior, which frequently leads to unexpected results. The more_set_headers directive from the headers-more module solves this problem elegantly.

The Inheritance Problem with add_header

In NGINX, configurations use a hierarchical structure with server, location, and nested blocks. The add_header directive has a non-intuitive behavior: if you define a header in a parent block and then use add_header again in a child block, the child completely overwrites all parent headers.

Consider this example:

server {
    add_header X-Server "NGINX";

    location / {
        add_header X-Location "Root";
    }
}

When you access a URL matching location /, only X-Location: Root appears in the response. The X-Server: NGINX header from the parent block is completely lost.

The Workaround (Repetitive and Error-Prone)

To make add_header work as expected, you must repeat every header in each child block:

server {
    add_header X-Server "NGINX";

    location / {
        add_header X-Server "NGINX";
        add_header X-Location "Root";
    }
}

This approach is tedious, error-prone, and difficult to maintain in complex configurations.

The Solution: more_set_headers

The more_set_headers directive from the headers-more module provides intuitive inheritance. Headers set in parent blocks are automatically included in child blocks:

server {
    more_set_headers "X-Server: NGINX";

    location / {
        more_set_headers "X-Location: Root";
    }
}

With this configuration, responses include both X-Server: NGINX and X-Location: Root headers – exactly what you’d expect.

Install the Headers-More Module

Step 1. Add GetPageSpeed Repository

For Rocky Linux, AlmaLinux, CentOS 8/9, or Fedora:

sudo dnf install -y https://extras.getpagespeed.com/release-latest.rpm

For CentOS/RHEL 7:

sudo yum install -y https://extras.getpagespeed.com/release-latest.rpm

Note: An active NGINX Extras subscription is required for RHEL-based systems. Fedora users have free access.

Step 2. Install the Module

For Rocky Linux, AlmaLinux, CentOS 8/9, or Fedora:

sudo dnf -y install nginx-module-headers-more

For CentOS/RHEL 7:

sudo yum -y install nginx-module-headers-more

Step 3. Enable the Module

Add the following at the top of /etc/nginx/nginx.conf:

load_module modules/ngx_http_headers_more_filter_module.so;

Step 4. Reload NGINX

sudo systemctl reload nginx

When to Use Each Directive

Use Case Recommended Directive
Simple, single-location headers add_header is fine
Headers that should inherit to child blocks more_set_headers
Complex multi-level configurations more_set_headers
Removing or clearing headers more_clear_headers
Modifying upstream response headers more_set_headers with -s flag

Additional Capabilities

The headers-more module provides more than just more_set_headers:

Summary

The primary difference between add_header and more_set_headers is inheritance behavior. Use more_set_headers for intuitive, maintainable header management in complex NGINX configurations.

D

Danila Vershinin

Founder & Lead Engineer

NGINX configuration and optimizationLinux system administrationWeb performance engineering

10+ years NGINX experience • Maintainer of GetPageSpeed RPM repository • Contributor to open-source NGINX modules

Exit mobile version