Refactor AIAgent runtime handling and remove unused fields
This commit is contained in:
@@ -24,7 +24,11 @@ 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)
|
||||
req.AIAgent = applyWorkflowInstruction(req.AIAgent)
|
||||
aiAgent, 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
|
||||
@@ -45,7 +49,11 @@ func (s *Service) Run(ctx context.Context, req Request) (*Summary, error) {
|
||||
}
|
||||
|
||||
func (s *Service) Resume(ctx context.Context, req ResumeRequest) (*Summary, error) {
|
||||
req.AIAgent = applyWorkflowInstruction(req.AIAgent)
|
||||
aiAgent, err := prepareWorkflowAgent(req.AIAgent)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
req.AIAgent = aiAgent
|
||||
toolSet, err := s.prepare.prepareToolsForResume(req)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
||||
@@ -82,7 +82,7 @@ func (c *toolCatalog) parseAgentAllowedToolCodes(aiAgent models.AIAgent) []strin
|
||||
ret = append(ret, graphTools...)
|
||||
}
|
||||
}
|
||||
if result, ok := resolveAgentWorkflow(aiAgent); ok {
|
||||
if result, err := resolveAgentWorkflow(aiAgent); err == nil {
|
||||
ret = append(ret, result.ToolCodes...)
|
||||
}
|
||||
return toolx.NormalizeToolCodes(ret)
|
||||
|
||||
@@ -85,7 +85,6 @@ func TestToolCatalogIncludesPublishedWorkflowGraphTools(t *testing.T) {
|
||||
|
||||
catalog := newToolCatalog()
|
||||
ret := catalog.parseAgentAllowedToolCodes(models.AIAgent{
|
||||
RuntimeMode: enums.AIAgentRuntimeModeWorkflow,
|
||||
WorkflowVersionID: version.ID,
|
||||
})
|
||||
|
||||
@@ -94,7 +93,7 @@ func TestToolCatalogIncludesPublishedWorkflowGraphTools(t *testing.T) {
|
||||
assertContainsToolCode(t, ret, toolx.GraphHandoffConversation.Code)
|
||||
}
|
||||
|
||||
func TestApplyWorkflowInstructionAppendsPublishedWorkflow(t *testing.T) {
|
||||
func TestPrepareWorkflowAgentAppendsPublishedWorkflow(t *testing.T) {
|
||||
setupWorkflowRuntimeTestDB(t)
|
||||
version := createWorkflowRuntimeTestVersion(t, dsl.Definition{
|
||||
SchemaVersion: 1,
|
||||
@@ -105,11 +104,13 @@ func TestApplyWorkflowInstructionAppendsPublishedWorkflow(t *testing.T) {
|
||||
},
|
||||
})
|
||||
|
||||
agent := applyWorkflowInstruction(models.AIAgent{
|
||||
agent, err := prepareWorkflowAgent(models.AIAgent{
|
||||
SystemPrompt: "Base prompt.",
|
||||
RuntimeMode: enums.AIAgentRuntimeModeWorkflow,
|
||||
WorkflowVersionID: version.ID,
|
||||
})
|
||||
if err != nil {
|
||||
t.Fatalf("prepare workflow agent: %v", err)
|
||||
}
|
||||
if agent.SystemPrompt == "Base prompt." {
|
||||
t.Fatalf("expected workflow appendix to be appended")
|
||||
}
|
||||
@@ -118,6 +119,39 @@ func TestApplyWorkflowInstructionAppendsPublishedWorkflow(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestPrepareWorkflowAgentRejectsMissingPublishedWorkflow(t *testing.T) {
|
||||
_, err := prepareWorkflowAgent(models.AIAgent{})
|
||||
if err == nil {
|
||||
t.Fatalf("expected missing workflow version error")
|
||||
}
|
||||
if !strings.Contains(err.Error(), "workflow version is required") {
|
||||
t.Fatalf("unexpected error: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestPrepareWorkflowAgentRejectsDeletedPublishedWorkflow(t *testing.T) {
|
||||
setupWorkflowRuntimeTestDB(t)
|
||||
version := createWorkflowRuntimeTestVersion(t, dsl.Definition{
|
||||
SchemaVersion: 1,
|
||||
EntryNodeID: "start",
|
||||
Nodes: []dsl.Node{
|
||||
{ID: "start", Type: workflowregistry.NodeTypeStart, Name: "Start"},
|
||||
{ID: "end", Type: workflowregistry.NodeTypeEnd, Name: "End"},
|
||||
},
|
||||
})
|
||||
if err := sqls.DB().Model(&models.AIWorkflowVersion{}).Where("id = ?", version.ID).Update("status", enums.StatusDeleted).Error; err != nil {
|
||||
t.Fatalf("delete workflow version: %v", err)
|
||||
}
|
||||
|
||||
_, err := prepareWorkflowAgent(models.AIAgent{WorkflowVersionID: version.ID})
|
||||
if err == nil {
|
||||
t.Fatalf("expected invalid workflow version error")
|
||||
}
|
||||
if !strings.Contains(err.Error(), "workflow version does not exist") {
|
||||
t.Fatalf("unexpected error: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func setupWorkflowRuntimeTestDB(t *testing.T) {
|
||||
t.Helper()
|
||||
db, err := gorm.Open(sqlite.Open("file:"+t.Name()+"?mode=memory&cache=shared"), &gorm.Config{})
|
||||
|
||||
@@ -8,37 +8,41 @@ import (
|
||||
"agent-desk/internal/ai/workflow/dsl"
|
||||
"agent-desk/internal/models"
|
||||
"agent-desk/internal/pkg/enums"
|
||||
"agent-desk/internal/pkg/errorsx"
|
||||
"agent-desk/internal/repositories"
|
||||
|
||||
"github.com/mlogclub/simple/sqls"
|
||||
)
|
||||
|
||||
func resolveAgentWorkflow(aiAgent models.AIAgent) (compiler.Result, bool) {
|
||||
if aiAgent.RuntimeMode != enums.AIAgentRuntimeModeWorkflow || aiAgent.WorkflowVersionID <= 0 {
|
||||
return compiler.Result{}, false
|
||||
func resolveAgentWorkflow(aiAgent models.AIAgent) (compiler.Result, error) {
|
||||
if aiAgent.WorkflowVersionID <= 0 {
|
||||
return compiler.Result{}, errorsx.InvalidParam("workflow version is required")
|
||||
}
|
||||
version := repositories.AIWorkflowVersionRepository.Get(sqls.DB(), aiAgent.WorkflowVersionID)
|
||||
if version == nil || version.Status != enums.StatusOk {
|
||||
return compiler.Result{}, false
|
||||
return compiler.Result{}, errorsx.InvalidParam("workflow version does not exist")
|
||||
}
|
||||
var def dsl.Definition
|
||||
if err := json.Unmarshal([]byte(version.Definition), &def); err != nil {
|
||||
return compiler.Result{}, false
|
||||
return compiler.Result{}, errorsx.InvalidParam("workflow definition is invalid")
|
||||
}
|
||||
return compiler.Compile(def), true
|
||||
return compiler.Compile(def), nil
|
||||
}
|
||||
|
||||
func applyWorkflowInstruction(aiAgent models.AIAgent) models.AIAgent {
|
||||
result, ok := resolveAgentWorkflow(aiAgent)
|
||||
if !ok || strings.TrimSpace(result.Appendix) == "" {
|
||||
return aiAgent
|
||||
func prepareWorkflowAgent(aiAgent models.AIAgent) (models.AIAgent, error) {
|
||||
result, err := resolveAgentWorkflow(aiAgent)
|
||||
if err != nil {
|
||||
return aiAgent, err
|
||||
}
|
||||
if strings.TrimSpace(result.Appendix) == "" {
|
||||
return aiAgent, nil
|
||||
}
|
||||
prompt := strings.TrimSpace(aiAgent.SystemPrompt)
|
||||
appendix := strings.TrimSpace(result.Appendix)
|
||||
if prompt == "" {
|
||||
aiAgent.SystemPrompt = appendix
|
||||
return aiAgent
|
||||
return aiAgent, nil
|
||||
}
|
||||
aiAgent.SystemPrompt = prompt + "\n\n" + appendix
|
||||
return aiAgent
|
||||
return aiAgent, nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user