По сути, вам нужно взглянуть на свою системную память, в частности на память Postgres, двумя способами.
Во-первых, это память, необходимая для запуска приложений. По сути, это статическая нагрузка на память для всех приложений, пока они работают. Если вам не хватает памяти при желаемой загрузке, значит, вам не хватает памяти. Современные системы могут использовать своп во времена «кризиса», но это все. Проще говоря, если вы используете своп, у вас возникает кризис памяти, и вы должны надеяться, что он скоро исчезнет.
Как только у вас есть базовая память, необходимая для приложений, вся оставшаяся системная память в основном выделяется для дискового кэша.
В системе, в которой размещен Postgres, у вас есть два вида дискового кэша. У вас есть кеш файловой системы ядра, и у вас есть внутренний кеш Postgres.
Внутренний кеш Postgres не будет выпущен. Это не так, как это работает. Вы сказали в своей конфигурации, что он может использовать XXX объем ОЗУ для своих целей, и он сохранит его. В этом состоянии Postgres не заботится о том, что еще находится в системе.
Если кеш был кешем ядра, и у вас был какой-то внезапный всплеск активности файловой системы, а не Postgres, то ядро будет кешировать последние страницы и очищать старые страницы. Кеш ядра увидит всю систему, а Postgres увидит только активность БД.
Зв
В мировоззрении Postgres кеш ядра конкурирует с буферным кешем. Рассмотрим этот сценарий. Постгрес просит блок диска. Ядро захватывает этот блок и кэширует его. В то же время Postgres захватывает этот блок из ядра, а также кэширует его. Теперь этот блок избыточно кэшируется. Если ядро найдет лучшее применение для этого блока кеш-памяти, оно выгрузит его из блока Postgres и загрузит новый. Тем временем Postgres сохранит этот блок во внутреннем кеше.
Если у вас есть выделенная машина Postgres, мало причин иметь большой объем кеша ядра. Поскольку весь дисковый ввод-вывод будет входным / выходным Postgres, кеш ядра избыточен и менее эффективен, чем кеш Postgres. Когда Postgres кэширует блок, он должен упорядочить байты, обновить свои внутренние структуры и все остальное, что он делает. После кэширования он больше не должен ничего делать. Таким образом, блок, кэшируемый Postgres, более эффективен, чем тот же блок, кэшируемый ядром, поскольку при переносе блока из кэша ядра в Postgres есть определенные затраты.
Однако, если у вас машина смешанного использования, то кешам ядра и Postges придется бороться с ней. Если у вас достаточно небольшая БД, которая вписывает большую часть ежедневных рабочих данных в ОЗУ, то у вас должно быть достаточно буферного пространства для обработки этого в Postgres, чтобы большая часть его операций выполнялась из памяти. Таким образом, Postgres один раз загрузит свои обычные, «занятые» страницы и кеширует их, а затем никогда не запрашивает их у ядра. Как только это будет сделано, ядро может использовать свой буферный кеш для обработки всех вспомогательных системных запросов.
С другой стороны, вы предоставляете Postgres очень мало выделенного буферного кеша, и он полагается исключительно на кеш ядра. Таким образом, каждый блок немного дороже, каждый раз приходя из кеша ядра, но гораздо дешевле, чем каждый раз читать его с диска. Таким образом, ядро может судить, какие процессы более достойны внимания кеша.
На практике определитесь с хорошим рабочим, устойчивым состоянием для Postgres и оставьте все как есть. Любые всплески активности (скажем, сканирование больших таблиц для отчета или чего-либо еще) будут смягчены кэшем ядра, и когда этот всплеск закончится, ядро сможет восстановить эту память для других целей.
Итак, суть в том, что Postgres не собирается возвращать память. Дайте столько, сколько вы можете посвятить этому.