Compare commits

...

4 Commits

Author SHA1 Message Date
relyay cab75a58f8
Merge pull request #9 from relyay/fix
Some fixes
2026-03-10 21:19:54 +03:00
Alexey Polyakov 4bd632e6df Мелкие правки 2026-03-10 18:21:59 +03:00
WowInceptionGood 32a88e8b05 Update README 2026-03-10 13:55:50 +00:00
Anatoliy Esherkin a2d6be7b94
Добавил причины для жалоб (#4)
* Добавил причины для жалоб

* Update static.py

---------

Co-authored-by: WowInceptionGood <143893762+WowInceptionGood@users.noreply.github.com>
2026-03-10 16:37:35 +03:00
6 changed files with 53 additions and 39 deletions

1
docs/proto/oneme_tcp.md Normal file
View File

@ -0,0 +1 @@
TODO

View File

@ -1,3 +1,10 @@
> [!Caution]
>
> Проект находится на ранней стадии разработки и вероятно полон багов.
>
> Использование в профессиональных средах не рекомендовано.
# OpenMAX # OpenMAX
Эмулятор сервера MAX и ТамТам Эмулятор сервера MAX и ТамТам
@ -15,6 +22,8 @@ https://t.me/openmax_alerts
Клиент может быть практически любым, главное условие - чтобы он был совместим с официальным сервером (`api.oneme.ru` / `api.tamtam.chat`). Клиент может быть практически любым, главное условие - чтобы он был совместим с официальным сервером (`api.oneme.ru` / `api.tamtam.chat`).
На данный момент с сервером может работать последняя версия MAX (26.7.1), однако все тесты проходят на версии 26.5.0.
# Установка # Установка
1. Склонируйте репозиторий 1. Склонируйте репозиторий

View File

@ -109,7 +109,15 @@ class Static:
### Причины для жалоб ### Причины для жалоб
COMPLAIN_REASONS = [ COMPLAIN_REASONS = [
# TODO: Было бы очень замечательно заполнить этот лист причинами для жалоб "Порнография или эротика",
"Экстремизм или терроризм",
"Фейк",
"Мошенничество",
"Нарушение авторского права",
"Шокирующий контент",
"Персональные данные",
"Незаконная услуга",
"Это законно, но надо удалить"
] ]
### Заглушка для папок ### Заглушка для папок
@ -160,4 +168,4 @@ class Static:
"SAFE_MODE": False, "SAFE_MODE": False,
"M_CALL_PUSH_NOTIFICATION": "ON", "M_CALL_PUSH_NOTIFICATION": "ON",
"QUICK_REPLY": False "QUICK_REPLY": False
} }

View File

@ -102,20 +102,14 @@ class Tools:
# Выносим результат в лист # Выносим результат в лист
chats.append( chats.append(
{ self.generate_chat(
"id": row.get("id"), row.get("id"),
"type": row.get("type"), row.get("owner"),
"status": "ACTIVE", row.get("type"),
"owner": row.get("owner"), participants,
"participants": participants, message,
"lastMessage": message, messageTime
"lastEventTime": messageTime, )
"lastDelayedUpdateTime": 0,
"lastFireDelayedErrorTime": 0,
"created": 1,
"joinTime": 1,
"modified": messageTime
}
) )
# Получаем последнее сообщение из избранного # Получаем последнее сообщение из избранного
@ -123,24 +117,19 @@ class Tools:
senderId, db_pool senderId, db_pool
) )
# ID избранного
chatId = senderId ^ senderId
# Хардкодим в лист чатов избранное # Хардкодим в лист чатов избранное
chats.append( chats.append(
{ self.generate_chat(
"id": 0, chatId,
"type": "DIALOG", senderId,
"status": "ACTIVE", "DIALOG",
"owner": senderId, [senderId],
"participants": { message,
str(senderId): 0 # if not messageTime else messageTime messageTime
}, )
"lastMessage": message,
"lastEventTime": messageTime,
"lastDelayedUpdateTime": 0,
"lastFireDelayedErrorTime": 0,
"created": 1,
"joinTime": 1,
"modified": messageTime
}
) )
return chats return chats
@ -185,9 +174,11 @@ class Tools:
"time": int(row.get("time")), "time": int(row.get("time")),
"type": row.get("type"), "type": row.get("type"),
"sender": row.get("sender"), "sender": row.get("sender"),
"cid": int(row.get("cid")),
"text": row.get("text"), "text": row.get("text"),
"attaches": json.loads(row.get("attaches")), "attaches": json.loads(row.get("attaches")),
# "reactionInfo": {} "elements": json.loads(row.get("elements")),
"reactionInfo": {}
} }
# Возвращаем # Возвращаем

View File

@ -445,7 +445,7 @@ class Processors:
chatId = userId ^ senderId chatId = userId ^ senderId
# Если клиент хочет отправить сообщение в избранное, # Если клиент хочет отправить сообщение в избранное,
# то выставляем ID чата 0 # то выставляем в качестве ID чата ID отправителя
# (А ещё используем это, если клиент вообще ничего не указал) # (А ещё используем это, если клиент вообще ничего не указал)
if chatId == 0 or not chatId: if chatId == 0 or not chatId:
chatId = senderId chatId = senderId
@ -491,7 +491,8 @@ class Processors:
"sender": senderId, "sender": senderId,
"cid": cid, "cid": cid,
"text": text, "text": text,
"attaches": attaches "attaches": attaches,
"elements": elements
} }
# Отправляем событие всем участникам чата # Отправляем событие всем участникам чата
@ -700,6 +701,9 @@ class Processors:
senderId, self.db_pool senderId, self.db_pool
) )
# ID избранного
chatId = senderId ^ senderId
# Добавляем чат в список # Добавляем чат в список
chats.append( chats.append(
self.tools.generate_chat( self.tools.generate_chat(

View File

@ -1,4 +1,5 @@
import hashlib, secrets, random, time, logging, json import hashlib, secrets, random, time, logging, json # PEP-8 по приколу сделан >_<
import re
from common.static import Static from common.static import Static
from common.tools import Tools from common.tools import Tools
from tamtam_tcp.proto import Proto from tamtam_tcp.proto import Proto
@ -76,17 +77,17 @@ class Processors:
return return
# Извлекаем телефон из пакета # Извлекаем телефон из пакета
phone = payload.get("phone").replace("+", "").replace(" ", "").replace("-", "") phone = re.sub(r'\D', '', payload.get("phone", "")) # Не хардкодим, через регулярки
# Генерируем токен с кодом # Генерируем токен с кодом
code = str(random.randint(000000, 999999)) code = f"{secrets.randbelow(1_000_000):06d}" # Старая версия ненадежна, могла отбросить ведущие нули или вообще интерпритировать как систему счисления с основанием 8
token = secrets.token_urlsafe(128) token = secrets.token_urlsafe(128)
# Хешируем # Хешируем
code_hash = hashlib.sha256(code.encode()).hexdigest() code_hash = hashlib.sha256(code.encode()).hexdigest()
token_hash = hashlib.sha256(token.encode()).hexdigest() token_hash = hashlib.sha256(token.encode()).hexdigest()
# Время истечения токена # Срок жизни токена (5 минут)
expires = int(time.time()) + 300 expires = int(time.time()) + 300
# Ищем пользователя, и если он существует, сохраняем токен # Ищем пользователя, и если он существует, сохраняем токен