---
name: antidup_window_larger_than_pool
description: "Бан-лист «не повторять» больше самого пула = вечное исчерпание, и фолбэк `pool = fresh or ВЕСЬ_СПИСОК` превращает ротацию в чистый рандом"
metadata: 
  node_type: memory
  type: feedback
  originSessionId: 0a7ddf2b-508e-45e8-9db2-bfeb94cae09b
  modified: 2026-08-06T13:07:11.081Z
---

Если антидубль-окно (сколько последних выдач помним) **больше пула вариантов**, то состояние «свежих не осталось» — не редкий край, а **постоянный режим работы**. Любой фолбэк вида `pool = fresh or ПОЛНЫЙ_СПИСОК` + `random.choice(pool)` в этот момент перестаёт быть страховкой и становится основным путём: ротация вырождается в рандом с повторами подряд.

**Why:** в CebersPost (`ideas.py`) окно было 30 сидов при пулах 7–16 тем. У самой частой рубрики «ликбез» замер дал **0 свежих из 16** — то есть КАЖДАЯ выдача шла через рандом. Симуляция 40 подряд: 18 повторов раньше круга, **минимальный разрыв 1** (одна тема два поста подряд). Юзер это видел как «рассказывает про то, что уже рассказывал, редко что-то новое» — и жаловался на дедуп, хотя дедуп текстов был ни при чём: ломался **выбор темы ДО генерации**.

**How to apply:**
- Чинить не порогом дедупа, а **LRU**: пул исчерпан → отдать САМУЮ ДАВНЮЮ по использованию, а не случайную. Это превращает исчерпанный пул в строгий круг (мин. разрыв = размер пула). Список «недавних» обычно приходит `ORDER BY id DESC`, т.е. свежие первыми — индекс в нём и есть свежесть.
- **Мерить, а не гадать:** посчитать `len(fresh)` для каждого пула на живой БД + симуляция N подряд выдач со сравнением старое/новое (минимальный разрыв, повторы раньше круга). Без этого «ротация вроде есть» выглядит рабочей.
- LRU гарантирует разрыв, но **длину круга задаёт только размер пула** — расширять пул тоже нужно.
- Смотреть на такие же ротации в других проектах: [[vakhunter_overview]], [[delor_sport_tg_grounding]], [[investpilot_overview]].

Родственное: [[ceberspost_overview]], [[ceberspost_llm_nvidia]].
