MAX: фикс версий < 25.8.0

This commit is contained in:
Alexey Polyakov
2026-04-24 21:30:02 +03:00
parent 227f90c3c3
commit 810d480dbd
4 changed files with 54 additions and 19 deletions

View File

@@ -16,7 +16,6 @@ from oneme.models import (
VerifyCodePayloadModel, VerifyCodePayloadModel,
) )
class AuthProcessors(BaseProcessor): class AuthProcessors(BaseProcessor):
def __init__( def __init__(
self, self,
@@ -30,6 +29,23 @@ class AuthProcessors(BaseProcessor):
self.server_config = OnemeConfig().SERVER_CONFIG self.server_config = OnemeConfig().SERVER_CONFIG
self.telegram_bot = telegram_bot self.telegram_bot = telegram_bot
def _check_legacy_version(self, app_version):
"""
Функция определения легаси версий клиентов,
для которых потребуются некоторые корректировки ответов сервера
Сейчас данная функция используется для форматирования ответов
под версии ниже 25.8.0
Функция вернет True, если версия слишком старая,
или False в противном случае
[fun fact] С 25.8.0, похоже, начали корректировать протокол, поскольку это
самая старая версия, которая работала без всяких корректировок сервера
"""
return tuple(int(v) for v in app_version.split(".")) < (25, 8, 0)
async def _send_banners(self, writer): async def _send_banners(self, writer):
"""Функция отправки баннеров клиенту""" """Функция отправки баннеров клиенту"""
# Итоговый список баннеров для отдачи клиенту # Итоговый список баннеров для отдачи клиенту
@@ -181,7 +197,7 @@ class AuthProcessors(BaseProcessor):
await self._send(writer, packet) await self._send(writer, packet)
self.logger.debug(f"Код для {phone}: {code} (существующий={user_exists})") self.logger.debug(f"Код для {phone}: {code} (существующий={user_exists})")
async def auth(self, payload, seq, writer, deviceType, deviceName): async def auth(self, payload, seq, writer, deviceType, deviceName, appVersion):
"""Обработчик проверки кода""" """Обработчик проверки кода"""
try: try:
VerifyCodePayloadModel.model_validate(payload) VerifyCodePayloadModel.model_validate(payload)
@@ -284,6 +300,11 @@ class AuthProcessors(BaseProcessor):
None if not account.get("description") else account.get("description") None if not account.get("description") else account.get("description")
) )
if self._check_legacy_version(appVersion):
include_profile_options = False
else:
include_profile_options = True
# Собираем данные пакета # Собираем данные пакета
payload = { payload = {
"tokenAttrs": {"LOGIN": {"token": login}}, "tokenAttrs": {"LOGIN": {"token": login}},
@@ -299,7 +320,7 @@ class AuthProcessors(BaseProcessor):
description=description, description=description,
accountStatus=int(account.get("accountstatus")), accountStatus=int(account.get("accountstatus")),
profileOptions=json.loads(account.get("profileoptions")), profileOptions=json.loads(account.get("profileoptions")),
includeProfileOptions=True, includeProfileOptions=include_profile_options,
username=account.get("username"), username=account.get("username"),
), ),
} }
@@ -312,7 +333,7 @@ class AuthProcessors(BaseProcessor):
# Отправляем # Отправляем
await self._send(writer, packet) await self._send(writer, packet)
async def auth_confirm(self, payload, seq, writer, deviceType, deviceName): async def auth_confirm(self, payload, seq, writer, deviceType, deviceName, appVersion):
"""Обработчик подтверждения регистрации нового пользователя""" """Обработчик подтверждения регистрации нового пользователя"""
# Валидируем данные пакета # Валидируем данные пакета
try: try:
@@ -441,6 +462,11 @@ class AuthProcessors(BaseProcessor):
), ),
) )
if self._check_legacy_version(appVersion):
include_profile_options = False
else:
include_profile_options = True
# Генерируем профиль # Генерируем профиль
profile = self.tools.generate_profile( profile = self.tools.generate_profile(
id=user_id, id=user_id,
@@ -454,7 +480,7 @@ class AuthProcessors(BaseProcessor):
description=None, description=None,
accountStatus=0, accountStatus=0,
profileOptions=[], profileOptions=[],
includeProfileOptions=True, includeProfileOptions=include_profile_options,
username=None, username=None,
) )
@@ -480,7 +506,7 @@ class AuthProcessors(BaseProcessor):
f"Новый пользователь зарегистрирован: phone={phone} id={user_id} name={first_name} {last_name}" f"Новый пользователь зарегистрирован: phone={phone} id={user_id} name={first_name} {last_name}"
) )
async def login(self, payload, seq, writer): async def login(self, payload, seq, writer, appVersion):
"""Обработчик авторизации клиента на сервере""" """Обработчик авторизации клиента на сервере"""
# Валидируем данные пакета # Валидируем данные пакета
try: try:
@@ -550,6 +576,11 @@ class AuthProcessors(BaseProcessor):
avatar_url = None if not photoId else self.config.avatar_base_url + photoId avatar_url = None if not photoId else self.config.avatar_base_url + photoId
description = None if not user.get("description") else user.get("description") description = None if not user.get("description") else user.get("description")
if self._check_legacy_version(appVersion):
include_profile_options = False
else:
include_profile_options = True
# Генерируем профиль # Генерируем профиль
profile = self.tools.generate_profile( profile = self.tools.generate_profile(
id=user.get("id"), id=user.get("id"),
@@ -563,7 +594,7 @@ class AuthProcessors(BaseProcessor):
description=description, description=description,
accountStatus=int(user.get("accountstatus")), accountStatus=int(user.get("accountstatus")),
profileOptions=json.loads(user.get("profileoptions")), profileOptions=json.loads(user.get("profileoptions")),
includeProfileOptions=True, includeProfileOptions=include_profile_options,
username=user.get("username"), username=user.get("username"),
) )

View File

@@ -20,11 +20,13 @@ class MainProcessors(BaseProcessor):
except pydantic.ValidationError as error: except pydantic.ValidationError as error:
self.logger.error(f"Возникли ошибки при валидации пакета: {error}") self.logger.error(f"Возникли ошибки при валидации пакета: {error}")
await self._send_error(seq, self.opcodes.SESSION_INIT, self.error_types.INVALID_PAYLOAD, writer) await self._send_error(seq, self.opcodes.SESSION_INIT, self.error_types.INVALID_PAYLOAD, writer)
return None, None return None, None, None
# Получаем данные из пакета # Получаем данные из пакета
deviceType = payload.get("userAgent").get("deviceType") userAgent = payload.get("userAgent")
deviceName = payload.get("userAgent").get("deviceName") deviceType = userAgent.get("deviceType")
deviceName = userAgent.get("deviceName")
appVersion = userAgent.get("appVersion")
# Данные пакета # Данные пакета
payload = { payload = {
@@ -43,7 +45,7 @@ class MainProcessors(BaseProcessor):
# Отправляем # Отправляем
await self._send(writer, packet) await self._send(writer, packet)
return deviceType, deviceName return deviceType, deviceName, appVersion
async def ping(self, payload, seq, writer): async def ping(self, payload, seq, writer):
"""Обработчик пинга""" """Обработчик пинга"""

View File

@@ -45,6 +45,7 @@ class OnemeMobile:
deviceType = None deviceType = None
deviceName = None deviceName = None
appVersion = None
userPhone = None userPhone = None
userId = None userId = None
@@ -89,7 +90,7 @@ class OnemeMobile:
match opcode: match opcode:
case self.opcodes.SESSION_INIT: case self.opcodes.SESSION_INIT:
deviceType, deviceName = await self.processors.session_init( deviceType, deviceName, appVersion = await self.processors.session_init(
payload, seq, writer payload, seq, writer
) )
case self.opcodes.AUTH_REQUEST: case self.opcodes.AUTH_REQUEST:
@@ -112,7 +113,7 @@ class OnemeMobile:
) )
else: else:
await self.processors.auth( await self.processors.auth(
payload, seq, writer, deviceType, deviceName payload, seq, writer, deviceType, deviceName, appVersion
) )
case self.opcodes.AUTH_CONFIRM: case self.opcodes.AUTH_CONFIRM:
if not self.auth_rate_limiter.is_allowed(address[0]): if not self.auth_rate_limiter.is_allowed(address[0]):
@@ -124,7 +125,7 @@ class OnemeMobile:
) )
elif payload and payload.get("tokenType") == "REGISTER": elif payload and payload.get("tokenType") == "REGISTER":
await self.processors.auth_confirm( await self.processors.auth_confirm(
payload, seq, writer, deviceType, deviceName payload, seq, writer, deviceType, deviceName, appVersion
) )
else: else:
self.logger.warning( self.logger.warning(
@@ -143,7 +144,7 @@ class OnemeMobile:
userPhone, userPhone,
userId, userId,
hashedToken, hashedToken,
) = await self.processors.login(payload, seq, writer) ) = await self.processors.login(payload, seq, writer, appVersion)
if userPhone: if userPhone:
await self._finish_auth( await self._finish_auth(

View File

@@ -37,6 +37,7 @@ class OnemeWS:
deviceType = None deviceType = None
deviceName = None deviceName = None
appVersion = None
userPhone = None userPhone = None
userId = None userId = None
@@ -63,7 +64,7 @@ class OnemeWS:
match opcode: match opcode:
case self.opcodes.SESSION_INIT: case self.opcodes.SESSION_INIT:
deviceType, deviceName = await self.processors.session_init( deviceType, deviceName, appVersion = await self.processors.session_init(
payload, seq, websocket payload, seq, websocket
) )
case self.opcodes.AUTH_REQUEST: case self.opcodes.AUTH_REQUEST:
@@ -86,7 +87,7 @@ class OnemeWS:
) )
else: else:
await self.processors.auth( await self.processors.auth(
payload, seq, websocket, deviceType, deviceName payload, seq, websocket, deviceType, deviceName, appVersion
) )
case self.opcodes.AUTH_CONFIRM: case self.opcodes.AUTH_CONFIRM:
if not self.auth_rate_limiter.is_allowed(address[0]): if not self.auth_rate_limiter.is_allowed(address[0]):
@@ -98,7 +99,7 @@ class OnemeWS:
) )
elif payload and payload.get("tokenType") == "REGISTER": elif payload and payload.get("tokenType") == "REGISTER":
await self.processors.auth_confirm( await self.processors.auth_confirm(
payload, seq, websocket, deviceType, deviceName payload, seq, websocket, deviceType, deviceName, appVersion
) )
else: else:
self.logger.warning( self.logger.warning(
@@ -117,7 +118,7 @@ class OnemeWS:
userPhone, userPhone,
userId, userId,
hashedToken, hashedToken,
) = await self.processors.login(payload, seq, websocket) ) = await self.processors.login(payload, seq, websocket, deviceType, appVersion)
if userPhone: if userPhone:
await self._finish_auth( await self._finish_auth(