Второй стрим

This commit is contained in:
2024-03-11 01:56:43 +04:00
parent 2649b9136a
commit 62922cf613
11 changed files with 147 additions and 12 deletions

12
app/handlers/events.py Normal file
View File

@ -0,0 +1,12 @@
from app.settings import bot, Secrets
from app.utils.commands import set_commands
from app import views
async def start_bot():
await set_commands(bot)
await bot.send_message(Secrets.admin_id, views.start_bot_message())
async def stop_bot():
await bot.send_message(Secrets.admin_id, views.stop_bot_message())

View File

View File

@ -0,0 +1,39 @@
import os
import subprocess
from aiogram.fsm.context import FSMContext
from aiogram.types import Message
from app import views
from app.utils.statesform import ExecuteCommandsSteps
async def multiply_commands(message: Message, state: FSMContext):
cwd = os.getcwd()
await message.answer(views.exec_command_message(cwd))
await state.set_data({"cwd": cwd})
await state.set_state(ExecuteCommandsSteps.EXECUTE)
async def execute_commands(message: Message, state: FSMContext):
if message.text.lower() == "cancel":
await message.answer(views.exec_canceled())
await state.clear()
else:
data = await state.get_data()
if message.text.lower().split()[0] == "cd":
new_cwd = os.path.join(data.get("cwd"), " ".join(message.text.split()[1:]))
os.chdir(new_cwd)
await state.set_data({"cwd": new_cwd})
res = views.changed_dir(new_cwd)
else:
try:
sub = subprocess.check_output(message.text, shell=True, cwd=data.get("cwd"))
res = sub.decode().replace("&", "&amp;").replace("<", "&lt;").replace(">", "&gt;")
except subprocess.CalledProcessError as e:
res = views.subprocess_error(e)
await message.answer(views.user_command(res), parse_mode="HTML")
await state.set_state(ExecuteCommandsSteps.EXECUTE)

7
app/handlers/simple.py Normal file
View File

@ -0,0 +1,7 @@
from aiogram.types import Message
from app import views
async def start_command(message: Message):
await message.answer(views.start_text())

View File

@ -0,0 +1,12 @@
import subprocess
from aiogram.types import Message
from app import views
async def execute_command(message: Message):
user_command = message.text.split()[1:]
sub = subprocess.check_output(user_command, shell=True)
res = sub.decode().replace("&", "&amp;").replace("<", "&lt;").replace(">", "&gt;")
await message.answer(views.user_command(res), parse_mode="HTML")

View File

@ -1,11 +0,0 @@
import subprocess
from aiogram.types import Message
async def execute_command(message: Message):
user_command = message.text.split()[1:]
print(user_command)
sub = subprocess.check_output(user_command)
# print(sub)
await message.answer(f"<pre><code>{sub.decode()}</code></pre>", parse_mode="HTML")

0
app/utils/__init__.py Normal file
View File

15
app/utils/commands.py Normal file
View File

@ -0,0 +1,15 @@
from aiogram import Bot
from aiogram.types import BotCommand, BotCommandScopeDefault
from app import views
async def set_commands(bot: Bot):
commands = [
BotCommand(command="start", description=views.menu.get("start")),
BotCommand(command="command", description=views.menu.get("command")),
BotCommand(command="multiply_commands", description=views.menu.get("multiply_commands")),
BotCommand(command="docker_list", description=views.menu.get("docker_list"))
]
await bot.set_my_commands(commands, BotCommandScopeDefault())

5
app/utils/statesform.py Normal file
View File

@ -0,0 +1,5 @@
from aiogram.fsm.state import StatesGroup, State
class ExecuteCommandsSteps(StatesGroup):
EXECUTE = State()

45
app/views.py Normal file
View File

@ -0,0 +1,45 @@
menu = {
"start": "Начало работы",
"command": "Выполнение произвольной команды",
"multiply_commands": "Выполнение нескольких команд",
"docker_list": "Список Docker-контейнеров",
}
def start_bot_message():
return "Бот запущен"
def stop_bot_message():
return "Бот остановлен"
def user_command(result: str):
return f"<pre><code>{result or 'Done'}</code></pre>"
def exec_command_message(cwd: str):
return f"Режим выполнения команд.\nВы находитесь в директории:\n{cwd}\n\nИли введите cancel для остановки."
def exec_canceled():
return "Процесс выполнения команд остановлен."
def changed_dir(cwd: str):
return f"Перешли в директорию {cwd}"
def subprocess_error(e: str):
return f"Неверная команда или произошла ошибка:\n<pre><code>{e}</code></pre>"
def start_text():
return """Бот для управления сервером.
Доступные команды:
/start - информация о доступных командах
/command <команда> - выполнение произвольной команды
/multiply_commands - выполнение нескольких команд с запоминанием пути
/docker_list - отображение списка Docker-контейнеров и действий для них
"""

13
main.py
View File

@ -4,19 +4,30 @@ from aiogram import Dispatcher, F
from aiogram.filters import Command from aiogram.filters import Command
from app.handlers.docker_commands import get_containers, container_actions, do_container_action from app.handlers.docker_commands import get_containers, container_actions, do_container_action
from app.handlers.user_command import execute_command from app.handlers.events import start_bot, stop_bot
from app.handlers.multiply_commands import multiply_commands, execute_commands
from app.handlers.simple import start_command
from app.handlers.single_command import execute_command
from app.settings import bot from app.settings import bot
from app.utils.statesform import ExecuteCommandsSteps
async def start(): async def start():
dp = Dispatcher() dp = Dispatcher()
dp.startup.register(start_bot)
dp.shutdown.register(stop_bot)
dp.message.register(start_command, Command(commands="start"))
dp.message.register(execute_command, Command(commands="command")) dp.message.register(execute_command, Command(commands="command"))
dp.message.register(multiply_commands, Command(commands="multiply_commands"))
dp.message.register(get_containers, Command(commands="docker_list")) dp.message.register(get_containers, Command(commands="docker_list"))
dp.callback_query.register(container_actions, F.data.startswith("container")) dp.callback_query.register(container_actions, F.data.startswith("container"))
dp.callback_query.register(do_container_action, F.data.startswith("action")) dp.callback_query.register(do_container_action, F.data.startswith("action"))
dp.message.register(execute_commands, ExecuteCommandsSteps.EXECUTE)
try: try:
await dp.start_polling(bot) await dp.start_polling(bot)
finally: finally: