- commands.yaml с рабочими примерами: медиа, громкость, поиск, папки, блокировка; перечитывается автоматически, ошибки не ломают остальные команды - Действия run / open / http / keys; вывод и ответы возвращаются модели - Вызов через модель (tool calling) и мгновенно по точным фразам, в том числе с параметрами - Подтверждение «да/нет» для опасных команд, после голосового вопроса микрофон включается сам - Безопасность: запуск без оболочки, защита аргументов cmd/PowerShell/.bat, переменные окружения раскрываются только в шаблоне - Вкладка «Команды» в настройках - Тесты разбора, действий, фраз и полных сценариев через Assistant Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
49 lines
1.9 KiB
Python
49 lines
1.9 KiB
Python
from agr_assistent.commands.matching import confirmation_decision, match_phrase, normalize
|
|
from agr_assistent.commands.model import parse_command
|
|
|
|
_COMMANDS = [
|
|
parse_command(
|
|
{
|
|
"name": "pause",
|
|
"description": "Пауза",
|
|
"phrases": ["Поставь на паузу", "пауза"],
|
|
"action": {"type": "keys", "keys": "media_play_pause"},
|
|
}
|
|
),
|
|
parse_command(
|
|
{
|
|
"name": "volume",
|
|
"description": "Громкость",
|
|
"phrases": ["громкость {level} процентов", "громкость {level}"],
|
|
"parameters": {"level": {"type": "integer", "minimum": 0, "maximum": 100}},
|
|
"action": {"type": "keys", "keys": "volume_up"},
|
|
}
|
|
),
|
|
]
|
|
|
|
|
|
def test_normalize() -> None:
|
|
assert normalize(" Ещё, пожалуйста!! ") == "еще пожалуйста"
|
|
|
|
|
|
def test_whole_phrase_must_match() -> None:
|
|
assert match_phrase(_COMMANDS, "Пауза.")[0].name == "pause"
|
|
assert match_phrase(_COMMANDS, "поставь на паузу")[0].name == "pause"
|
|
assert match_phrase(_COMMANDS, "пауза в работе") is None
|
|
assert match_phrase(_COMMANDS, "") is None
|
|
|
|
|
|
def test_phrase_parameters_are_validated() -> None:
|
|
command, arguments = match_phrase(_COMMANDS, "Громкость 30 процентов")
|
|
assert command.name == "volume" and arguments == {"level": 30}
|
|
|
|
assert match_phrase(_COMMANDS, "громкость 30")[1] == {"level": 30}
|
|
assert match_phrase(_COMMANDS, "громкость 300") is None
|
|
assert match_phrase(_COMMANDS, "громкость много") is None
|
|
|
|
|
|
def test_confirmation_decision() -> None:
|
|
assert confirmation_decision("Да!") is True
|
|
assert confirmation_decision("не надо") is False
|
|
assert confirmation_decision("да, но сначала сохрани файл") is None
|