Назад | Перейти на главную страницу

Nginx: Оптимальный map_hash_max_size и map_hash_bucket_size для 1M карты?

У меня есть 1M статических правил перезаписи и я использую эта конфигурация карты. Как определить оптимальные значения для map_hash_max_size и map_hash_bucket_size? Хочу оптимизировать по потреблению памяти. В документация очень минимально об этом.

Кто-нибудь еще спросил это на форуме Nginx, но без ответа.

Я сделал анализ исходного кода для server_names_hash_bucket_size и server_names_hash_max_size, Я думаю, он использует тот же хеш, что и карта.

Вот обобщенная копия моей ответ:

  • Общая рекомендация - сохранить оба значения как можно меньшими.
  • Если nginx жалуется на увеличение max_size сначала пока жалуется. Если число превышает какое-то большое число (например, 32769), увеличьте bucket_size до кратного значения по умолчанию на вашей платформе, пока он жалуется. Если больше не жалуется, уменьшите max_size назад пока не жалуется. Теперь у вас есть лучшая настройка для вашего набора ключей (для каждого набора ключей может потребоваться другая настройка).
  • Больше max_size означает больше потребляемой памяти (один раз на рабочий или сервер, прокомментируйте, если знаете).
  • Больше bucket_size означает больше циклов ЦП (для каждого поиска ключа) и больше передач из основной памяти в кеш.
  • max_size не связан напрямую с количеством ключей, если количество ключей удваивается, возможно, вам придется увеличить max_size 10 раз и даже больше, чтобы избежать столкновений. Если вы не можете их избежать, вам нужно увеличить bucket_size.
  • bucket_size считается, что увеличивается до следующей степени двойки, исходя из исходного кода, я бы решил, что этого должно быть достаточно, чтобы сделать его кратным значению по умолчанию, это должно поддерживать оптимальные переводы в кеш.
  • Размер bucket_size зависит от длины ваших ключей. Если средний размер ключа составляет 32 байта (с накладными расходами хэш-массива), увеличение bucket_size до 512 байт означало бы, что он может вместить 16 ключей с конфликтующим хеш-ключом. Это не то, что вам нужно, если произойдет столкновение он ищет линейно. Вы хотите, чтобы столкновений было как можно меньше.
  • Если у вас есть max_size менее 10000 и маленький bucket_size, вы можете столкнуться с длительным временем загрузки, потому что nginx будет пытаться найти оптимальный размер хэша в цикле.
  • Если у вас есть max_size больше 10000, будет выполнено "только" 1000 циклов, прежде чем он будет жаловаться.

Документация nginx по хешу и размер ведра ужасно расплывчато. Эти числа выражены в байтах? Записи?

У меня 128 592 байта файл карты с 1351 записями. Минимальные значения, подходящие для этого случая:

map_hash_bucket_size 128;
map_hash_max_size 45948;

Я не знаю, как связаны эти числа. Я пришел к ним, увеличив размер ведра до 128, а затем выполнив двоичный поиск максимального размера.