MAX: bootstrap-история в LOGIN — клиент перестал думать что всё уже синканулось

В ответе LOGIN сервер слал messages: {} и chatMarker: 0. Десктопный
клиент в этом случае считает, что локальная история уже синхронизирована
со старого запуска, и НЕ отправляет CHAT_HISTORY (49) при открытии чата.
В окне видно только lastMessage из chats[], а вся реальная переписка —
ничерта.

- src/common/tools.py: collect_bootstrap_history(chatIds, ...) —
  собирает карту {chatId: [последние N сообщений]}, в т.ч. избранное
  под клиентским id = senderId ^ senderId.
- src/oneme/processors/auth.py: подсовываем эту карту в
  payload.messages, chatMarker = текущее время вместо 0.
This commit is contained in:
zavolo
2026-05-10 22:27:42 +03:00
parent fa0ed34adc
commit 861b75eb1c
2 changed files with 53 additions and 2 deletions

View File

@@ -429,6 +429,44 @@ class Tools:
# Возвращаем айдишки
return int(message_id), int(last_message_id), message_time
async def collect_bootstrap_history(
self, chatIds, db_pool, senderId, protocol_type="mobile", limit=50, include_favourites=True
):
"""Собирает карту {chatId: [messages...]} для bootstrap-pre-fetch в LOGIN.
Десктопный MAX в ответе LOGIN ждёт поле `messages` как карту чат→история.
Если карта пустая — клиент полагает, что у него уже есть локальная
история и НЕ запрашивает CHAT_HISTORY (49). В итоге в окне чата
видно только lastMessage из chats[].
"""
result = {}
async def _fetch(chat_db_id, key_for_client):
async with db_pool.acquire() as conn:
async with conn.cursor() as cursor:
await cursor.execute(
"SELECT * FROM `messages` WHERE chat_id = %s ORDER BY time DESC LIMIT %s",
(chat_db_id, limit),
)
rows = await cursor.fetchall()
if not rows:
return
messages = [self.build_message_dict(row, protocol_type) for row in rows]
messages.sort(key=lambda m: m["time"])
result[key_for_client] = messages
for chatId in chatIds:
await _fetch(chatId, chatId)
if include_favourites:
# Избранное: в БД хранится как chat_id = -senderId,
# но клиенту отдаётся под id = senderId ^ senderId (= 0)
await _fetch(-senderId, senderId ^ senderId)
return result
async def get_last_message(self, chatId, db_pool, protocol_type="mobile"):
"""Получение последнего сообщения в чате"""
async with db_pool.acquire() as db_connection: