How to Reference Nginx Root Directive Path as a Variable in server Block Configuration


3 views

When working with Nginx configurations, you might encounter situations where you need to reuse the root path defined in your server block. A common use case is when you want to dynamically include configuration files from subdirectories relative to your root path.

server {
    listen 80;
    root /var/www/foosite;
    
    # This won't work - $root isn't automatically available
    include $root/*.ngaccess;
}

Nginx doesn't automatically expose the root directive value as a variable. Unlike some other web servers, Nginx variables must be explicitly declared. The root directive is part of the path resolution process, but it's not accessible as a standard variable.

Here are three practical approaches to solve this problem:

1. Using the map Directive

This method creates a reusable variable for your root path:

http {
    map $host $project_root {
        default /var/www/foosite;
    }

    server {
        listen 80;
        root $project_root;
        
        include $project_root/*.ngaccess;
    }
}

2. Environment Variables

For more dynamic configurations, consider using environment variables:

server {
    listen 80;
    root ${NGINX_ROOT:-/var/www/default};
    
    include ${NGINX_ROOT:-/var/www/default}/*.ngaccess;
}

3. Relative Path Approach

If your include files are in known locations relative to the configuration:

server {
    listen 80;
    root /var/www/foosite;
    
    # Use relative path from nginx config directory
    include ../sites/foosite/*.ngaccess;
}
  • Document your root path conventions in a central location
  • Consider using symbolic links for shared configurations
  • For complex setups, explore Nginx modules like ngx_http_js_module

If you have OpenResty or the ngx_http_lua_module installed:

server {
    listen 80;
    root /var/www/foosite;
    
    set_by_lua_block $custom_root {
        return ngx.var.document_root or "/var/www/foosite"
    }
    
    include $custom_root/*.ngaccess;
}

When configuring Nginx servers, developers often need to reuse the root path value elsewhere in their configuration. The straightforward approach of using $root doesn't work because Nginx doesn't automatically expose this directive as a variable.

Unlike some other web servers, Nginx doesn't create automatic variables for configuration directives. The root directive sets the filesystem path but doesn't create a corresponding $root variable you can reference later.

Here are three effective ways to solve this problem:

1. Using map to Create a Variable

http {
    map "" $root_path {
        default "/var/www/foosite";
    }

    server {
        listen 80;
        root $root_path;
        
        include $root_path/*.ngaccess;
    }
}

2. Environment Variables

env ROOT_PATH=/var/www/foosite;

server {
    listen 80;
    root $env:ROOT_PATH;
    
    include $env:ROOT_PATH/*.ngaccess;
}

Note: You'll need to ensure Nginx is built with the --with-http_realip_module for this approach.

3. Lua Scripting (Advanced)

For complex scenarios, you can use Nginx+Lua:

http {
    lua_shared_dict root_path 1m;
    
    init_by_lua_block {
        ngx.shared.root_path:set("main", "/var/www/foosite")
    }

    server {
        listen 80;
        set_by_lua $root_path 'return ngx.shared.root_path:get("main")';
        root $root_path;
        
        include $root_path/*.ngaccess;
    }
}

The map solution is generally the most performant for simple cases. Environment variables work well in containerized environments, while Lua provides maximum flexibility at a small performance cost.

If you're using Nginx 1.15.10+ with the --with-http_perl_module, you could also consider Perl variables:

perl_set $root_path 'sub { return "/var/www/foosite"; }';

server {
    listen 80;
    root $root_path;
    
    include $root_path/*.ngaccess;
}