Message Logger: hidden messages on the server, removed chats, old chat photos
Publish plugin / publish (push) Successful in 6s

- Hidden deleted messages are marked on the server (local marks migrated);
  "Reveal hidden messages" in the chat menu, Unhide in the message menu and
  the selection bar.
- Chats an account lost are reported, listed among its chats again and
  opened read-only with their logged messages, all deleted.
- Logged chat photos: a removed chat's avatar, and in a chat's photos the
  ones it no longer has, translucent with a trash icon in the viewer's
  previews.
- Fix: the deleted-post comments thread is answered locally again.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
lyuksovannyyandClaude Opus 5.5 committed 2026-10-10 23:12:33 +02:00
1 parent 0176f7099d
commit 362b358d8d
15 files changed
+1821 -125

No files matched your search

+67
View File
@@ -152,3 +152,70 @@ class Api:
for _token, result in self._each("POST", "/deletions", json=body):
marked += int((result or {}).get("marked", 0))
return marked
def hidden(self, account_id, chat_id, message_ids, hidden):
"""Hide messages from the chat for every client (or show them again);
True once every master took it."""
ids = sorted(set(int(i) for i in message_ids))
for start in range(0, len(ids), 500):
body = {
"account_id": account_id,
"chat_id": chat_id,
"message_ids": ids[start : start + 500],
"hidden": bool(hidden),
}
for _token, _result in self._each("POST", "/hidden", json=body):
pass
return True
# removed chats
def chat_removed(self, account_id, chat_id, own):
body = {"account_id": account_id, "chat_id": chat_id, "own": bool(own)}
known = False
for _token, result in self._each("POST", "/chats/removed", json=body):
known = known or bool((result or {}).get("known"))
return known
def chat_hidden(self, account_id, chat_id, hidden):
body = {"account_id": account_id, "chat_id": chat_id, "hidden": bool(hidden)}
for _token, _result in self._each("POST", "/chats/hidden", json=body):
pass
def removed_chats(self, account_id):
"""The account's removed chats, each master's answer merged (the
first one listing a chat wins), or None when no master answered."""
chats, any_result = {}, False
for _token, result in self._each(
"GET", "/chats/removed", params={"account_id": account_id}
):
if result is None:
continue
any_result = True
for chat in result.get("chats") or []:
chat["master_tg_id"] = result.get("master_tg_id")
chats.setdefault(int(chat["chat_id"]), chat)
return list(chats.values()) if any_result else None
def history(self, account_id, chat_id, before=0, limit=100):
"""Logged messages of a chat older than `before`, newest first: the
first master that has any."""
params = {"account_id": account_id, "before": int(before), "limit": int(limit)}
for _token, result in self._each(
"GET", f"/chats/{chat_id}/history", params=params
):
if result and result.get("messages"):
return result
return None
def avatars(self, account_id, chat_id):
"""Chat photos logged for a chat, newest first, every master's."""
out = []
for _token, result in self._each(
"GET", f"/chats/{chat_id}/avatars", params={"account_id": account_id}
):
for avatar in (result or {}).get("avatars") or []:
avatar["master_tg_id"] = (result or {}).get("master_tg_id")
out.append(avatar)
out.sort(key=lambda a: a.get("date") or "", reverse=True)
return out