import logging
import sqlite3
from aiogram import Bot, Dispatcher, types
from aiogram.types import ReplyKeyboardMarkup, KeyboardButton
from aiogram.filters import Command
import asyncio
from datetime import datetime, timedelta
import random
# Включаем логирование
logging.basicConfig(level=logging.INFO)
# Укажи здесь свой токен бота
API_TOKEN = 'Token'
# Список разрешённых ID пользователей
ALLOWED_USERS = {3423423423} # Ваш ID добавлен сюда
# Инициализация бота и диспетчера
bot = Bot(token=API_TOKEN)
dp = Dispatcher(bot) # Передаем бот в диспетчер
# Создаем кнопки
button_menu = KeyboardButton(text='Меню')
button_profile = KeyboardButton(text='Мой профиль')
button_back = KeyboardButton(text='Назад')
button1 = KeyboardButton(text='Снос аккаунта')
button2 = KeyboardButton(text='Снос канала')
button3 = KeyboardButton(text='Снос бота')
button_subscriptions = KeyboardButton(text='Подписки')
# Новые кнопки для управления подписками
button_give_access = KeyboardButton(text='Выдать подписку')
button_remove_access = KeyboardButton(text='Удалить подписку')
button_extend_access = KeyboardButton(text='Продлить подписку') # Новая кнопка
# Функция, возвращающая клавиатуру для профиля
def get_profile_keyboard(user_id: int) -> ReplyKeyboardMarkup:
if user_id in ALLOWED_USERS:
return ReplyKeyboardMarkup(keyboard=[
[button_menu],
[button_profile, button_subscriptions]
], resize_keyboard=True)
else:
return ReplyKeyboardMarkup(keyboard=[
[button_menu],
[button_profile]
], resize_keyboard=True)
# Функция создания клавиатуры для меню
action_keyboard = ReplyKeyboardMarkup(keyboard=[
[button1],
[button2],
[button3],
[button_back]
], resize_keyboard=True)
# Функция создания клавиатуры для подписок
subscriptions_keyboard = ReplyKeyboardMarkup(keyboard=[
[button_give_access],
[button_remove_access],
[button_extend_access], # Добавленная кнопка
[button_back]
], resize_keyboard=True)
# Функция инициализации базы данных
def init_db():
conn = sqlite3.connect('tempusers.db')
cursor = conn.cursor()
cursor.execute('''
CREATE TABLE IF NOT EXISTS temp_access (
user_id INTEGER PRIMARY KEY,
expiration_time TEXT
)
''')
conn.commit()
conn.close()
# Функция добавления подписки
def add_subscription(user_id: int, expiration_time: datetime):
conn = sqlite3.connect('tempusers.db')
cursor = conn.cursor()
cursor.execute('''
INSERT OR REPLACE INTO temp_access (user_id, expiration_time)
VALUES (?, ?)
''', (user_id, expiration_time.isoformat()))
conn.commit()
conn.close()
# Функция удаления подписки
def remove_subscription(user_id: int):
conn = sqlite3.connect('tempusers.db')
cursor = conn.cursor()
cursor.execute('DELETE FROM temp_access WHERE user_id = ?', (user_id,))
conn.commit()
conn.close()
# Функция получения времени окончания подписки
def get_subscription(user_id: int) -> datetime:
conn = sqlite3.connect('tempusers.db')
cursor = conn.cursor()
cursor.execute('SELECT expiration_time FROM temp_access WHERE user_id = ?', (user_id,))
result = cursor.fetchone()
conn.close()
if result:
return datetime.fromisoformat(result[0])
return None
# Функция проверки, разрешён ли пользователь
def is_user_allowed(user_id: int) -> bool:
if user_id in ALLOWED_USERS:
return True
expiration_time = get_subscription(user_id)
if expiration_time and expiration_time > datetime.now():
return True
return False
# Функция форматирования оставшегося времени
def format_remaining_time(expiration_time: datetime) -> str:
now = datetime.now()
remaining_time = expiration_time - now
if remaining_time.total_seconds() <= 0:
return "Подписка истекла"
days, remainder = divmod(remaining_time.total_seconds(), 86400) # 86400 секунд в дне
hours, remainder = divmod(remainder, 3600) # 3600 секунд в часе
minutes, _ = divmod(remainder, 60) # 60 секунд в минуте
return f"{int(days)} дн. {int(hours)} ч. {int(minutes)} мин."
# Функция форматирования даты в буквенном виде
def format_date(date: datetime) -> str:
months = ["Января", "Февраля", "Марта", "Апреля", "Мая", "Июня", "Июля", "Августа", "Сентября", "Октября", "Ноября", "Декабря"]
month = months[date.month - 1]
return f"{date.day} {month} {date.year} года, {date.strftime('%H:%M:%S')}"
# Функция получения юзернейма пользователя
async def get_username(user_id: int) -> str:
try:
chat_member = await bot.get_chat_member(chat_id=user_id, user_id=user_id)
return chat_member.user.username or "Не указан"
except Exception as e:
logging.error(f"Не удалось получить информацию о пользователе {user_id}: {e}")
return "Не указан"
# Функция форматирования подписок в виде строки
async def format_subscriptions() -> str:
conn = sqlite3.connect('tempusers.db')
cursor = conn.cursor()
cursor.execute('SELECT user_id, expiration_time FROM temp_access')
subscriptions = cursor.fetchall()
conn.close()
if not subscriptions:
return "Нет активных подписок."
result = f"Активные подписки ({len(subscriptions)}):\n"
for index, (user_id, expiration_time) in enumerate(subscriptions, start=1):
username = await get_username(user_id)
result += f"{index}. Юзернейм: @{username} , ID пользователя: {user_id} , До: {format_date(datetime.fromisoformat(expiration_time))}\n"
return result
# Обработчик команды /start
@dp.message(Command("start"))
async def send_welcome(message: types.Message):
if is_user_allowed(message.from_user.id):
await message.answer("Привет! Нажмите 'Меню', чтобы открыть основные действия.", reply_markup=get_profile_keyboard(message.from_user.id))
else:
await message.answer("Извините, у вас нет доступа к этому боту. Вы можете открыть 'Мой профиль'.")
# Обработчик кнопки "Меню"
@dp.message(lambda message: message.text == "Меню")
async def show_main_menu(message: types.Message):
if is_user_allowed(message.from_user.id):
await message.answer("Выберите действие:", reply_markup=action_keyboard)
else:
await message.answer("Извините, у вас нет доступа к этому разделу.")
# Обработчик кнопки "Назад"
@dp.message(lambda message: message.text == "Назад")
async def go_back(message: types.Message):
if message.text == "Назад" and message.reply_markup == subscriptions_keyboard:
await message.answer("Вы вернулись в меню подписок.", reply_markup=get_profile_keyboard(message.from_user.id))
else:
await message.answer("Вы вернулись в главное меню.", reply_markup=get_profile_keyboard(message.from_user.id))
# Обработчик кнопки "Мой профиль"
@dp.message(lambda message: message.text == "Мой профиль")
async def show_profile(message: types.Message):
user_id = message.from_user.id
username = message.from_user.username or "Не указан"
first_name = message.from_user.first_name or "Не указан" # Добавляем имя пользователя
expiration_time = get_subscription(user_id)
subscription_status = "Не активна"
if expiration_time:
subscription_status = format_remaining_time(expiration_time)
profile_info = (
f"Ваш профиль:\n"
f"Имя: {first_name}\n"
f"Юзернейм: @{username}\n"
f"ID: {user_id}\n"
f"Подписка: {subscription_status}"
)
await message.answer(profile_info, reply_markup=get_profile_keyboard(user_id))
# Обработчик кнопки "Подписки"
@dp.message(lambda message: message.text == "Подписки")
async def show_subscriptions(message: types.Message):
if message.from_user.id in ALLOWED_USERS:
subscriptions_info = await format_subscriptions()
await message.answer(subscriptions_info, reply_markup=subscriptions_keyboard)
else:
await message.answer("Извините, у вас нет доступа к этому разделу.")
# Обработчик кнопки "Выдать подписку"
@dp.message(lambda message: message.text == "Выдать подписку")
async def give_access(message: types.Message):
if message.from_user.id in ALLOWED_USERS:
await message.answer("Отправьте ID пользователя и время подписки в днях в формате:\n<ID пользователя> <Время в днях>")
else:
await message.answer("Извините, у вас нет доступа к этому действию.")
# Обработчик кнопки "Удалить подписку"
@dp.message(lambda message: message.text == "Удалить подписку")
async def remove_access(message: types.Message):
if message.from_user.id in ALLOWED_USERS:
await message.answer("Отправьте ID пользователя для удаления подписки.")
else:
await message.answer("Извините, у вас нет доступа к этому действию.")
# Обработчик кнопки "Продлить подписку"
@dp.message(lambda message: message.text == "Продлить подписку")
async def extend_access(message: types.Message):
if message.from_user.id in ALLOWED_USERS:
await message.answer("Отправьте ID пользователя для продления подписки и время в днях в формате:\n<ID пользователя> <Время в днях>")
else:
await message.answer("Извините, у вас нет доступа к этому действию.")
# Обработчик кнопки "Снос аккаунта", "Снос канала" и "Снос бота"
@dp.message(lambda message: message.text in ["Снос аккаунта", "Снос канала", "Снос бота"])
async def start_deletion_process(message: types.Message):
if is_user_allowed(message.from_user.id):
await message.answer("Отправьте юзернейм для удаления.")
else:
await message.answer("Извините, у вас нет доступа к этому действию.")
# Обработчик получения юзернейма для удаления
@dp.message(lambda message: message.text.startswith("@"))
async def handle_username_for_deletion(message: types.Message):
if is_user_allowed(message.from_user.id):
await message.answer("Атака запущена!")
# Случайное время ожидания между 1 и 20 минутами
await asyncio.sleep(random.randint(1, 20) * 60)
await message.answer("Готово, аккаунт снесён!")
else:
await message.answer("Извините, у вас нет доступа к этому действию.")
# Запуск бота
async def main():
init_db()
await dp.start_polling()
if __name__ == '__main__':
asyncio.run(main())