NGINX: How to Allow Only a Range of IP Addresses

Updated: January 19, 2024 By: Guest Contributor Post a comment

Introduction

In the world of server management, NGINX is known for its high performance and ability to handle a large number of connections simultaneously. However, there might be scenarios where you only want to allow traffic from a specific range of IP addresses to access certain pages or your entire server. This could be for security reasons, to restrict access to an internal network, or to ensure that only authorized users can access your application. In this tutorial, we’ll go over how to set up IP-based restrictions in NGINX, from basic to advanced configurations.

Prerequisites

  • An NGINX web server up and running.
  • Access to the terminal with sudo privileges.
  • Basic knowledge of NGINX configuration files.

Basic IP Restriction

The basic form of IP restriction in NGINX involves using the allow and deny directives inside your server or location blocks. While allow specifies which IP addresses should have access, deny will block the specified IP addresses or ranges.

server {
    listen 80;
    server_name example.com;

    location / {
        allow 192.168.1.0/24;
        deny all;

        try_files $uri $uri/ =404;
    }
}

In this example, we’re allowing the entire 192.168.1.0/24 range to access our server. This means any IP address from 192.168.1.1 to 192.168.1.255 can access the site, while other IP addresses will be denied.

Multiple IP Ranges

If you want to allow several different IP ranges to access your server, you can list multiple allow directives before the deny directive.

location /admin {
    allow 192.168.1.0/24;
    allow 10.0.0.0/16;
    deny all;

    # Admin specific configuration...
}

This configuration would allow access to the /admin location from two IP ranges: 192.168.1.0/24 and 10.0.0.0/16. All other IP addresses will be denied access.

Advanced IP Restriction with Geo Module

NGINX’s ngx_http_geo_module module allows for more advanced IP filtering rules. This includes setting variable values based on the client IP address that can be used later in the configuration for conditional access.

geo $limited_access {
    default 0;
    192.168.1.0/24 1;
    10.0.0.0/16 1;
}

server {
    location /restricted {
        if ($limited_access = 0) {
            return 403;
        }

        # Restricted content...
    }
}

The geo block defines a variable $limited_access based on the IP address of the incoming request. In the location block, we then use an if statement to return a 403 Forbidden error if $limited_access is set to 0, which represents not being in the specified IP ranges.

Whitelisting and Blacklisting

You can also create a mix of allow and deny rules to create a detailed access control list. Whitelisting allows certain IP addresses while blacklisting denies them.

location / {
    deny 192.168.1.100;
    allow 192.168.1.0/24;

   # Continue with existing location block configurations...
    deny all;
}

This configuration denies access to a single IP address (192.168.1.100) within an allowed range before denying access to all other IP addresses.

Including External Access Lists

If you have a large list of allowed or denied IPs, it may be cleaner to maintain these lists outside of your main NGINX configuration file. You can include external files using the include directive.

geo $limited_access {
    include /etc/nginx/conf.d/ip_allowlist.conf;
    default 0;
}

And inside ip_allowlist.conf:

192.168.1.0/24 1;
10.0.0.0/16 1;

Remember to create the ip_allowlist.conf file with the necessary IP ranges and permissions.

Restricting Access Based on Country

If you want to take your geo-restrictions further, you can restrict traffic based on the geographical location or country using the GeoIP module.

geoip_country /usr/share/GeoIP/GeoIP.dat;
map $geoip_country_code $allowed_country {
    default no;
    US yes;
    CA yes;
}

server {
    if ($allowed_country = no) {
        return 403;
    }

    # Server content...
}

This requires MaxMind’s GeoIP databases and the ngx_http_geoip_module.

Testing Your Configuration

It’s important to test your NGINX configuration for any syntax errors before reloading:

sudo nginx -t

If there are no errors, you can proceed with:

sudo service nginx reload

Remember to clear your caches and refresh your page after any changes to see the effect.

Conclusion

Restricting access to your NGINX server by IP range is a powerful way to secure your server and web applications. With the techniques discussed in this tutorial, you are now able to create and manage complex access control lists tailored to your needs. Consistently review and update your access rules to maintain optimal security and functionality.