Compare commits

..

3 Commits

Author SHA1 Message Date
51e1d59b12 fixed bot.send_message 2025-08-14 14:04:20 +03:00
a60c6b2ee9 updated main.py 2025-08-14 14:01:06 +03:00
4cbb60fdf4 added botdata command 2025-08-14 13:08:09 +03:00
5 changed files with 122 additions and 15 deletions

View File

@@ -1,3 +1,4 @@
BOT_TOKEN = "..." # Токен бота получать у @BotFather BOT_TOKEN = "..." # Токен бота получать у @BotFather
ADMIN_CHAT_ID = -1001111111111 # ID админ-чата получать у @username_to_id_bot ADMIN_CHAT_ID = -1001111111111 # ID админ-чата получать у @username_to_id_bot
LOG_THREAD_ID = 2 # ID топика, брать из ссылки сообщения LOG_THREAD_ID = 2 # ID топика, брать из ссылки сообщения
ADMIN_IDS = "11111,22222" # ID администраторов получать у @username_to_id_bot

View File

@@ -16,14 +16,17 @@ from action_reporter import init_action_reporter
from config import MODULES_DIR from config import MODULES_DIR
load_dotenv() # Загружаем токен бота из .env # Загружаем токен бота из .env
load_dotenv()
bot = AsyncTeleBot(os.getenv("BOT_TOKEN"), parse_mode="html") bot = AsyncTeleBot(os.getenv("BOT_TOKEN"), parse_mode="html")
# Загружаем ID админ-чата из .env и инициализируемся для логов в чат # Загружаем ID админ-чата из .env и инициализируемся для логов в чат
init_action_reporter(bot, os.getenv("ADMIN_CHAT_ID"), os.getenv("LOG_THREAD_ID")) init_action_reporter(bot, os.getenv("ADMIN_CHAT_ID"), os.getenv("LOG_THREAD_ID"))
logger = logging.getLogger(__name__) # Получаем логгер для текущего модуля # Получаем логгер для текущего модуля
logger = logging.getLogger(__name__)
# Middleware для автоматического обновления информации о пользователях в базе данных
class UserUpdateMiddleware(BaseMiddleware): class UserUpdateMiddleware(BaseMiddleware):
def __init__(self, db): def __init__(self, db):
super().__init__() super().__init__()
@@ -32,6 +35,7 @@ class UserUpdateMiddleware(BaseMiddleware):
self.update_types = ['message', 'chat_member'] self.update_types = ['message', 'chat_member']
self.db = db self.db = db
# Обработчик, вызываемый ДО обработки сообщения основными хэндлерами
async def pre_process(self, message, data): async def pre_process(self, message, data):
# Обработка пользователей, отправившие сообщение # Обработка пользователей, отправившие сообщение
@@ -52,43 +56,78 @@ class UserUpdateMiddleware(BaseMiddleware):
) )
return data return data
# Обработчик, вызываемый ПОСЛЕ обработки сообщения основными хэндлерами
async def post_process(self, message, data, exception): async def post_process(self, message, data, exception):
pass pass
# Регистрируем middleware # Регистрируем middleware
bot.setup_middleware(UserUpdateMiddleware(db)) bot.setup_middleware(UserUpdateMiddleware(db))
async def load_modules(): # Загружает все модули из директории /modules # Загружает все модули из директории /modules
async def load_modules():
setup_logging() # Инициализация логирования # Инициализация логирования
setup_logging()
loaded_count = 0 # Переменная для подсчёта модулей # Переменная для подсчёта модулей
modules_path = os.path.join(os.path.dirname(__file__), MODULES_DIR) # Импортируем относительный путь проекта loaded_count = 0
# Импортируем относительный путь проекта
modules_path = os.path.join(os.path.dirname(__file__), MODULES_DIR)
for filename in os.listdir(modules_path): for filename in os.listdir(modules_path):
# Если файл содержит в конце .py (кроме __init__.py)
if filename.endswith(".py") and filename != "__init__.py": if filename.endswith(".py") and filename != "__init__.py":
module_name = filename[:-3] # Убираем расширение .py
# Убираем расширение .py
module_name = filename[:-3]
try: try:
# Импортируем модуль (modules.start)
module = importlib.import_module(f"{MODULES_DIR}.{module_name}") module = importlib.import_module(f"{MODULES_DIR}.{module_name}")
# Если присутствует register_handlers
if hasattr(module, "register_handlers"): if hasattr(module, "register_handlers"):
module.register_handlers(bot) module.register_handlers(bot)
loaded_count += 1 loaded_count += 1
logger.info(f"Модуль {module_name} успешно загружен.") logger.info(f"Модуль {module_name} успешно загружен.")
# Если нет register_handlers
else: else:
# Записываем действие в логи
logger.warning(f"Модуль {module_name} не содержит функцию register_handlers.") logger.warning(f"Модуль {module_name} не содержит функцию register_handlers.")
except Exception as e: except Exception as e:
# Записываем ошибку в логи
logger.error(f"Ошибка при загрузке модуля {module_name}: {str(e)}") logger.error(f"Ошибка при загрузке модуля {module_name}: {str(e)}")
# Записываем отчет о модулях в логи
logger.info(f"Загружено модулей: {loaded_count} шт. Бот запущен.") logger.info(f"Загружено модулей: {loaded_count} шт. Бот запущен.")
async def main(): async def main():
os.system('clear') # Очищаем терминал
# Очищаем терминал
os.system('clear')
try: try:
await load_modules() # Проверяем и загружаем модули
await bot.infinity_polling() # Запускаем бота # Проверяем и загружаем модули
except (KeyboardInterrupt, asyncio.CancelledError): await load_modules()
logger.info("Бот остановлен.")
# Запускаем бота
await bot.infinity_polling()
except Exception as e: except Exception as e:
# Записываем критическую ошибку в логи
logger.critical(f"Критическая ошибка: {str(e)}") logger.critical(f"Критическая ошибка: {str(e)}")
# Завершаем скрипт с критической ошибкой
sys.exit(1) sys.exit(1)
if __name__ == "__main__": if __name__ == "__main__":

67
src/modules/botdata.py Normal file
View File

@@ -0,0 +1,67 @@
from telebot.async_telebot import AsyncTeleBot
from telebot.types import Message
import asyncio
import logging
import os
from utils import delete_messages
from config import COMMAND_MESSAGES, DATABASE_NAME, LOG_FILE_NAME
# Получаем логгер для текущего модуля
logger = logging.getLogger(__name__)
# Загружаем id администраторов из .env
ADMIN_IDS = [int(id_str.strip()) for id_str in os.getenv('ADMIN_IDS').split(',')]
# Регистрирует все обработчики команд
def register_handlers(bot: AsyncTeleBot):
# Обработчик команды /botdata
@bot.message_handler(commands=['botdata'])
async def botdata_command(message: Message):
try:
# Если id администратора совпадает
if message.from_user.id in ADMIN_IDS:
# Отправляем базу данных
await bot.send_document(
chat_id=message.chat.id,
document=open(DATABASE_NAME, 'rb')
)
# Отправляем файл с логами
await bot.send_document(
chat_id=message.chat.id,
document=open(LOG_FILE_NAME, 'rb')
)
# Записываем действие в логи
logger.info(f"Администратор {message.from_user.id} запустил /botdata.")
# Если id администратора не совпадает
else:
# Отправляем предупреждение
await bot.send_message(
chat_id=message.chat.id,
text=COMMAND_MESSAGES['no_admin_rights'],
message_thread_id=message.message_thread_id,
)
# Записываем действие в логи
logger.info(f"Пользователь {message.from_user.id} запустил /botdata.")
except Exception as e:
# Отправляем ошибку
await bot.send_message(
chat_id=message.chat.id,
text=COMMAND_MESSAGES['general_error'],
message_thread_id=message.message_thread_id,
)
# Записываем ошибку в логи
logger.error(f"Общая ошибка в botdata_command: {str(e)}")

View File

@@ -38,7 +38,7 @@ def register_handlers(bot: AsyncTeleBot):
except Exception as e: except Exception as e:
# Отправляем ошибку # Отправляем ошибку
await send_message( await bot.send_message(
chat_id=message.chat.id, chat_id=message.chat.id,
text=COMMAND_MESSAGES['general_error'], text=COMMAND_MESSAGES['general_error'],
message_thread_id=message.message_thread_id, message_thread_id=message.message_thread_id,

View File

@@ -38,7 +38,7 @@ def register_handlers(bot: AsyncTeleBot):
except Exception as e: except Exception as e:
# Отправляем ошибку # Отправляем ошибку
await send_message( await bot.send_message(
chat_id=message.chat.id, chat_id=message.chat.id,
text=COMMAND_MESSAGES['general_error'], text=COMMAND_MESSAGES['general_error'],
message_thread_id=message.message_thread_id, message_thread_id=message.message_thread_id,