mirror of
https://github.com/R0m1k3/Loki.git
synced 2026-10-12 09:47:20 +02:00
Backend : - tools.py : web_search (DuckDuckGo HTML sans clé, ou SearxNG via SEARX_URL) et run_shell (confiné au workspace, sortie bornée, timeout) - agent.py : run_shell sensible -> émet tool_confirm et ne s'exécute pas tant que l'utilisateur n'a pas validé (confirm_shell) - agent_config.py : web_search/run_shell désactivés par défaut, flag confirm_shell - routes/shell.py : POST /api/shell/run exécute une commande validée - routes/chat.py : relaie l'événement tool_confirm, passe confirm_shell Frontend : - streamChat : événement tool_confirm - store : pendingShell + approveShell/rejectShell (réinjecte le résultat à l'agent) - ChatPanel : carte de validation de commande (Approuver / Refuser) - SettingsView : toggles web_search/run_shell, marqueur sensible, switch confirm_shell - ToolCard : glyphes web_search/run_shell, statut 'à valider', aperçu d'argument Tests : run_shell confiné, gate de confirmation (commande dangereuse non exécutée), route shell, parser DuckDuckGo. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01SVay7z3y7q2gEe54ByAE6N
34 lines
1002 B
Python
34 lines
1002 B
Python
"""Route d'exécution d'une commande shell validée par l'utilisateur.
|
|
|
|
La boucle agentique n'exécute jamais run_shell elle-même quand la confirmation
|
|
est active : elle émet un événement `tool_confirm`. Le client affiche la
|
|
commande, et c'est seulement après clic explicite de l'utilisateur que cette
|
|
route exécute la commande (confinée au workspace).
|
|
"""
|
|
from __future__ import annotations
|
|
|
|
from fastapi import APIRouter, HTTPException
|
|
from pydantic import BaseModel
|
|
|
|
from ..tools import ToolError, run_shell
|
|
|
|
router = APIRouter(prefix="/api/shell", tags=["shell"])
|
|
|
|
|
|
class ShellRequest(BaseModel):
|
|
command: str
|
|
|
|
|
|
@router.post("/run")
|
|
async def run(req: ShellRequest) -> dict:
|
|
"""Exécute la commande validée et renvoie sa sortie."""
|
|
try:
|
|
result = run_shell(req.command)
|
|
except ToolError as exc:
|
|
raise HTTPException(400, str(exc))
|
|
return {
|
|
"command": req.command,
|
|
"exit_code": result["exit_code"],
|
|
"output": result["output"],
|
|
}
|