Skip to content

Function Tools

David-Andrew Samson edited this page Aug 26, 2024 · 5 revisions

Creating a function tool

Function tools are the simplest way to build custom tools for a ReActAgent

  1. create your function
  2. add type annotations
  3. add a docstring (with matching type information)
  4. add the @tool decorator
from archytas.tool_utils import tool

@tool
def myTool(a:int, b:str, c:bool, d:dict=None) -> dict:
    """
    Simple description of what myTool does

    More detailed description of the tool. This can be multiple lines.
    Explain more what the tool does, and what it is used for. 
    Do not use python syntax in the description (since the LLM doesn't call functions that way).

    Args:
        a (int): Description of a
        b (str): Description of b
        c (bool): Description of c
        d (dict): Description of d. Defaults to {}.

    Returns:
        dict: Description of the return value
    """
    #set d to default
    if d is None: d = {}

    # do something with a, b, c, d
    # result = ...
    return result

Notes:

  • functions can have zero or more arguments so long as they are all valid python equivalents of json object types:
    • int, float, str, list, dict, None
  • currently union types (e.g. int|bool, str|list|None, etc.) are not supported in the argument types

@tool decorator

The tool decorator servers two main functions:

  1. creates the prompt description for the tool that the LLM sees:

    myTool:
        Simple description of what myTool does
    
        More detailed description of the tool. This can be multiple lines.
        Explain more what the tool does, and what it is used for. 
        Do not use python syntax in the description (since the LLM doesn't call functions that way).
    
        _input_: a json object with the following fields:
        {
            "a": # (int) Description of a
            "b": # (str) Description of b
            "c": # (bool) Description of c
            "d": # (dict, optional) Description of d. Defaults to {}.
        }
        _output_: (dict) Description of the return value
    

    This prompt is generated directly from the function signature and docstring. The docstring is parsed to extract the short description, long description, input arguments, and return value. Depending on the input arguments, Archytas determines a suitable format for the input, and describes that format in the prompt. E.g. this multiple argument example uses a json object as the input, but if the tool input was simpler, e.g. a single string, then the format can be simpler as well.

  2. manages calling the function and passing the results to the LLM

    • Normally all communication with the LLM is handled as string in, string out, so the @tool decorator manages the conversion from string to the correct types, and then converting the results back to a string the LLM can understand

For example, if an agent wanted to call this tool, it would output the following json:

{
    "thought": "I need to use myTool to complete the task",
    "tool": "myTool",
    "tool_input": {
        "a": 5,
        "b": "some input",
        "c": true,
        "d": {"override":42}
    }
}

which then gets parsed and passed into myTool

# this example skips a lot of validation and other machinery

# convert llm response to json
action_input = json.loads(llm_response)

# pull out the function input json 
# should be an object with keys a, b, c and optionally d
tool_input = action_input['tool_input']

# pull the function out of the tool dict
tool_name = action_input['tool']
func = tools_dict[tool_name]

# call the function
result = func(**tool_input)