diff --git a/core/agent/prompt.go b/core/agent/prompt.go index f1a68ed..b012760 100644 --- a/core/agent/prompt.go +++ b/core/agent/prompt.go @@ -1,101 +1,6 @@ package agent -import ( - "fmt" - "strings" - - "github.com/mudler/LocalAgent/pkg/xlog" - "github.com/traefik/yaegi/interp" - "github.com/traefik/yaegi/stdlib" -) - type PromptBlock interface { Render(a *Agent) (string, error) Role() string } - -type DynamicPrompt struct { - config map[string]string - goPkgPath string - i *interp.Interpreter -} - -func NewDynamicPrompt(config map[string]string, goPkgPath string) (*DynamicPrompt, error) { - a := &DynamicPrompt{ - config: config, - goPkgPath: goPkgPath, - } - - if err := a.initializeInterpreter(); err != nil { - return nil, err - } - - if err := a.callInit(); err != nil { - xlog.Error("Error calling custom action init", "error", err) - } - - return a, nil -} - -func (a *DynamicPrompt) callInit() error { - if a.i == nil { - return nil - } - - v, err := a.i.Eval(fmt.Sprintf("%s.Init", a.config["name"])) - if err != nil { - return err - } - - run := v.Interface().(func() error) - - return run() -} - -func (a *DynamicPrompt) initializeInterpreter() error { - if _, exists := a.config["code"]; exists && a.i == nil { - unsafe := strings.ToLower(a.config["unsafe"]) == "true" - i := interp.New(interp.Options{ - GoPath: a.goPkgPath, - Unrestricted: unsafe, - }) - if err := i.Use(stdlib.Symbols); err != nil { - return err - } - - if _, exists := a.config["name"]; !exists { - a.config["name"] = "custom" - } - - _, err := i.Eval(fmt.Sprintf("package %s\n%s", a.config["name"], a.config["code"])) - if err != nil { - return err - } - - a.i = i - } - - return nil -} - -func (a *DynamicPrompt) Render(c *Agent) (string, error) { - v, err := a.i.Eval(fmt.Sprintf("%s.Render", a.config["name"])) - if err != nil { - return "", err - } - - run := v.Interface().(func() (string, error)) - - return run() -} - -func (a *DynamicPrompt) Role() string { - v, err := a.i.Eval(fmt.Sprintf("%s.Role", a.config["name"])) - if err != nil { - return "system" - } - - run := v.Interface().(func() string) - - return run() -} diff --git a/main.go b/main.go index daac218..455f6c0 100644 --- a/main.go +++ b/main.go @@ -6,6 +6,7 @@ import ( "path/filepath" "github.com/mudler/LocalAgent/core/state" + "github.com/mudler/LocalAgent/services" "github.com/mudler/LocalAgent/webui" ) @@ -47,9 +48,9 @@ func main() { apiKey, stateDir, localRAG, - webui.Actions, - webui.Connectors, - webui.PromptBlocks, + services.Actions, + services.Connectors, + services.PromptBlocks, timeout, ) if err != nil { diff --git a/webui/actions.go b/services/actions.go similarity index 99% rename from webui/actions.go rename to services/actions.go index c96b23d..ad2f0a9 100644 --- a/webui/actions.go +++ b/services/actions.go @@ -1,4 +1,4 @@ -package webui +package services import ( "context" diff --git a/webui/connectors.go b/services/connectors.go similarity index 98% rename from webui/connectors.go rename to services/connectors.go index b092962..0d74454 100644 --- a/webui/connectors.go +++ b/services/connectors.go @@ -1,4 +1,4 @@ -package webui +package services import ( "encoding/json" diff --git a/webui/prompts.go b/services/prompts.go similarity index 87% rename from webui/prompts.go rename to services/prompts.go index cbb9e42..b8335ec 100644 --- a/webui/prompts.go +++ b/services/prompts.go @@ -1,9 +1,10 @@ -package webui +package services import ( "encoding/json" "github.com/mudler/LocalAgent/pkg/xlog" + "github.com/mudler/LocalAgent/services/prompts" "github.com/mudler/LocalAgent/core/agent" "github.com/mudler/LocalAgent/core/state" @@ -29,7 +30,7 @@ func PromptBlocks(a *state.AgentConfig) []agent.PromptBlock { } switch c.Type { case DynamicPromptCustom: - prompt, err := agent.NewDynamicPrompt(config, "") + prompt, err := prompts.NewDynamicPrompt(config, "") if err != nil { xlog.Error("Error creating custom prompt", "error", err) continue diff --git a/services/prompts/custom.go b/services/prompts/custom.go new file mode 100644 index 0000000..d1fcbea --- /dev/null +++ b/services/prompts/custom.go @@ -0,0 +1,97 @@ +package prompts + +import ( + "fmt" + "strings" + + "github.com/mudler/LocalAgent/core/agent" + "github.com/mudler/LocalAgent/pkg/xlog" + "github.com/traefik/yaegi/interp" + "github.com/traefik/yaegi/stdlib" +) + +type DynamicPrompt struct { + config map[string]string + goPkgPath string + i *interp.Interpreter +} + +func NewDynamicPrompt(config map[string]string, goPkgPath string) (*DynamicPrompt, error) { + a := &DynamicPrompt{ + config: config, + goPkgPath: goPkgPath, + } + + if err := a.initializeInterpreter(); err != nil { + return nil, err + } + + if err := a.callInit(); err != nil { + xlog.Error("Error calling custom action init", "error", err) + } + + return a, nil +} + +func (a *DynamicPrompt) callInit() error { + if a.i == nil { + return nil + } + + v, err := a.i.Eval(fmt.Sprintf("%s.Init", a.config["name"])) + if err != nil { + return err + } + + run := v.Interface().(func() error) + + return run() +} + +func (a *DynamicPrompt) initializeInterpreter() error { + if _, exists := a.config["code"]; exists && a.i == nil { + unsafe := strings.ToLower(a.config["unsafe"]) == "true" + i := interp.New(interp.Options{ + GoPath: a.goPkgPath, + Unrestricted: unsafe, + }) + if err := i.Use(stdlib.Symbols); err != nil { + return err + } + + if _, exists := a.config["name"]; !exists { + a.config["name"] = "custom" + } + + _, err := i.Eval(fmt.Sprintf("package %s\n%s", a.config["name"], a.config["code"])) + if err != nil { + return err + } + + a.i = i + } + + return nil +} + +func (a *DynamicPrompt) Render(c *agent.Agent) (string, error) { + v, err := a.i.Eval(fmt.Sprintf("%s.Render", a.config["name"])) + if err != nil { + return "", err + } + + run := v.Interface().(func() (string, error)) + + return run() +} + +func (a *DynamicPrompt) Role() string { + v, err := a.i.Eval(fmt.Sprintf("%s.Role", a.config["name"])) + if err != nil { + return "system" + } + + run := v.Interface().(func() string) + + return run() +} diff --git a/webui/routes.go b/webui/routes.go index 48075d5..d996438 100644 --- a/webui/routes.go +++ b/webui/routes.go @@ -10,6 +10,7 @@ import ( "github.com/mudler/LocalAgent/core/agent" "github.com/mudler/LocalAgent/core/sse" "github.com/mudler/LocalAgent/core/state" + "github.com/mudler/LocalAgent/services" ) //go:embed views/* @@ -45,9 +46,9 @@ func (app *App) registerRoutes(pool *state.AgentPool, webapp *fiber.App) { webapp.Get("/create", func(c *fiber.Ctx) error { return c.Render("views/create", fiber.Map{ - "Actions": AvailableActions, - "Connectors": AvailableConnectors, - "PromptBlocks": AvailableBlockPrompts, + "Actions": services.AvailableActions, + "Connectors": services.AvailableConnectors, + "PromptBlocks": services.AvailableBlockPrompts, }) }) @@ -97,8 +98,6 @@ func (app *App) registerRoutes(pool *state.AgentPool, webapp *fiber.App) { }) webapp.Post("/settings/import", app.ImportAgent(pool)) webapp.Get("/settings/export/:name", app.ExportAgent(pool)) - - return } var letterRunes = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ")