From 6695cd1da845b03720ff994485875b62c4547dfa Mon Sep 17 00:00:00 2001 From: Jason Date: Tue, 26 Mar 2024 12:24:34 -0700 Subject: [PATCH 01/12] add warning if duplicate function is registereed --- autogen/agentchat/conversable_agent.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/autogen/agentchat/conversable_agent.py b/autogen/agentchat/conversable_agent.py index 54206b55052..0ab423d4ffe 100644 --- a/autogen/agentchat/conversable_agent.py +++ b/autogen/agentchat/conversable_agent.py @@ -130,6 +130,7 @@ def __init__( self._name = name # a dictionary of conversations, default value is list self._oai_messages = defaultdict(list) + self._registered_tools = {} self._oai_system_message = [{"content": system_message, "role": "system"}] self._description = description if description is not None else system_message self._is_termination_msg = ( @@ -2552,6 +2553,9 @@ def _decorator(func: F) -> F: elif not hasattr(func, "_name"): func._name = func.__name__ + if func._name in self._registered_tools: + warnings.warn(f"Function '{func._name}' is being overridden.", UserWarning) + self.register_function({func._name: self._wrap_function(func)}) return func From 836981de8065d015456f012bfe848d5036d3821f Mon Sep 17 00:00:00 2001 From: Jason Date: Tue, 26 Mar 2024 13:05:53 -0700 Subject: [PATCH 02/12] check _function_map and llm_config --- autogen/agentchat/conversable_agent.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/autogen/agentchat/conversable_agent.py b/autogen/agentchat/conversable_agent.py index 0ab423d4ffe..d77b728ef7c 100644 --- a/autogen/agentchat/conversable_agent.py +++ b/autogen/agentchat/conversable_agent.py @@ -130,7 +130,6 @@ def __init__( self._name = name # a dictionary of conversations, default value is list self._oai_messages = defaultdict(list) - self._registered_tools = {} self._oai_system_message = [{"content": system_message, "role": "system"}] self._description = description if description is not None else system_message self._is_termination_msg = ( @@ -2552,8 +2551,7 @@ def _decorator(func: F) -> F: func._name = name elif not hasattr(func, "_name"): func._name = func.__name__ - - if func._name in self._registered_tools: + if func._name in self._function_map or (llm_config and tools in llm_config.keys() and func._name in llm_config["tools"]): warnings.warn(f"Function '{func._name}' is being overridden.", UserWarning) self.register_function({func._name: self._wrap_function(func)}) From bb5fa59311a3788a2cdbb63ef9947971d4234769 Mon Sep 17 00:00:00 2001 From: Jason Date: Tue, 26 Mar 2024 15:54:04 -0700 Subject: [PATCH 03/12] check function_map and llm_config --- autogen/agentchat/conversable_agent.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/autogen/agentchat/conversable_agent.py b/autogen/agentchat/conversable_agent.py index 88042c0dd50..7cc4028c458 100644 --- a/autogen/agentchat/conversable_agent.py +++ b/autogen/agentchat/conversable_agent.py @@ -2550,7 +2550,8 @@ def _decorator(func: F) -> F: func._name = name elif not hasattr(func, "_name"): func._name = func.__name__ - if func._name in self._function_map or (llm_config and tools in llm_config.keys() and func._name in llm_config["tools"]): + + if (func._name in self._function_map) or (self.llm_config and "tools" in self.llm_config.keys() and func._name in [tool["function"]["name"] for tool in self.llm_config["tools"]]): warnings.warn(f"Function '{func._name}' is being overridden.", UserWarning) self.register_function({func._name: self._wrap_function(func)}) From 3a35ba87cb8a1c402b4ec91d9fed2dfafa13b6ae Mon Sep 17 00:00:00 2001 From: Jason Date: Tue, 26 Mar 2024 17:35:50 -0700 Subject: [PATCH 04/12] use register_function and llm_config --- autogen/agentchat/conversable_agent.py | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/autogen/agentchat/conversable_agent.py b/autogen/agentchat/conversable_agent.py index 7cc4028c458..4d41a79613a 100644 --- a/autogen/agentchat/conversable_agent.py +++ b/autogen/agentchat/conversable_agent.py @@ -2284,6 +2284,8 @@ def register_function(self, function_map: Dict[str, Union[Callable, None]]): self._assert_valid_name(name) if func is None and name not in self._function_map.keys(): warnings.warn(f"The function {name} to remove doesn't exist", name) + if name in self._function_map.keys(): + warnings.warn(f"Function '{name}' is being overridden.", UserWarning) self._function_map.update(function_map) self._function_map = {k: v for k, v in self._function_map.items() if v is not None} @@ -2320,6 +2322,9 @@ def update_function_signature(self, func_sig: Union[str, Dict], is_remove: None) self._assert_valid_name(func_sig["name"]) if "functions" in self.llm_config.keys(): + if any(func["name"] == func_sig["name"] for func in self.llm_config["functions"]): + warnings.warn(f"Function '{func_sig['name']}' is being overridden.", UserWarning) + self.llm_config["functions"] = [ func for func in self.llm_config["functions"] if func.get("name") != func_sig["name"] ] + [func_sig] @@ -2359,6 +2364,8 @@ def update_tool_signature(self, tool_sig: Union[str, Dict], is_remove: None): f"The tool signature must be of the type dict. Received tool signature type {type(tool_sig)}" ) self._assert_valid_name(tool_sig["function"]["name"]) + if any(tool["function"]["name"] == tool_sig["function"]["name"] for tool in self.llm_config["tools"]): + warnings.warn(f"Function '{tool_sig['function']['name']}' is being overridden.", UserWarning) if "tools" in self.llm_config.keys(): self.llm_config["tools"] = [ tool @@ -2551,8 +2558,6 @@ def _decorator(func: F) -> F: elif not hasattr(func, "_name"): func._name = func.__name__ - if (func._name in self._function_map) or (self.llm_config and "tools" in self.llm_config.keys() and func._name in [tool["function"]["name"] for tool in self.llm_config["tools"]]): - warnings.warn(f"Function '{func._name}' is being overridden.", UserWarning) self.register_function({func._name: self._wrap_function(func)}) From 68c723708400516743a967a670454f86a0218bd7 Mon Sep 17 00:00:00 2001 From: Jason Date: Tue, 26 Mar 2024 17:37:27 -0700 Subject: [PATCH 05/12] cleanups --- autogen/agentchat/conversable_agent.py | 1 - 1 file changed, 1 deletion(-) diff --git a/autogen/agentchat/conversable_agent.py b/autogen/agentchat/conversable_agent.py index 389f1a545b5..24d3ad19d05 100644 --- a/autogen/agentchat/conversable_agent.py +++ b/autogen/agentchat/conversable_agent.py @@ -2586,7 +2586,6 @@ def _decorator(func: F) -> F: elif not hasattr(func, "_name"): func._name = func.__name__ - self.register_function({func._name: self._wrap_function(func)}) return func From 0aa5446d07098a769639ebc6a9e25829572ed298 Mon Sep 17 00:00:00 2001 From: Jason Date: Wed, 27 Mar 2024 08:00:45 -0700 Subject: [PATCH 06/12] cleanups --- autogen/agentchat/conversable_agent.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/autogen/agentchat/conversable_agent.py b/autogen/agentchat/conversable_agent.py index 24d3ad19d05..96df9408832 100644 --- a/autogen/agentchat/conversable_agent.py +++ b/autogen/agentchat/conversable_agent.py @@ -2312,7 +2312,7 @@ def register_function(self, function_map: Dict[str, Union[Callable, None]]): self._assert_valid_name(name) if func is None and name not in self._function_map.keys(): warnings.warn(f"The function {name} to remove doesn't exist", name) - if name in self._function_map.keys(): + if name in self._function_map: warnings.warn(f"Function '{name}' is being overridden.", UserWarning) self._function_map.update(function_map) self._function_map = {k: v for k, v in self._function_map.items() if v is not None} @@ -2392,9 +2392,9 @@ def update_tool_signature(self, tool_sig: Union[str, Dict], is_remove: None): f"The tool signature must be of the type dict. Received tool signature type {type(tool_sig)}" ) self._assert_valid_name(tool_sig["function"]["name"]) - if any(tool["function"]["name"] == tool_sig["function"]["name"] for tool in self.llm_config["tools"]): - warnings.warn(f"Function '{tool_sig['function']['name']}' is being overridden.", UserWarning) - if "tools" in self.llm_config.keys(): + if "tools" in self.llm_config: + if any(tool["function"]["name"] == tool_sig["function"]["name"] for tool in self.llm_config["tools"]): + warnings.warn(f"Function '{tool_sig['function']['name']}' is being overridden.", UserWarning) self.llm_config["tools"] = [ tool for tool in self.llm_config["tools"] From 98142edab980b05b0ac84fe2a7c0338294d2a74c Mon Sep 17 00:00:00 2001 From: Jason Date: Wed, 27 Mar 2024 17:28:02 -0700 Subject: [PATCH 07/12] warning test --- test/agentchat/test_conversable_agent.py | 27 ++++++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/test/agentchat/test_conversable_agent.py b/test/agentchat/test_conversable_agent.py index 6d9c1ac3246..fee60dfb442 100755 --- a/test/agentchat/test_conversable_agent.py +++ b/test/agentchat/test_conversable_agent.py @@ -1263,6 +1263,32 @@ def test_messages_with_carryover(): with pytest.raises(InvalidCarryOverType): agent1.generate_init_message(**context) +def test_adding_duplicate_function_warning(): + agent = autogen.ConversableAgent( + "jason", + llm_config=False + ) + + # Define a sample function + def sample_function(): + pass + + # Register the function for the first time + agent.register_function( + function_map={ + "sample_function": sample_function, + } + ) + + # Try to register the same function again and check for a warning + with pytest.warns(UserWarning, match="Function 'sample_function' is being overridden."): + agent.register_function( + function_map={ + "sample_function": sample_function, + } + ) + + if __name__ == "__main__": # test_trigger() @@ -1275,3 +1301,4 @@ def test_messages_with_carryover(): # test_process_before_send() test_message_func() test_summary() + test_adding_duplicate_function_warning() From ff564f9a86127d7a63239af9f4079a21630a46eb Mon Sep 17 00:00:00 2001 From: Jason Date: Wed, 27 Mar 2024 17:30:53 -0700 Subject: [PATCH 08/12] warning test --- test/agentchat/test_conversable_agent.py | 3 --- 1 file changed, 3 deletions(-) diff --git a/test/agentchat/test_conversable_agent.py b/test/agentchat/test_conversable_agent.py index fee60dfb442..44201b60835 100755 --- a/test/agentchat/test_conversable_agent.py +++ b/test/agentchat/test_conversable_agent.py @@ -1269,18 +1269,15 @@ def test_adding_duplicate_function_warning(): llm_config=False ) - # Define a sample function def sample_function(): pass - # Register the function for the first time agent.register_function( function_map={ "sample_function": sample_function, } ) - # Try to register the same function again and check for a warning with pytest.warns(UserWarning, match="Function 'sample_function' is being overridden."): agent.register_function( function_map={ From 8aa7f6f6cf4210c050b53e7a533af5ea19a788c1 Mon Sep 17 00:00:00 2001 From: Jason Date: Fri, 29 Mar 2024 16:47:27 -0700 Subject: [PATCH 09/12] more test coverage --- test/agentchat/test_conversable_agent.py | 46 ++++++++++++++++++++++-- 1 file changed, 43 insertions(+), 3 deletions(-) diff --git a/test/agentchat/test_conversable_agent.py b/test/agentchat/test_conversable_agent.py index 44201b60835..87045ee2e7e 100755 --- a/test/agentchat/test_conversable_agent.py +++ b/test/agentchat/test_conversable_agent.py @@ -1263,10 +1263,19 @@ def test_messages_with_carryover(): with pytest.raises(InvalidCarryOverType): agent1.generate_init_message(**context) + def test_adding_duplicate_function_warning(): + config_list = autogen.config_list_from_json( + OAI_CONFIG_LIST, + file_location=KEY_LOC, + ) + agent = autogen.ConversableAgent( - "jason", - llm_config=False + "jtoy", + llm_config={ + "config_list": config_list, + "model": "gpt-3.5-turbo-0613", + }, ) def sample_function(): @@ -1277,6 +1286,21 @@ def sample_function(): "sample_function": sample_function, } ) + agent.update_function_signature( + { + "name": "foo", + }, + is_remove=False, + ) + agent.update_tool_signature( + { + "type": "function", + "function": { + "name": "yo", + }, + }, + is_remove=False, + ) with pytest.warns(UserWarning, match="Function 'sample_function' is being overridden."): agent.register_function( @@ -1284,7 +1308,23 @@ def sample_function(): "sample_function": sample_function, } ) - + with pytest.warns(UserWarning, match="Function 'foo' is being overridden."): + agent.update_function_signature( + { + "name": "foo", + }, + is_remove=False, + ) + with pytest.warns(UserWarning, match="Function 'yo' is being overridden."): + agent.update_tool_signature( + { + "type": "function", + "function": { + "name": "yo", + }, + }, + is_remove=False, + ) if __name__ == "__main__": From e9367d00266c623693b97a594f74810243a2203c Mon Sep 17 00:00:00 2001 From: Jason Date: Fri, 17 May 2024 09:08:23 -0700 Subject: [PATCH 10/12] use a fake config --- test/agentchat/test_conversable_agent.py | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/test/agentchat/test_conversable_agent.py b/test/agentchat/test_conversable_agent.py index f284530e855..275b1611bd3 100755 --- a/test/agentchat/test_conversable_agent.py +++ b/test/agentchat/test_conversable_agent.py @@ -1404,16 +1404,15 @@ def test_http_client(): def test_adding_duplicate_function_warning(): - config_list = autogen.config_list_from_json( - OAI_CONFIG_LIST, - file_location=KEY_LOC, - ) + config_base = [{ + "base_url": "http://0.0.0.0:8000", + "api_key": "NULL" + }] agent = autogen.ConversableAgent( "jtoy", llm_config={ - "config_list": config_list, - "model": "gpt-3.5-turbo-0613", + "config_list": config_base }, ) From b6e5b8ae90e7c3ea54e4739d420007fb00841916 Mon Sep 17 00:00:00 2001 From: Jason Date: Fri, 17 May 2024 09:14:46 -0700 Subject: [PATCH 11/12] formatting --- test/agentchat/test_conversable_agent.py | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) diff --git a/test/agentchat/test_conversable_agent.py b/test/agentchat/test_conversable_agent.py index 275b1611bd3..209e85337b9 100755 --- a/test/agentchat/test_conversable_agent.py +++ b/test/agentchat/test_conversable_agent.py @@ -1404,16 +1404,12 @@ def test_http_client(): def test_adding_duplicate_function_warning(): - config_base = [{ - "base_url": "http://0.0.0.0:8000", - "api_key": "NULL" - }] + + config_base = [{"base_url": "http://0.0.0.0:8000", "api_key": "NULL"}] agent = autogen.ConversableAgent( "jtoy", - llm_config={ - "config_list": config_base - }, + llm_config={"config_list": config_base}, ) def sample_function(): From 2fd34b751d63ecf53d8a46fe50cf238d95af0224 Mon Sep 17 00:00:00 2001 From: Jason Date: Fri, 17 May 2024 09:30:24 -0700 Subject: [PATCH 12/12] formatting --- test/agentchat/test_conversable_agent.py | 1 - 1 file changed, 1 deletion(-) diff --git a/test/agentchat/test_conversable_agent.py b/test/agentchat/test_conversable_agent.py index 209e85337b9..3c2e79beb13 100755 --- a/test/agentchat/test_conversable_agent.py +++ b/test/agentchat/test_conversable_agent.py @@ -1474,4 +1474,3 @@ def sample_function(): test_summary() test_adding_duplicate_function_warning() # test_function_registration_e2e_sync() -