Ограничение скорости Nginx для всей подсети, а не только для каждого IP-адреса

У меня есть определенная зона в Nginx для ограничения запросов, это просто, как описано в их документации:

limit_req_zone $ binary_remote_addr zone = привязь: скорость 10м = 18р / с;

Все идет нормально.

Он отлично работает с клиентами, которые действуют оскорбительно, но в последнее время некоторые из них начали ротацию своих IP-адресов при доступе к моей службе, в основном в диапазоне / 24, поэтому мне было интересно, можно ли применить ограничение количества подключений зоны ко всему IP диапазон (не только на IP), что-то вроде флага --connlimit-mask 24 будет работать с iptables ...?


person Istvan Prosinger    schedule 24.04.2018    source источник


Ответы (2)


Самый простой способ - это комбинация nginx директив map и geo, которые также дадут вам максимальную гибкость, ИМХО.

geo $geoRateBlacklist {
    default        0;
    192.0.0.0/24   1;
    10.0.0.0/24    1;
    172.0.0.0/24   1;
}

map $geoRateBlacklist $rateBlacklist {
    1              $binary_remote_addr;
    0              "";
}

limit_req_zone $rateBlacklist zone=leash:10m rate=18r/s;

Быстро делается по памяти, но должно работать.

person Shawn C.    schedule 24.04.2018
comment
Спасибо за идею. Это может частично сработать. Проблема в том, что в блоке geo вы приняли входящие блоки IP как константу. Хотя на самом деле в какой-то момент он является константой, они могут его изменить, поэтому я предполагаю, что IP-блок изначально неизвестен. - person Istvan Prosinger; 26.04.2018
comment
@IstvanProsinger Мне бы очень хотелось узнать, нашли ли вы ответ на этот вопрос. - person user1265125; 25.02.2019
comment
Поправьте меня, если я ошибаюсь, но разве это не будет блокировать по IP? Блок geo создает новую переменную $ geoRateBlacklist из клиентского IP. Эта переменная будет 0 или 1. Блок карты отобразит этот 0 или 1 в новую переменную $ rateBlacklist, которая является либо $ binary_remote_addr, либо. Разве это не означает, что в тех случаях, когда эта переменная не пуста, она всегда будет эквивалентна limit_req_zone $ binary_remote_addr zone = leash: 10m rate = 18r / s, т.е. ограничение для IP, а не для подсети? - person andresp; 27.03.2019

Можно использовать директиву map с регулярным выражением для извлечения подсети для $binary_remote_addr. Например, для подсети с косой чертой 16:

map $binary_remote_addr $bin_slash16 {
"~^(?P<a>..)..$" "$a";
}

Источник: https://forum.nginx.org/read.php?2,271483,271788#msg-271788

person nwarp    schedule 01.03.2020