mirror of
https://github.com/MODSetter/SurfSense.git
synced 2026-05-29 19:35:20 +02:00
fix automation run inputs, hitl routing, and detail UI polish
This commit is contained in:
parent
ed8d56aa16
commit
91962ba879
8 changed files with 258 additions and 86 deletions
|
|
@ -22,11 +22,14 @@ from typing import Any
|
|||
from uuid import UUID
|
||||
|
||||
from fastapi import HTTPException
|
||||
from langchain.tools import ToolRuntime
|
||||
from langchain_core.messages import HumanMessage
|
||||
from langchain_core.tools import tool
|
||||
from pydantic import ValidationError
|
||||
|
||||
from app.agents.new_chat.tools.hitl import request_approval
|
||||
from app.agents.multi_agent_chat.subagents.shared.hitl.approvals.self_gated import (
|
||||
request_approval,
|
||||
)
|
||||
from app.automations.schemas.api import AutomationCreate
|
||||
from app.automations.services.automation import AutomationService
|
||||
from app.db import User, async_session_maker
|
||||
|
|
@ -56,7 +59,7 @@ def create_create_automation_tool(
|
|||
uid = UUID(user_id) if isinstance(user_id, str) else user_id
|
||||
|
||||
@tool
|
||||
async def create_automation(intent: str) -> dict[str, Any]:
|
||||
async def create_automation(intent: str, runtime: ToolRuntime) -> dict[str, Any]:
|
||||
"""Draft + save an automation from a natural-language intent.
|
||||
|
||||
Use this when the user wants SurfSense to do something on its own
|
||||
|
|
@ -137,6 +140,7 @@ def create_create_automation_tool(
|
|||
tool_name="create_automation",
|
||||
params=card_params,
|
||||
context={"search_space_id": search_space_id},
|
||||
tool_call_id=runtime.tool_call_id,
|
||||
)
|
||||
|
||||
if result.rejected:
|
||||
|
|
@ -200,6 +204,5 @@ def _extract_json(text: str) -> dict[str, Any] | None:
|
|||
|
||||
def _format_validation_issues(exc: ValidationError) -> list[str]:
|
||||
return [
|
||||
f"{'.'.join(str(p) for p in err['loc'])}: {err['msg']}"
|
||||
for err in exc.errors()
|
||||
f"{'.'.join(str(p) for p in err['loc'])}: {err['msg']}" for err in exc.errors()
|
||||
]
|
||||
|
|
|
|||
|
|
@ -49,6 +49,7 @@ def request_approval(
|
|||
params: dict[str, Any],
|
||||
context: dict[str, Any] | None = None,
|
||||
trusted_tools: list[str] | None = None,
|
||||
tool_call_id: str | None = None,
|
||||
) -> HITLResult:
|
||||
"""Pause the graph for user approval and return the user's decision.
|
||||
|
||||
|
|
@ -64,6 +65,10 @@ def request_approval(
|
|||
forwarded verbatim to the FE for richer card chrome.
|
||||
trusted_tools: Per-session allowlist; when ``tool_name`` is in it the
|
||||
interrupt is skipped and the tool runs immediately.
|
||||
tool_call_id: Caller's LangChain tool-call id. Required for tools
|
||||
running directly on the main agent; subagent-mounted tools omit
|
||||
it (the ``task`` chokepoint stamps it on re-raise — see
|
||||
:mod:`...checkpointed_subagent_middleware.propagation`).
|
||||
|
||||
Returns:
|
||||
:class:`HITLResult` with ``rejected=True`` if the user declined or
|
||||
|
|
@ -90,6 +95,8 @@ def request_approval(
|
|||
interrupt_type=action_type,
|
||||
context=context,
|
||||
)
|
||||
if tool_call_id:
|
||||
payload["tool_call_id"] = tool_call_id
|
||||
approval = interrupt(payload)
|
||||
|
||||
parsed = parse_lc_envelope(approval)
|
||||
|
|
|
|||
|
|
@ -67,8 +67,15 @@ async def dispatch_run(
|
|||
def _validate_inputs(
|
||||
definition: AutomationDefinition, inputs: dict[str, Any]
|
||||
) -> dict[str, Any]:
|
||||
"""Validate merged inputs against the optional declared schema.
|
||||
|
||||
No declared schema → pass through (runtime inputs like ``fired_at`` /
|
||||
``last_fired_at`` and trigger ``static_inputs`` must still reach the
|
||||
template context). Returning ``{}`` here strips them and makes Jinja
|
||||
blow up on any ``{{ inputs.* }}`` reference.
|
||||
"""
|
||||
if definition.inputs is None or not definition.inputs.schema_:
|
||||
return {}
|
||||
return inputs
|
||||
try:
|
||||
jsonschema.validate(instance=inputs, schema=definition.inputs.schema_)
|
||||
except jsonschema.ValidationError as exc:
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue