feat(mma): Enable manual ticket approval via Hook API for Step Mode

This commit is contained in:
2026-05-02 13:48:14 -04:00
parent 9f67a31b2f
commit 7fdf6c9782
4 changed files with 35 additions and 2 deletions
+4
View File
@@ -267,3 +267,7 @@ class ApiHookClient:
"""Mutates the MMA DAG (Directed Acyclic Graph) structure."""
return self._make_request('POST', '/api/mma/dag/mutate', data=data) or {}
def approve_mma_ticket(self, ticket_id: str) -> dict:
"""Manually approves a specific ticket for execution in Step Mode."""
return self._make_request('POST', '/api/mma/ticket/approve', data={"ticket_id": ticket_id}) or {}
+18 -1
View File
@@ -605,7 +605,7 @@ class HookHandler(BaseHTTPRequestHandler):
elif self.path == "/api/mma/dag/mutate":
def mutate_dag():
try:
func = _get_app_attr(app, "_mutate_dag")
func = _get_app_attr(app, "mutate_dag")
if func: func(data)
except Exception as e:
sys.stderr.write(f"[DEBUG] Hook API mutate_dag error: {e}\n")
@@ -618,6 +618,23 @@ class HookHandler(BaseHTTPRequestHandler):
self.send_header("Content-Type", "application/json")
self.end_headers()
self.wfile.write(json.dumps({"status": "queued"}).encode("utf-8"))
elif self.path == "/api/mma/ticket/approve":
ticket_id = data.get("ticket_id")
def approve_ticket():
try:
func = _get_app_attr(app, "approve_ticket")
if func: func(ticket_id)
except Exception as e:
sys.stderr.write(f"[DEBUG] Hook API approve_ticket error: {e}\n")
sys.stderr.flush()
lock = _get_app_attr(app, "_pending_gui_tasks_lock")
tasks = _get_app_attr(app, "_pending_gui_tasks")
if lock and tasks is not None:
with lock: tasks.append({"action": "custom_callback", "callback": approve_ticket})
self.send_response(200)
self.send_header("Content-Type", "application/json")
self.end_headers()
self.wfile.write(json.dumps({"status": "queued"}).encode("utf-8"))
else:
self.send_response(404)
self.end_headers()
+12
View File
@@ -2780,6 +2780,18 @@ class AppController:
self.files.append(item)
self._refresh_from_project()
def approve_ticket(self, ticket_id: str) -> None:
"""Manually approves a ticket for execution."""
if self.engine and self.engine.engine:
self.engine.engine.approve_task(ticket_id)
else:
# Fallback if engine not running
for t in self.active_tickets:
if t.get('id') == ticket_id:
t['status'] = 'in_progress'
break
self._push_mma_state_update()
def mutate_dag(self, data: dict) -> None:
"""Modifies task dependencies."""
ticket_id = data.get("ticket_id")
+1 -1
View File
@@ -3450,7 +3450,7 @@ def hello():
def bulk_execute(self) -> None:
for tid in self.ui_selected_tickets:
t = next((t for t in self.active_tickets if str(t.get('id', '')) == tid), None)
if t: t['status'] = 'ready'
if t: t['status'] = 'in_progress'
self._push_mma_state_update()
def bulk_skip(self) -> None: