From d0bbd87aa0d6e6037294a20103c71d3a4dce689f Mon Sep 17 00:00:00 2001 From: Max Date: Wed, 14 Jan 2026 17:18:50 +0800 Subject: [PATCH] Refactor Task and TriggerRequest Structures for Rich Input Support - Updated the Task struct in DESIGN.md to replace the Input field with Messages, allowing for rich content input (text, images, files, audio). - Revised the TriggerRequest struct in TECHNICAL.md to utilize Messages instead of Input, enhancing the flexibility of user interactions. - Improved related code examples to demonstrate the new Messages structure, ensuring consistency and clarity in task management and execution processes. --- agent/robot/DESIGN.md | 16 +++++----- agent/robot/TECHNICAL.md | 69 +++++++++++++++++++++++++++++++--------- 2 files changed, 62 insertions(+), 23 deletions(-) diff --git a/agent/robot/DESIGN.md b/agent/robot/DESIGN.md index bda5e6d4..8871086a 100644 --- a/agent/robot/DESIGN.md +++ b/agent/robot/DESIGN.md @@ -298,14 +298,14 @@ P2 Agent reads Goals markdown and breaks into executable tasks: ```go type Task struct { - ID string // unique task ID - Input string // natural language description - GoalRef string // reference to goal (e.g., "Goal 1") - Source TaskSource // auto | human | event - ExecutorType ExecutorType // assistant | mcp | process - ExecutorID string // agent ID or mcp tool name - Args []any // arguments for executor - Order int // execution order + ID string // unique task ID + Messages []context.Message // original input (text, images, files, audio) + GoalRef string // reference to goal (e.g., "Goal 1") + Source TaskSource // auto | human | event + ExecutorType ExecutorType // assistant | mcp | process + ExecutorID string // agent ID or mcp tool name + Args []any // arguments for executor + Order int // execution order } ``` diff --git a/agent/robot/TECHNICAL.md b/agent/robot/TECHNICAL.md index aac67aaa..186513c1 100644 --- a/agent/robot/TECHNICAL.md +++ b/agent/robot/TECHNICAL.md @@ -256,12 +256,13 @@ type RobotState struct { // ==================== Trigger Types ==================== // TriggerRequest - request for Trigger() +// Input uses []context.Message to support rich content (text, images, files, audio) type TriggerRequest struct { Type types.TriggerType `json:"type"` // human | event // Human intervention fields (when Type = human) Action types.InterventionAction `json:"action,omitempty"` // task.add | goal.adjust | task.cancel | plan.add - Input string `json:"input,omitempty"` // user's input + Messages []context.Message `json:"messages,omitempty"` // user's input (supports text, images, files) PlanAt *time.Time `json:"plan_at,omitempty"` // for action=plan.add InsertAt InsertPosition `json:"insert_at,omitempty"` // where to insert: first | last | next | at AtIndex int `json:"at_index,omitempty"` // index when insert_at=at @@ -362,11 +363,32 @@ const list = Process("robot.List", { pagesize: 20, }); -// Trigger with human intervention +// Trigger with text message const result = Process("robot.Trigger", "mem_abc123", { type: "human", action: "task.add", - input: "Prepare meeting materials for BigCorp", + messages: [ + { role: "user", content: "Prepare meeting materials for BigCorp" }, + ], + insert_at: "first", +}); + +// Trigger with image (multimodal) +const imageResult = Process("robot.Trigger", "mem_abc123", { + type: "human", + action: "task.add", + messages: [ + { + role: "user", + content: [ + { type: "text", text: "Analyze this chart and summarize key trends" }, + { + type: "image_url", + image_url: { url: "https://example.com/chart.png" }, + }, + ], + }, + ], insert_at: "first", }); @@ -490,6 +512,24 @@ interface TriggerResult { message?: string; } +// Message - same as context.Message, supports rich content +interface Message { + role: "user" | "assistant" | "system" | "tool"; + content: string | ContentPart[]; + name?: string; + tool_call_id?: string; + tool_calls?: ToolCall[]; +} + +interface ContentPart { + type: "text" | "image_url" | "input_audio" | "file" | "data"; + text?: string; + image_url?: { url: string; detail?: "auto" | "low" | "high" }; + input_audio?: { data: string; format: string }; + file?: { url: string; name?: string; mime_type?: string }; + data?: { data: string; mime_type: string }; +} + interface TriggerRequest { type: "human" | "event"; @@ -506,7 +546,7 @@ interface TriggerRequest { | "plan.remove" | "plan.update" | "instruct"; - input?: string; + messages?: Message[]; // supports text, images, files, audio insert_at?: "first" | "last" | "next" | "at"; at_index?: number; plan_at?: string; // ISO date for plan.add @@ -620,7 +660,7 @@ if (state.status === "idle") { const result = bot.Trigger({ type: "human", action: "task.add", - input: "Analyze sales data", + messages: [{ role: "user", content: "Analyze sales data" }], insert_at: "first", }); console.log("Triggered:", result.accepted); @@ -653,7 +693,7 @@ function Create(ctx, messages) { const result = bot.Trigger({ type: "human", action: "task.add", - input: "Analyze this data", + messages: [{ role: "user", content: "Analyze this data" }], insert_at: "first", }); @@ -1211,9 +1251,9 @@ type Execution struct { // TriggerInput - stored trigger input for traceability type TriggerInput struct { // For human intervention - Action InterventionAction `json:"action,omitempty"` // task.add, goal.adjust, etc. - Input string `json:"input,omitempty"` // user's original input - UserID string `json:"user_id,omitempty"`// who triggered + Action InterventionAction `json:"action,omitempty"` // task.add, goal.adjust, etc. + Messages []context.Message `json:"messages,omitempty"` // user's input (text, images, files) + UserID string `json:"user_id,omitempty"` // who triggered // For event trigger Source EventSource `json:"source,omitempty"` // webhook | database @@ -1247,10 +1287,10 @@ type Goals struct { // Task - planned task (structured, for execution) type Task struct { - ID string `json:"id"` - Input string `json:"input"` // natural language description - GoalRef string `json:"goal_ref,omitempty"`// reference to goal (e.g., "Goal 1") - Source TaskSource `json:"source"` // auto | human | event + ID string `json:"id"` + Messages []context.Message `json:"messages"` // original input (text, images, files) + GoalRef string `json:"goal_ref,omitempty"` // reference to goal (e.g., "Goal 1") + Source TaskSource `json:"source"` // auto | human | event // Executor ExecutorType ExecutorType `json:"executor_type"` @@ -1422,8 +1462,7 @@ type InterveneRequest struct { TeamID string `json:"team_id"` MemberID string `json:"member_id"` Action InterventionAction `json:"action"` - Input string `json:"input"` - Priority Priority `json:"priority,omitempty"` + Messages []context.Message `json:"messages"` // user input (text, images, files) PlanTime *time.Time `json:"plan_time,omitempty"` // for action=plan }