adk-go icon indicating copy to clipboard operation
adk-go copied to clipboard

[Bug] llmagent is only compatible with functiontool where input is a struct

Open yarolegovich opened this issue 1 month ago • 1 comments

Problem

functiontool can be used in contexts other than llmagent so any Type parameter constraints make sense:

type Func[TArgs, TResults any] func(tool.Context, TArgs) (TResults, error)

But llmagent is incompatible with functiontools where input is a non-struct type, because genai.FunctionCall.Args is a map:

Args map[string]any `json:"args,omitempty"`

The result is that an agent can never succeed in calling such tool.

Desired behavior

One of:

  1. Validate tools in llmagent.New and report tool incompatibility as an error.
  2. Make llmagent wrap such tools in a special decorator which will be handling unboxing of llm-provided arguments of form like map[string]any{"input": arg}. It will need to override input schema as well.

Reproduction

The agent will never succeed in running the super_tool:

func main() {
	ctx := context.Background()

	model, err := gemini.NewModel(ctx, "gemini-2.5-flash", &genai.ClientConfig{
		APIKey: os.Getenv("GOOGLE_API_KEY"),
	})
	if err != nil {
		log.Fatalf("Failed to create model: %v", err)
	}

	superTool, err := functiontool.New(functiontool.Config{Name: "super_tool"}, functiontool.Func[string, string](
		func(ctx tool.Context, input string) (string, error) {
			return "Hello", nil
		},
	))
	if err != nil {
		log.Fatalf("Failed to create a tool: %v", err)
	}

	a, err := llmagent.New(llmagent.Config{
		Name:        "super_tool_caller",
		Model:       model,
		Description: "Agent to invoke the super_tool",
		Instruction: "Your SOLE purpose is to invoke the super_tool and pass the result to me.",
		Tools:       []tool.Tool{superTool},
	})
	if err != nil {
		log.Fatalf("Failed to create agent: %v", err)
	}

	l := full.NewLauncher()
	if err = l.Execute(ctx, &launcher.Config{AgentLoader: agent.NewSingleLoader(a)}, os.Args[1:]); err != nil {
		log.Fatalf("Run failed: %v\n\n%s", err, l.CommandLineSyntax())
	}
}

yarolegovich avatar Nov 21 '25 08:11 yarolegovich

Hi Yaroslav,

Thanks for the detailed bug report. I agree, and I prefer your 1st suggestion: Validate tools in llmagent.New and report incompatibility as an error.

This approach is more explicit and easier to maintain. Relaxing validation later is safer than changing implicit decorator behavior, which could break existing users.

mazas-google avatar Nov 24 '25 17:11 mazas-google