feat: added class CommandsRobot, func command_to_robot, fuctional for send and get answer robot

This commit is contained in:
Arduinum628
2025-06-02 12:24:30 +03:00
parent d567835bcc
commit 3d7a7a64db
2 changed files with 62 additions and 20 deletions

View File

@@ -1,8 +1,8 @@
from pydantic_settings import BaseSettings, SettingsConfigDict from pydantic_settings import BaseSettings, SettingsConfigDict
class Settings(BaseSettings): class ModelConfig(BaseSettings):
"""Класс для данных конфига""" """Модель конфига"""
model_config = SettingsConfigDict( model_config = SettingsConfigDict(
env_file = '.env', env_file = '.env',
@@ -10,7 +10,27 @@ class Settings(BaseSettings):
extra='ignore' extra='ignore'
) )
class CommandsRobot(ModelConfig):
"""Класс с командами для робота"""
forward: str
backward: str
left: str
right: str
def get_list_commands(self):
"""Метод вернёт список всех команд"""
return list(self.model_dump().values())
class Settings(ModelConfig):
"""Класс для данных конфига"""
stream_url: str stream_url: str
websocket_url_robot: str
commands_robot: CommandsRobot = CommandsRobot()
settings = Settings() settings = Settings()

View File

@@ -1,10 +1,10 @@
from fastapi import APIRouter, WebSocket from fastapi import APIRouter, WebSocket, WebSocketDisconnect, WebSocketException
from fastapi.requests import Request from fastapi.requests import Request
from fastapi.responses import HTMLResponse, Response from fastapi.responses import HTMLResponse, Response
from fastapi.templating import Jinja2Templates from fastapi.templating import Jinja2Templates
from websockets import exceptions, connect
from starlette.websockets import WebSocketDisconnect import asyncio
import httpx import socket
from web_robot_control.settings import settings from web_robot_control.settings import settings
@@ -35,27 +35,49 @@ async def get_config() -> dict:
return {'stream_url': settings.stream_url} return {'stream_url': settings.stream_url}
async def command_to_robot(command: str) -> str:
"""Асинхронная функция для отправки команды роботу через websockets"""
try:
async with connect(settings.websocket_url_robot) as robot_ws:
await robot_ws.send(command)
response = await robot_ws.recv()
return response
# Todo: для каждой ошибки написать своё сообщение
except (
exceptions.InvalidURI,
asyncio.TimeoutError,
exceptions.ConnectionClosedError,
exceptions.ConnectionClosedOK,
exceptions.InvalidHandshake,
ConnectionRefusedError,
socket.gaierror,
exceptions.InvalidMessage
) as err:
return f'{err.__class__.__name__}: {err}'
@router.websocket('/ws') @router.websocket('/ws')
async def websocket_endpoint(websocket: WebSocket) -> None: async def websocket_endpoint(websocket: WebSocket) -> None:
# Установка содединения по веб-сокету # Установка содединения по веб-сокету
await websocket.accept() await websocket.accept()
try: try:
async with httpx.AsyncClient() as client: while True:
while True: # Получение команды от клиента (с веб-сокета)
# Получение команды от клиента (с веб-сокета) command = await websocket.receive_text()
command = await websocket.receive_text() valid_commands = settings.commands_robot.get_list_commands()
print(f'Получена команда: {command}')
# Todo: здесь будет логика валидации команд if command in valid_commands:
# оптравка команды роботу
# Todo: здесь будет логика обработки команды robot_answer = await command_to_robot(command=command)
if robot_answer:
# отправка ответа робота на вебсокет фронтенда
await websocket.send_text(f'Получена команда: {command}, ответ робота: {robot_answer}')
print(f'Ответ робота: {robot_answer}')
except WebSocketDisconnect: except WebSocketDisconnect:
print('WebSocket отключен') # Todo: для вывода ошибок будет настроен logger print('WebSocket отключен') # Todo: для вывода ошибок будет настроен logger
# Todo: вместо Exception будут добавлена ловля других ошибок # Todo: для каждой ошибки написать своё сообщение
# (после того как функция будет полностью дописана) except (WebSocketException, exceptions.InvalidMessage) as err:
except Exception as err: print(f'{err.__class__.__name__}: {err}')
err_text = f'Ошибка: {str(err)}'
await websocket.send_text(err_text)
print(err_text)