Войдите или зарегистрируйтесь
Вы сможете писать комментарии и посты, ставить лайки и другое
Поиск
Тёмная тема

Посты по тегу: PostgreSQL

Пагинация курсором в PostgreSQL: не путайте реальный CURSOR и фейковый курсор из WHERE

11 дн. назад
На любом собесе по system design и хайлоаду вас наверняка спросят про пагинацию. И вопрос этот с подвохом, т.к. на хайлоаде БД очень большие, с миллионами записей. Например, спросят как сделать бесконечную ленту последних постов с подгрузкой. И тут главное не обос****ться как я сделал на своем собесе 😂

Итак, что мы знаем про курсоры? В PostgreSQL есть самые настоящие курсосы! Они так и называются CURSOR. В постгресе они работают только внутри транзакций.
BEGIN;
DECLARE zhopa_cursor CURSOR FOR
  SELECT id, title, created_at FROM posts;

-- Получаем 10 строк:
FETCH 10 FROM zhopa_cursor;

-- Получаем еще следующие 10 строк сразу после места, где остановились до этого:
FETCH 10 FROM zhopa_cursor;

CLOSE zhopa_cursor;
COMMIT;

Обратите внимание, что обязательны транзакция и конкретное имя для курсора. Можно ли это использовать в вебе? Нет. Но я на собесе начал заливать про эти курсоры постгреса и про хранение имен курсоров, хотя непонятно как это все реализовать для веба. Типа не закрывать некоторое время транзакцию и держать открытой некоторое время пока идут http запросы? 😂

Короче, в веб разработке есть так называемые курсоры, которые никакими курсорами на самом деле не являются. Это обычные WHERE условия в SQL! Но за каким-то х***м это называется курсором.

Вот SQL получения первого списка постов для ленты:

SELECT id, title, created_at
FROM posts
ORDER BY created_at DESC, id DESC
LIMIT 20;

Далее браузер в http запросе для получения следующих 20 постов передает payload:

"last_created_at": "2026-01-15 12:30:00+00",
"last_id": 12345,

И бэк делает SQL запрос:

SELECT id, title, created_at
FROM posts
WHERE (created_at, id) < ($1, $2)
ORDER BY created_at DESC, id DESC
LIMIT 20;

Вот эта строка:
WHERE (created_at, id) < ($1, $2)
это и есть как бы наш курсор, хотя нифига это не курсор.

Такой запрос с псевдо-курсором намного быстрее, чем юзанье OFFSET когда постгрес читает все подходящие записи в таблице и тут же скипает часть их.
Показать полностью...
+2
7

Как я сражался на сервере с вирусом-криптомайнером, маскирующимся под PostgreSQL

1 г. назад
Целая детективная история разыгралась на моём сервере.

Дано: небольшой арендуемый у хостера сервер с Debian 12 и последней PostgreSQL 16. Постгрес стоит без всяких докеров.

Месяц назад начал тормозить сервак. Думаю, что за ерунда, захожу по SSH, ввожу:
top
и вверху поверх всякой мелочи вижу это:
 PID USER      PR  NI    VIRT    RES    SHR S  %CPU  %MEM     TIME+ COMMAND
2251 postgres  20   0 2445140   2,3g      4 S 400,7  14,7   6:20.66 kswapd0
Жрёт все ресурсы, процессор загружен полностью.
Зарождается слабая мысль о криптомайнерах, но пока не понимаю, как вирус проник на сервер. Пароль у рута сложный, да и тут про постгрес написано.

В общем, думаю - ну, заглючил PostgreSQL, наверное. Убиваю процесс и перезагружаю сервак (это всегда полезно):
kill 2251
reboot
Захожу по SSH снова - чисто. Ну, думаю, всё ок.

Потом опять тормоза через некоторое время. Смотрю - эта хрень опять запущена. И странно как-то всё, причём тут юзер postgres?

Полез гуглить. Про этот kswapd и нагрузку на проц много разрозненных сообщений. Народ про него пишет и 2013, и в 2017, а у меня вообще-то 2024 на дворе, а ведь в те годы не было ещё криптовалют.
Может это не криптомайнер, а что-то другое?
Пытаюсь понять, кто запускает процесс. Делаю:
ls -l /proc/2251/exe
выводит:
lrwxrwxrwx 1 postgres postgres 0 июл 23 13:12 /proc/2251/exe -> /var/lib/postgresql/.configrc5/a/kswapd0
Такс... Находится в каталоге postgresql. А вдруг это важная часть сервера базы данных? Названо ведь так "по-умному" - configrc5.

Решаю просто переименовать каталог:
kill 2251
cd /var/lib/postgresql
mv .configrc5 _renamed_.configrc5
reboot
После этого всё хорошо... но только пару недель :)

Через эти пару недель опять веселуха с загрузкой всех ядер процессора.
Смотрю - каталог снова создан. Значит точно криптовалютный вирус. Но как зараза проникла на сервер?

Наконец-то до моей глупой головы дошло посмотреть логи SSH:
journalctl -t sshd
Опытные линуксоиды знают, что так смотреть не имеет смысла. Там толпы кул-хацкеров пытаются подключиться к серверу, но обламываются.
Фильтрую только логи успешного входа по SSH:
journalctl -t sshd --since "2024-08-01" --until "2024-08-16 10:00:00" | grep "Accepted "
И там среди моих заходов вижу эту падлюку:
Jul 06 11:40:07 debian sshd[589266]: Accepted password for postgres from 103.94.113.2 port 33482 ssh2
Jul 10 08:18:00 debian sshd[723300]: Accepted publickey for postgres from 162.217.64.26 port 60366 ssh2: RSA SHA256:MkYY9qiVsFGBC5WkjoClCkwEFW5iSjcGQF7m4n4H7Cw
Aug 02 07:45:44 debian sshd[258599]: Accepted publickey for postgres from 206.189.36.236 port 47140 ssh2: RSA SHA256:MkYY9qiVsFGBC5WkjoClCkwEFW5iSjcGQF7m4n4H7Cw
Aug 02 07:50:53 debian sshd[258915]: Accepted publickey for postgres from 157.245.42.37 port 50478 ssh2: RSA SHA256:MkYY9qiVsFGBC5WkjoClCkwEFW5iSjcGQF7m4n4H7Cw
Aug 14 10:23:08 debian sshd[99132]: Accepted publickey for postgres from 82.165.79.77 port 40086 ssh2: RSA SHA256:MkYY9qiVsFGBC5WkjoClCkwEFW5iSjcGQF7m4n4H7Cw
Aug 14 10:47:37 debian sshd[99723]: Accepted publickey for postgres from 103.146.52.138 port 55110 ssh2: RSA SHA256:MkYY9qiVsFGBC5WkjoClCkwEFW5iSjcGQF7m4n4H7Cw
Ёлы-палы! Сначала чувак вошёл по паролю, а потом уже входил по ключу.

Ради интереса проверил айпишники:
103.94.113.2 - India
162.217.64.26 - USA
206.189.36.236 - Singapore
103.146.52.138 - Hong Kong
Целый ботнет. Или VPN-ы. Не знаю, да и это не важно.

Начинаю вспоминать, что когда ставил PostgreSQL, создавал примитивный пароль. Или вообще не задавал его - точно не помню.

Срочно меняю пароль юзеру postgres:
passwd postgres
и ставлю запрет входа SSH для определённых юзеров:
nano /etc/ssh/sshd_config
DenyUsers postgres no-reply blah
В идеале, конечно вообще всем запретить, а оставить только для разрешённых.

Перезагружаем SSH демона:
systemctl restart sshd

Кстати, это зараза прописала SSH-ключ в:
/var/lib/postgresql/.ssh/authorized_keys
ssh-rsa AAAAB3NzaC1yc2EAAAABJQAAAQEArDp4cun2lhr4KUhBGE7VvAcwdli2a8dbnrTOrbMz1+5O73fcBOx8NVbUT0bUanUV9tJ2/9p7+vD0EpZ3Tz/+0kX34uAx1RV/75GVOmNx+9EuWOnvNoaJe0QXxziIg9eLBHpgLMuakb5+BgTFB+rKJAw9u9FSTDengvS8hX1kNFS4Mjux0hJOK8rvcEmPecjdySYMb66nylAKGwCEE6WEQHmd1mUPgHwGQ0hWCwsQk13yCGPK5w6hYp5zYkFnvlC8hGmd4Ww+u97k6pfTGTUbJk14ujvcD9iUKQTTWYYjIIu5PmUux5bsZ0R4WFwdIe6+i6rBLAsPKgAySVKPRK+oRw== mdrfckr
Разумеется это надо сразу удалять.
Показать полностью...
+3
64
1