Системный каталог, или просто каталог — это таблицы, в которых PostgreSQL хранит информацию обо всех остальных объектах, хранящихся в базе данных. К ним относятся таблицы, функции, триггеры, и т.д. Обращение к системному каталогу происходит часто, поэтому для него предусмотрен кэш. Давайте же разберемся, как этот кэш устроен.
Мне захотелось попробовать разные программы для Микроши. В наши дни они распространяются в виде файлов RKM. Существуют готовые конвертеры из RKM в аудио, но они имеют различные проблемы. Например, WRKWIN32.EXE как будто работает, но мой Микроша отказывается загружать результирующее аудио. То ли не та версия Wine, то ли не та звуковая карта — об истинной причине остается лишь гадать. В общем, долго ли, коротко ли, было решено написать свой конвертер.
Карта свободного пространства, она же free space map или FSM — это структура в PostgreSQL, предназначенная для быстрого поиска страницы c заданным количеством свободного места. Без FSM при записи новых данных СУБД приходилось бы сканировать всю кучу, либо записывать данные в ее конец.
Ранее в постах серии «Внутренности PostgreSQL» несколько раз упоминалось нечто под названием visibility map, или карта видимости (случай один, случай два и далее по ссылкам). Однако не сообщалось, что это за штука такая и почему она важна. Пришло время заполнить данный пробел.
Благодаря посту Внутренности PostgreSQL: ProcArray и CLOG мы узнали, как PostgreSQL определяет состояние транзакции по ее идентификатору, или XID. Однако из статьи Внутренности PostgreSQL: страницы и кортежи мы также помним, что XID является 32-х битным числом. Несложными математическими расчетами несложно понять, что даже при скромных нагрузках (~1000 TPS), уникальные XID’ы могут закончится за несколько месяцев. Давайте разберемся, как PostgreSQL решает эту проблему.
PostgreSQL хранит данные в страницах, а страницы кэшируются в разделяемых буферах. Казалось бы, в случае аварийной остановки грязные страницы не будут записаны на диск, и часть данных пропадет. Чтобы такого не происходило, СУБД пишет журнал предзаписи, он же Write Ahead Log, или WAL.
Ранее мы установили (часть один, часть два) что PostgreSQL хранит все данные в страницах, размер которых по умолчанию равен 8 Кб. Однако напрямую читать и писать страницы с/на диск было бы дороговато. Поэтому используется кэш в разделяемой памяти. Он называется разделяемые буферы, или shared buffers. Попробуем разобраться, как именно устроен этот кэш.
Благодаря статье Внутренности PostgreSQL: страницы и кортежи мы узнали, что каждый кортеж в PostgreSQL хранит t_xmin и t_xmax — XIDы транзакций создавшей и удалившей кортеж соответственно. Зная XID текущей транзакции, ее уровень изоляции, а также состояние транзакций t_xmin и t_xmax, СУБД способна определить, виден ли кортеж в текущей транзакции или нет. Узнать состояние транзакции по ее XID можно при помощи ProcArray и CLOG.
Ранее мы разобрались, как PostgreSQL хранит страницы на диске, и как можно посмотреть их содержимое при помощи pageinspect. Но возникает вот какой вопрос. Если размер страницы составляет несколько килобайт, и кортежи не могут занимать несколько страниц, то как СУБД хранит атрибуты с типом TEXT
? Ведь строки явно могут быть длиннее пары тысяч символов. Это возможно благодаря штуке под названием The Oversized-Attribute Storage Technique, или сокращенно TOAST.
Недавно мы научились напрямую работать с таблицами PostgreSQL из расширений на C. Предлагаю капнуть чуть глубже и разобраться, как PostgreSQL физически хранит данные на диске. Стоит сказать, что представленный материал не претендует на новизну. Вопрос этот хорошо описан в более чем в одном источнике, не исключая официальной документации на PostgreSQL. Однако мне хотелось бы иметь собственную шпаргалку, акцентирующую внимание на наиболее интересных мне лично моментах.