Add workflow runtime execution and condition validation

This commit is contained in:
mlogclub
2026-06-23 09:34:08 +08:00
parent 560843686b
commit ed9d60db0d
10 changed files with 1026 additions and 45 deletions
+78 -12
View File
@@ -2,9 +2,16 @@ package runtime
import (
"context"
"encoding/json"
"time"
"agent-desk/internal/ai/runtime/executor"
workflowexecutor "agent-desk/internal/ai/runtime/workflow"
"agent-desk/internal/models"
"agent-desk/internal/pkg/utils"
"agent-desk/internal/repositories"
"github.com/mlogclub/simple/sqls"
)
type Service struct {
@@ -24,32 +31,29 @@ func NewService() *Service {
func (s *Service) Run(ctx context.Context, req Request) (*Summary, error) {
req.UserMessage.Content = utils.BuildRuntimeMessageText(req.UserMessage.MessageType, req.UserMessage.Content)
aiAgent, err := prepareWorkflowAgent(req.AIAgent)
aiAgent, workflow, err := prepareWorkflowAgent(req.AIAgent)
if err != nil {
return nil, err
}
req.AIAgent = aiAgent
toolSet, err := s.prepare.prepareToolsForRun(req)
if err != nil {
return nil, err
}
req.ToolSet = toolSet
summary, err := s.runtime.ExecuteRun(ctx, executor.RunInput{
workflowResult, err := workflowexecutor.NewExecutor().Execute(ctx, workflowexecutor.Input{
Definition: workflow.Definition,
Conversation: req.Conversation,
UserMessage: req.UserMessage,
AIAgent: req.AIAgent,
AIConfig: req.AIConfig,
CheckPointID: req.CheckPointID,
ToolSet: req.ToolSet,
})
if err != nil {
return toSummary(summary), err
return nil, err
}
return toSummary(summary), nil
if err := writeWorkflowRun(req, workflow, workflowResult, ""); err != nil {
return nil, err
}
return toWorkflowSummary(workflowResult, req.AIConfig.ModelName), nil
}
func (s *Service) Resume(ctx context.Context, req ResumeRequest) (*Summary, error) {
aiAgent, err := prepareWorkflowAgent(req.AIAgent)
aiAgent, _, err := prepareWorkflowAgent(req.AIAgent)
if err != nil {
return nil, err
}
@@ -72,3 +76,65 @@ func (s *Service) Resume(ctx context.Context, req ResumeRequest) (*Summary, erro
}
return toSummary(summary), nil
}
func toWorkflowSummary(result *workflowexecutor.Result, modelName string) *Summary {
if result == nil {
return nil
}
trace := map[string]any{
"status": result.Status,
"nodePath": result.NodePath,
}
traceData, _ := json.Marshal(trace)
return &Summary{
Status: result.Status,
ReplyText: result.ReplyText,
ModelName: modelName,
PromptTokens: result.PromptTokens,
CompletionTokens: result.CompletionTokens,
RetrieverCount: result.RetrieverCount,
TraceData: string(traceData),
}
}
func writeWorkflowRun(req Request, workflow resolvedWorkflow, result *workflowexecutor.Result, errorMessage string) error {
if result == nil {
return nil
}
now := time.Now()
endedAt := now
nodeTypes := make(map[string]string, len(workflow.Definition.Nodes))
for _, node := range workflow.Definition.Nodes {
nodeTypes[node.ID] = node.Type
}
return sqls.WithTransaction(func(ctx *sqls.TxContext) error {
run := &models.AIWorkflowRun{
WorkflowID: workflow.WorkflowID,
WorkflowVersionID: workflow.VersionID,
ConversationID: req.Conversation.ID,
AIAgentID: req.AIAgent.ID,
MessageID: req.UserMessage.ID,
Status: 1,
StartedAt: now,
EndedAt: &endedAt,
ErrorMessage: errorMessage,
}
if err := repositories.AIWorkflowRunRepository.Create(ctx.Tx, run); err != nil {
return err
}
for _, nodeID := range result.NodePath {
nodeRun := &models.AIWorkflowNodeRun{
WorkflowRunID: run.ID,
NodeID: nodeID,
NodeType: nodeTypes[nodeID],
Status: 1,
StartedAt: now,
EndedAt: &endedAt,
}
if err := repositories.AIWorkflowNodeRunRepository.Create(ctx.Tx, nodeRun); err != nil {
return err
}
}
return nil
})
}