Главная / База знаний / GeoIP-блокировка в Nginx: ограничиваем доступ по странам
инструкция · 19 октября 2026

GeoIP-блокировка в Nginx: ограничиваем доступ по странам

Настраиваем ограничение доступа к сайту по географии через ngx_http_geoip2_module и базу MaxMind, разбираем реальные сценарии применения и почему это не замена настоящей защите.

Что такое GeoIP-фильтрация и когда она действительно нужна

GeoIP-фильтрация — это определение страны (а иногда и региона или города) по IP-адресу посетителя с последующим принятием решения на основе этой информации: пропустить запрос, показать другой контент или полностью отклонить соединение. В основе лежит открытая или коммерческая база данных, сопоставляющая диапазоны IP-адресов с географическими координатами и странами регистрации.

Легитимных причин использовать такую фильтрацию на практике несколько. Первая — у сайта объективно нет и не планируется реальной аудитории в определённых регионах, зато именно оттуда стабильно идёт основная масса автоматизированных сканеров уязвимостей, попыток перебора паролей и паразитного трафика ботов, создающего фоновую нагрузку на сервер без какой-либо коммерческой пользы.

Вторая причина — юридические и лицензионные ограничения: некоторые виды контента, стриминговых сервисов или программного обеспечения по условиям лицензии или закону должны быть недоступны в определённых странах, и владелец сайта обязан технически это обеспечить, а не полагаться на добросовестность посетителя. Третья, более редкая причина — маркетинговая логика, когда для разных регионов существуют разные локализованные версии сайта, и трафик из конкретной страны нужно направить на соответствующий раздел, а не блокировать вовсе.

Важно сразу разграничить два разных сценария использования: полную блокировку доступа для одних стран и просто ветвление логики (другой язык, другая валюта, другой раздел каталога) для других — технически оба реализуются похожим образом через определение страны, но по цели и по строгости это разные задачи, и в этой статье речь в первую очередь о первом сценарии, блокировке.

Модуль ngx_http_geoip2_module и база MaxMind GeoLite2

Современный способ определения страны по IP в Nginx — модуль ngx_http_geoip2_module, работающий с базами данных в формате MMDB от компании MaxMind. Устаревший модуль ngx_http_geoip_module, работавший с более старым форматом Legacy, официально не поддерживается MaxMind с 2019 года — новые серверы стоит настраивать сразу через geoip2, не тратя время на устаревший вариант.

В большинстве дистрибутивов модуль устанавливается отдельным пакетом, поскольку не входит в базовую сборку Nginx по умолчанию, — либо через официальный пакет для конкретного дистрибутива, либо путём пересборки Nginx из исходников с явным указанием флага --add-module, если используется нестандартная сборка сервера.

Установка модуля geoip2 для Nginx на Ubuntu/Debian из штатного пакета
apt install libnginx-mod-http-geoip2 -y

Саму базу данных GeoLite2 (в бесплатном варианте — GeoLite2-Country.mmdb для определения страны или GeoLite2-City.mmdb для более детального определения города) нужно скачать отдельно с сайта MaxMind после бесплатной регистрации и получения лицензионного ключа — без ключа автоматическое скачивание через их официальную утилиту geoipupdate работать не будет.

Скачивание и обновление баз GeoLite2 через официальную утилиту geoipupdate
geoipupdate -f /etc/GeoIP.conf -d /usr/share/GeoIP/

Настройка блока geoip2 и переменной страны

После установки модуля и загрузки базы данных в основной конфигурации Nginx, вне блока server (обычно в http-контексте или в отдельном подключаемом файле), нужно указать путь к файлу базы и объявить переменную, в которую модуль будет записывать код страны для каждого входящего запроса.

Подключение базы GeoLite2 и объявление переменной с кодом страны в http-контексте Nginx
geoip2 /usr/share/GeoIP/GeoLite2-Country.mmdb {
    auto_reload 60m;
    $geoip2_data_country_code country iso_code;
}

Параметр auto_reload указывает Nginx периодически перечитывать файл базы данных без полного перезапуска сервера — это удобно в связке с автоматическим обновлением базы через cron: как только geoipupdate перезаписывает файл свежей версией, Nginx подхватит изменения сам в течение заданного интервала, без ручной команды nginx -s reload.

Далее переменную \$geoip2_data_country_code можно использовать в любом месте конфигурации так же, как встроенные переменные Nginx вроде \$remote_addr или \$http_user_agent — чаще всего для построения карты «разрешено/запрещено» через директиву map, которая компактнее и производительнее, чем длинная цепочка условий if внутри самого блока server.

Практическая конфигурация: блокировка по списку стран

Наиболее аккуратный способ задать список заблокированных или разрешённых стран — директива map в http-контексте, которая один раз сопоставляет код страны с булевым значением, а затем это значение просто проверяется в нужном location или server-блоке без повторной логики.

Блокировка запросов из перечисленных стран с явным кодом ответа 403
map $geoip2_data_country_code $blocked_country {
    default     0;
    KP          1;
    CN          1;
    RU          0;
}

server {
    listen 80;
    server_name example.ru;

    if ($blocked_country) {
        return 403;
    }

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }
}

В примере выше используются двухбуквенные коды стран по стандарту ISO 3166-1 alpha-2 — их полный список легко найти в документации самого MaxMind или в справочных таблицах ISO; важно не перепутать коды похожих по звучанию стран, поскольку ошибка в коде приведёт либо к блокировке не той аудитории, либо к отсутствию блокировки вовсе без явной ошибки в логах.

Использование конструкции if внутри блока server в Nginx в общем случае считается спорной практикой из-за известных ограничений её поведения в сочетании с другими директивами, но для простой проверки одной переменной и немедленного return это один из немногих безопасных и общепринятых случаев её применения, не вызывающих побочных эффектов.

Обратная логика — не блокировать список стран, а разрешать доступ только из явно перечисленных — реализуется тем же способом с обратной default-веткой карты: default 1 (запретить всё) и явное перечисление разрешённых кодов стран со значением 0, что удобнее, когда легитимная аудитория сайта ограничена одним-двумя регионами.

GeoIP-блокировка — это не защита, а грубый инструмент управления трафиком

Здесь необходима максимально прямая оговорка: определение страны по IP-адресу опирается исключительно на то, какому регистратору формально принадлежит диапазон адресов, — и это никак не связано с реальным физическим местоположением человека за экраном или с его добрыми или злыми намерениями. Любой платный или бесплатный VPN-сервис, прокси-сервер или Tor с выходным узлом в разрешённой стране полностью и мгновенно обходит любую GeoIP-блокировку без каких-либо специальных знаний со стороны пользователя.

Блокировка по геолокации IP-адреса — это фильтр для фонового шума, а не замок для входной двери; воспринимать её как средство защиты от целенаправленной атаки — категорическая ошибка проектирования безопасности.

Общий принцип из практики настройки периметровой фильтрации трафика

Практический вывод из этого прост: GeoIP-блокировку разумно применять для снижения объёма фонового паразитного трафика и нагрузки от массовых automated-сканеров, которые не утруждают себя обходом через VPN просто потому, что атакуют миллионы случайных адресов подряд без разбора, а не конкретно ваш сайт. Но опираться на неё как на единственную меру защиты от целенаправленной атаки или как на юридически надёжный барьер для доступа к чувствительному контенту нельзя — для настоящей защиты периметра нужен полноценный файрвол и актуальные обновления самого приложения.

Стоит также заранее принять компромисс, неизбежный при использовании этого метода: часть легитимных посетителей из разрешённой страны, пользующихся VPN с выходом за рубежом по личным причинам (приватность, обход геоблокировок других сервисов, корпоративная политика удалённой работы), будут ошибочно заблокированы, хотя географически физически находятся именно там, где сайт готов их принять. Обратная ситуация тоже возможна: житель заблокированной страны, случайно оказавшийся за VPN с выходом в разрешённом регионе, получит доступ, который формально должен был быть закрыт.

GeoIP за CDN или прокси: важность правильного определения реального IP

Отдельная и часто упускаемая деталь — если перед сайтом уже стоит CDN, балансировщик нагрузки или другой обратный прокси, то Nginx на конечном сервере по умолчанию видит в качестве \$remote_addr не настоящий IP-адрес посетителя, а IP-адрес самого прокси-сервера. В такой конфигурации GeoIP-модуль будет определять страну прокси или CDN-узла, а не реальную страну пользователя, что делает всю фильтрацию бессмысленной без дополнительной настройки.

Настройка модуля ngx_http_realip_module для восстановления реального IP посетителя за CDN
set_real_ip_from 173.245.48.0/20;
set_real_ip_from 103.21.244.0/22;
real_ip_header X-Forwarded-For;
real_ip_recursive on;

Модуль ngx_http_realip_module решает эту проблему, извлекая настоящий IP-адрес клиента из заголовка X-Forwarded-For или CF-Connecting-IP (в случае Cloudflare), присланного доверенным прокси, и подставляя его в \$remote_addr для всех последующих директив, включая GeoIP2. Диапазоны IP-адресов, из которых разрешено доверять этому заголовку (set_real_ip_from), обязательно должны быть ограничены реальными адресами используемого CDN или балансировщика — иначе любой посетитель сможет подделать заголовок X-Forwarded-For напрямую и обмануть не только GeoIP-фильтрацию, но и любые другие механизмы, опирающиеся на реальный IP-адрес, включая rate limiting и системы защиты от брутфорса.

Модуль geoip2 также умеет извлекать не только код страны, но и более детальные данные при использовании базы GeoLite2-City — например, код региона или название города, что может быть полезно для более тонкой сегментации трафика, чем простое деление по странам, хотя точность определения на уровне города заметно ниже, чем на уровне страны, из-за особенностей регистрации адресных блоков.

Актуальность базы данных: почему обновление — не разовая задача

Диапазоны IP-адресов не закреплены за странами навечно — региональные интернет-регистратуры (RIPE, ARIN, APNIC и другие) регулярно перераспределяют блоки адресов между провайдерами, а провайдеры, в свою очередь, могут передавать выделенные им диапазоны от одного юридического лица к другому, в том числе между разными странами при слияниях и поглощениях бизнеса.

Устаревшая база данных постепенно накапливает всё больше ошибок классификации: диапазон, ранее принадлежавший провайдеру в одной стране, спустя месяцы может обслуживать клиентов совершенно другого региона, а блокировка или разрешение, настроенные по старым данным, начнут работать не так, как задумывалось изначально, без каких-либо явных признаков поломки в логах ошибок.

MaxMind обновляет саму базу GeoLite2 еженедельно, и разумная практика — настроить автоматическое скачивание свежей версии через cron с той же периодичностью, не полагаясь на разовое скачивание при первоначальной настройке сервера.

Задача cron для еженедельного обновления базы GeoLite2 по средам в 4 утра
0 4 * * 3 /usr/bin/geoipupdate -f /etc/GeoIP.conf -d /usr/share/GeoIP/ >> /var/log/geoipupdate.log 2>&1

В сочетании с параметром auto_reload в конфигурации Nginx, рассмотренным выше, эта задача cron полностью автоматизирует поддержание базы в актуальном состоянии без единого ручного вмешательства администратора после первоначальной настройки.

Логирование и диагностика: как проверить, что фильтрация действительно работает

Прежде чем полагаться на GeoIP-блокировку в продакшене, стоит убедиться, что переменная страны действительно определяется корректно для тестовых запросов, — проще всего добавить её значение во временный расширенный формат access-лога Nginx и проверить реальные значения по логам за несколько минут работы.

Временный формат лога с выводом определённой страны для каждого запроса
log_format geoip_debug '$remote_addr [$geoip2_data_country_code] "$request" $status';
access_log /var/log/nginx/geoip_debug.log geoip_debug;

Если для части запросов в логе появляется пустое значение вместо кода страны, это обычно означает, что IP-адрес отсутствует в базе данных — такое бывает с недавно выделенными блоками, ещё не попавшими в текущую версию GeoLite2, или с локальными и служебными адресами вроде 127.0.0.1 и адресов из частных диапазонов, для которых географическая привязка в принципе не определена.

Для проверки конкретного правила блокировки без риска заблокировать себя самого удобно временно тестировать конфигурацию через curl с явной подменой заголовка или через любой публичный VPN с выходом в тестируемой стране, а не редактировать список заблокированных стран методом проб и ошибок прямо на продакшен-сервере.

Комбинирование с другими механизмами защиты

GeoIP-фильтрация раскрывает свой практический потенциал не как самостоятельная мера, а в сочетании с другими механизмами Nginx и системы в целом. Например, для стран с высокой долей паразитного трафика разумно не блокировать доступ полностью, а применять более строгий rate limiting, снижая допустимую частоту запросов вместо полного запрета — это мягче для случайных легитимных посетителей, но всё ещё ощутимо снижает нагрузку от массовых ботов.

Более мягкий вариант: ограничение частоты запросов вместо полной блокировки для трафика из отдельных стран
limit_req_zone $binary_remote_addr zone=strict:10m rate=2r/s;

server {
    if ($blocked_country) {
        limit_req zone=strict burst=3 nodelay;
    }
}

Ещё один практический сценарий — не блокировать доступ к сайту целиком, а ограничивать по географии только определённые чувствительные разделы: страницу входа в административную панель, форму регистрации или API, которые чаще всего становятся целью автоматизированных атак, оставляя основной контент сайта доступным для всех без ограничений.

Полноценная защита от направленных атак строится на других уровнях — файрволе, ограничивающем доступ к служебным портам по IP, актуальных обновлениях CMS и её плагинов, а также инструментах вроде Fail2ban, блокирующих конкретный IP-адрес после нескольких неудачных попыток входа независимо от того, из какой страны он пришёл. GeoIP-блокировка в этой системе — лишь один из многих слоёв, снижающий фоновый шум, но не заменяющий остальные.

Чек-лист внедрения GeoIP-фильтрации

Шаг 1. Определите реальную географию легитимной аудитории сайта на основе аналитики посещаемости, а не предположений — блокировка страны с неожиданно активной, но легитимной аудиторией обернётся прямой потерей посетителей и заказов.

Шаг 2. Установите модуль ngx_http_geoip2_module и скачайте базу GeoLite2 с бесплатным лицензионным ключом MaxMind.

Шаг 3. Настройте директиву map с явным списком кодов стран и подключите переменную результата в нужных server- или location-блоках.

Шаг 4. Протестируйте конфигурацию на нескольких реальных IP-адресах из разных стран через временный отладочный лог, прежде чем полагаться на неё в продакшене.

Шаг 5. Настройте автоматическое еженедельное обновление базы через cron и параметр auto_reload в конфигурации Nginx, чтобы фильтрация не работала по устаревшим данным месяцами.

Шаг 6. Рассматривайте GeoIP-блокировку как дополнение к файрволу и другим мерам защиты, а не как их замену, и не полагайтесь на неё как на единственный барьер для критичных разделов сайта.

Итог: полезный, но ограниченный по природе инструмент

GeoIP-блокировка в Nginx — простой в настройке и практически бесплатный по нагрузке способ снизить объём паразитного трафика и фонового шума в логах от массовых автоматизированных атак, идущих из регионов без реальной аудитории конкретного сайта. Настраивается она буквально за несколько строк конфигурации при уже установленном модуле и загруженной базе данных.

При этом важно трезво понимать её пределы: это грубый фильтр по формальной регистрации IP-адреса, а не проверка личности или намерений посетителя, и он тривиально обходится любым VPN или прокси-сервером. Использовать GeoIP-блокировку стоит как один из многих слоёв защиты трафика, обязательно в сочетании с полноценным файрволом, регулярными обновлениями CMS и мониторингом логов на подозрительную активность.

Если нужна помощь с настройкой Nginx под конкретные требования проекта — от географической фильтрации до полноценной защиты от DDoS и грамотного rate limiting, — можно подобрать VPS с нужными ресурсами в конфигураторе и обсудить конкретную конфигурацию сервера со специалистами.

почему мы

Почему стоит выбрать нас

Быстрый запуск

Подберём конфигурацию и развернём проект в день обращения.

Надёжность

NVMe-диски, защита от DDoS и резервные копии по расписанию.

Поддержка 24/7

Дежурные инженеры на связи в любое время суток.

Настройка под ключ

Установим CMS, настроим веб-сервер, SSL и почту за вас.

Перенос без простоя

Аккуратно перенесём сайт и базу данных на новый сервер.

Прозрачные цены

Актуальные тарифы и честный подбор без навязывания.

частые вопросы

Вопросы и ответы

Заменяет ли GeoIP-блокировка полноценный файрвол?

Нет, ни в коем случае — это фильтрация на уровне HTTP по географическому признаку IP-адреса, тогда как файрвол вроде UFW или iptables работает на уровне сети и защищает от совершенно другого класса угроз; их стоит использовать вместе, а не как замену друг другу.

Можно ли обойти GeoIP-блокировку через VPN?

Да, легко — любой VPN-сервис или прокси, физически расположенный в разрешённой стране, покажет системе именно тот IP-адрес, который она считает легитимным, полностью нейтрализуя блокировку по географии без каких-либо технических сложностей.

Как часто нужно обновлять базу GeoLite2?

MaxMind обновляет свою базу еженедельно, поскольку блоки IP-адресов регулярно перераспределяются между странами и провайдерами; для актуальности данных разумно настраивать автоматическое обновление базы не реже одного раза в неделю через cron.

Бесплатна ли база GeoLite2 от MaxMind?

Да, версия GeoLite2 бесплатна для скачивания после бесплатной регистрации на сайте MaxMind и получения лицензионного ключа, но по точности она немного уступает платной версии GeoIP2 той же компании.

Что произойдёт с легитимным посетителем из заблокированной страны, использующим VPN с выходом в разрешённой стране?

Он получит доступ к сайту как обычно, поскольку с точки зрения сервера его запрос пришёл из разрешённой страны — это иллюстрирует и слабость метода как средства защиты, и его относительную мягкость как инструмента ограничения по сравнению с полной блокировкой на уровне сети.

Стоит ли использовать GeoIP-блокировку для интернет-магазина, доставляющего товары только по России?

Это разумный сценарий: если у сайта объективно нет легитимной аудитории за пределами определённых стран, а основная доля паразитного трафика и попыток эксплуатации уязвимостей идёт именно из-за рубежа, ограничение по географии снижает фоновый шум в логах и нагрузку на сервер от automated-сканеров.

Влияет ли GeoIP-модуль на производительность Nginx?

Влияние минимально — поиск страны по IP-адресу в базе MaxMind реализован через быструю бинарную структуру данных и занимает микросекунды на запрос, что несопоставимо мало по сравнению с временем генерации самой страницы на стороне PHP или базы данных.

Как оплачивать услуги?

Оплата помесячная, для облачных серверов доступна почасовая тарификация. Принимаются карты, банковские переводы и электронные кошельки.

Есть ли круглосуточная поддержка?

Да, дежурные инженеры на связи 24/7.

Выдаёте ли закрывающие документы?

Да, предоставим необходимые документы для оплаты.

Как оставить заявку?

Заполните форму на странице или нажмите «Заказать» — мы свяжемся и поможем с подбором.

заявка

Оставьте заявку

Ответим и поможем с подбором и настройкой.