Двадцатая страница списка открывается мгновенно, а двухтысячная — четыре секунды
Пагинация в списке реализована через смещение:
SELECT id, title, created_at
FROM documents
ORDER BY created_at DESC, id DESC
LIMIT 20 OFFSET 40000;
Индекс по (created_at DESC, id DESC) есть. Первые страницы отдаются за десятки миллисекунд, глубокие — за секунды.
Почему так и что делать?
- Индекс перестаёт работать после первых страниц, его нужно перестроить командой REINDEX
- Причина в сортировке: без ORDER BY то же самое смещение отработало бы за миллисекунды
- База читает и отбрасывает все строки до смещения; нужна пагинация по ключу-курсору
- Помогает только кэширование каждой страницы результата в Redis на несколько минут
