diff --git a/docs/02-dynamic-routes.ipynb b/docs/02-dynamic-routes.ipynb index 59f1366e93f410876b127815cae0e6618f795c9d..5470ddfb81708e2e9a8c4bd5d7a775d970e0e628 100644 --- a/docs/02-dynamic-routes.ipynb +++ b/docs/02-dynamic-routes.ipynb @@ -185,27 +185,27 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger local\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 2 length: 51\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 2 trunc length: 51\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 3 length: 66\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 3 trunc length: 66\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 4 length: 38\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 4 trunc length: 38\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 5 length: 27\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 5 trunc length: 27\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 6 length: 24\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 6 trunc length: 24\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 7 length: 21\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 7 trunc length: 21\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 8 length: 20\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 8 trunc length: 20\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 9 length: 25\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 9 trunc length: 25\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 10 length: 22\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:13 INFO semantic_router.utils.logger Document 10 trunc length: 22\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger local\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 2 length: 51\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 2 trunc length: 51\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 3 length: 66\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 3 trunc length: 66\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 4 length: 38\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 4 trunc length: 38\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 5 length: 27\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 5 trunc length: 27\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 6 length: 24\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 6 trunc length: 24\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 7 length: 21\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 7 trunc length: 21\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 8 length: 20\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 8 trunc length: 20\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 9 length: 25\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 9 trunc length: 25\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 10 length: 22\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:39 INFO semantic_router.utils.logger Document 10 trunc length: 22\u001b[0m\n" ] } ], @@ -254,8 +254,8 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 1 length: 24\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 1 trunc length: 24\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:40 INFO semantic_router.utils.logger Document 1 length: 24\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:40 INFO semantic_router.utils.logger Document 1 trunc length: 24\u001b[0m\n" ] }, { @@ -332,7 +332,7 @@ { "data": { "text/plain": [ - "'15:07'" + "'16:45'" ] }, "execution_count": 6, @@ -475,13 +475,13 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Adding `get_time` route\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 2 length: 27\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 2 trunc length: 27\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 3 length: 32\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:14 INFO semantic_router.utils.logger Document 3 trunc length: 32\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Adding `get_time` route\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 2 length: 27\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 2 trunc length: 27\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 3 length: 32\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 3 trunc length: 32\u001b[0m\n" ] } ], @@ -523,15 +523,15 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:15 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:15 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", - "\u001b[33m2024-05-01 23:07:15 WARNING semantic_router.utils.logger No LLM provided for dynamic route, will use OpenAI LLM default. Ensure API key is set in OPENAI_API_KEY environment variable.\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:41 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", + "\u001b[33m2024-05-02 00:45:41 WARNING semantic_router.utils.logger No LLM provided for dynamic route, will use OpenAI LLM default. Ensure API key is set in OPENAI_API_KEY environment variable.\u001b[0m\n" ] }, { "data": { "text/plain": [ - "RouteChoice(name='get_time', function_call=[{'function_name': 'get_time', 'arguments': '{\"timezone\":\"America/New_York\"}'}], similarity_score=None)" + "RouteChoice(name='get_time', function_call=[{'function_name': 'get_time', 'arguments': {'timezone': 'America/New_York'}}], similarity_score=None)" ] }, "execution_count": 13, @@ -553,7 +553,7 @@ "name": "stdout", "output_type": "stream", "text": [ - "[{'function_name': 'get_time', 'arguments': '{\"timezone\":\"America/New_York\"}'}]\n" + "[{'function_name': 'get_time', 'arguments': {'timezone': 'America/New_York'}}]\n" ] } ], @@ -570,7 +570,7 @@ "name": "stdout", "output_type": "stream", "text": [ - "15:07\n" + "16:45\n" ] } ], @@ -579,7 +579,7 @@ "\n", "for call in response.function_call:\n", " if call['function_name'] == 'get_time':\n", - " args = json.loads(call['arguments'])\n", + " args = call['arguments']\n", " result = get_time(**args)\n", "print(result)" ] @@ -646,28 +646,12 @@ " now = datetime.now(ZoneInfo(timezone))\n", " return now.strftime(\"%H:%M\")\n", "\n", - "# # Function with two arguments\n", - "# def get_time_difference(timezone1: str, timezone2: str) -> str:\n", - "# \"\"\"Calculates the time difference between two timezones.\n", - "# :param timezone1: The first timezone.\n", - "# :param timezone2: The second timezone.\n", - "# :type timezone1: str\n", - "# :type timezone2: str\n", - "# :return: The time difference in hours between the two timezones.\"\"\"\n", - "# now = datetime.now()\n", - "# tz1 = now.astimezone(ZoneInfo(timezone1))\n", - "# tz2 = now.astimezone(ZoneInfo(timezone2))\n", - "# difference = tz2 - tz1\n", - "# total_seconds = difference.total_seconds()\n", - "# hours_difference = total_seconds / 3600\n", - "# return f\"The time difference between {timezone1} and {timezone2} is {hours_difference} hours.\"\n", - "\n", "\n", "\n", "def get_time_difference(timezone1: str, timezone2: str) -> str:\n", " \"\"\"Calculates the time difference between two timezones.\n", - " :param timezone1: The first timezone.\n", - " :param timezone2: The second timezone.\n", + " :param timezone1: The first timezone, should be a valid timezone from the IANA Time Zone Database like \"America/New_York\" or \"Europe/London\".\n", + " :param timezone2: The second timezone, should be a valid timezone from the IANA Time Zone Database like \"America/New_York\" or \"Europe/London\".\n", " :type timezone1: str\n", " :type timezone2: str\n", " :return: The time difference in hours between the two timezones.\"\"\"\n", @@ -703,22 +687,16 @@ " convert_time(\"12:30\", \"America/New_York\", \"Asia/Tokyo\") -> \"03:30\"\n", " \"\"\"\n", " try:\n", - " print(f\"Attempting to parse the time '{time}' and apply timezone '{from_timezone}'\")\n", " # Use today's date to avoid historical timezone issues\n", " today = datetime.now().date()\n", " datetime_string = f\"{today} {time}\"\n", " time_obj = datetime.strptime(datetime_string, \"%Y-%m-%d %H:%M\").replace(tzinfo=ZoneInfo(from_timezone))\n", - " print(f\"Time parsed successfully: {time_obj}\")\n", " \n", - " print(f\"Converting time from '{from_timezone}' to '{to_timezone}'\")\n", " converted_time = time_obj.astimezone(ZoneInfo(to_timezone))\n", - " print(f\"Time conversion successful: {converted_time}\")\n", " \n", " formatted_time = converted_time.strftime(\"%H:%M\")\n", - " print(f\"Formatted converted time: {formatted_time}\")\n", " return formatted_time\n", " except Exception as e:\n", - " print(f\"Error encountered: {e}\")\n", " raise ValueError(f\"Error converting time: {e}\")\n", "\n", "\n" @@ -750,11 +728,12 @@ " 'required': ['timezone']}}},\n", " {'type': 'function',\n", " 'function': {'name': 'get_time_difference',\n", - " 'description': 'Calculates the time difference between two timezones.\\n:param timezone1: The first timezone.\\n:param timezone2: The second timezone.\\n:type timezone1: str\\n:type timezone2: str\\n:return: The time difference in hours between the two timezones.',\n", + " 'description': 'Calculates the time difference between two timezones.\\n:param timezone1: The first timezone, should be a valid timezone from the IANA Time Zone Database like \"America/New_York\" or \"Europe/London\".\\n:param timezone2: The second timezone, should be a valid timezone from the IANA Time Zone Database like \"America/New_York\" or \"Europe/London\".\\n:type timezone1: str\\n:type timezone2: str\\n:return: The time difference in hours between the two timezones.',\n", " 'parameters': {'type': 'object',\n", " 'properties': {'timezone1': {'type': 'string',\n", - " 'description': 'The first timezone.'},\n", - " 'timezone2': {'type': 'string', 'description': 'The second timezone.'}},\n", + " 'description': 'The first timezone, should be a valid timezone from the IANA Time Zone Database like \"America/New_York\" or \"Europe/London\".'},\n", + " 'timezone2': {'type': 'string',\n", + " 'description': 'The second timezone, should be a valid timezone from the IANA Time Zone Database like \"America/New_York\" or \"Europe/London\".'}},\n", " 'required': ['timezone1', 'timezone2']}}},\n", " {'type': 'function',\n", " 'function': {'name': 'convert_time',\n", @@ -811,6 +790,9 @@ " \"adjust 20:00 from Rome time to London time\",\n", " \"convert 12:00 from Madrid time to Chicago time\",\n", " \"change 18:00 from Beijing time to Los Angeles time\"\n", + "\n", + " # All three functions\n", + " \"What is the time in Seattle? What is the time difference between Mumbai and Tokyo? What is 5:53 Toronto time in Sydney time?\"\n", " ],\n", " function_schemas=schemas\n", ")\n" @@ -834,57 +816,57 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger local\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 2 length: 51\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 2 trunc length: 51\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 3 length: 66\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 3 trunc length: 66\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 4 length: 38\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 4 trunc length: 38\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 5 length: 27\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 5 trunc length: 27\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 6 length: 24\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 6 trunc length: 24\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 7 length: 21\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 7 trunc length: 21\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 8 length: 20\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 8 trunc length: 20\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 9 length: 25\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 9 trunc length: 25\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 10 length: 22\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 10 trunc length: 22\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 11 length: 29\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 11 trunc length: 29\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 12 length: 23\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 12 trunc length: 23\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 13 length: 36\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 13 trunc length: 36\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 14 length: 42\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 14 trunc length: 42\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 15 length: 41\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 15 trunc length: 41\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 16 length: 42\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 16 trunc length: 42\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 17 length: 40\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 17 trunc length: 40\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 18 length: 53\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 18 trunc length: 53\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 19 length: 59\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 19 trunc length: 59\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 20 length: 55\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 20 trunc length: 55\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 21 length: 47\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 21 trunc length: 47\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 22 length: 43\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 22 trunc length: 43\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 23 length: 42\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 23 trunc length: 42\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 24 length: 46\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 24 trunc length: 46\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 25 length: 50\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:16 INFO semantic_router.utils.logger Document 25 trunc length: 50\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger local\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 1 length: 34\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 1 trunc length: 34\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 2 length: 51\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 2 trunc length: 51\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 3 length: 66\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 3 trunc length: 66\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 4 length: 38\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 4 trunc length: 38\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 5 length: 27\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 5 trunc length: 27\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 6 length: 24\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 6 trunc length: 24\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 7 length: 21\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 7 trunc length: 21\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 8 length: 20\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 8 trunc length: 20\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 9 length: 25\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 9 trunc length: 25\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 10 length: 22\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 10 trunc length: 22\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 11 length: 29\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 11 trunc length: 29\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 12 length: 23\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 12 trunc length: 23\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 13 length: 36\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 13 trunc length: 36\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 14 length: 42\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 14 trunc length: 42\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 15 length: 41\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 15 trunc length: 41\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 16 length: 42\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 16 trunc length: 42\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 17 length: 40\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 17 trunc length: 40\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 18 length: 53\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 18 trunc length: 53\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 19 length: 59\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 19 trunc length: 59\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 20 length: 55\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 20 trunc length: 55\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 21 length: 47\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 21 trunc length: 47\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 22 length: 43\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 22 trunc length: 43\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 23 length: 42\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 23 trunc length: 42\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 24 length: 46\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 24 trunc length: 46\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 25 length: 174\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:42 INFO semantic_router.utils.logger Document 25 trunc length: 174\u001b[0m\n" ] } ], @@ -908,7 +890,7 @@ "def parse_response(response: str):\n", "\n", " for call in response.function_call:\n", - " args = json.loads(call['arguments'])\n", + " args = call['arguments']\n", " if call['function_name'] == 'get_time':\n", " result = get_time(**args)\n", " print(result)\n", @@ -936,8 +918,8 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:17 INFO semantic_router.utils.logger Document 1 length: 31\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:17 INFO semantic_router.utils.logger Document 1 trunc length: 31\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:47 INFO semantic_router.utils.logger Document 1 length: 31\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:47 INFO semantic_router.utils.logger Document 1 trunc length: 31\u001b[0m\n" ] }, { @@ -972,8 +954,8 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:17 INFO semantic_router.utils.logger Document 1 length: 29\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:17 INFO semantic_router.utils.logger Document 1 trunc length: 29\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:47 INFO semantic_router.utils.logger Document 1 length: 29\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:47 INFO semantic_router.utils.logger Document 1 trunc length: 29\u001b[0m\n" ] }, { @@ -1008,15 +990,15 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:18 INFO semantic_router.utils.logger Document 1 length: 29\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:18 INFO semantic_router.utils.logger Document 1 trunc length: 29\u001b[0m\n", - "\u001b[33m2024-05-01 23:07:18 WARNING semantic_router.utils.logger No LLM provided for dynamic route, will use OpenAI LLM default. Ensure API key is set in OPENAI_API_KEY environment variable.\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:48 INFO semantic_router.utils.logger Document 1 length: 29\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:48 INFO semantic_router.utils.logger Document 1 trunc length: 29\u001b[0m\n", + "\u001b[33m2024-05-02 00:45:48 WARNING semantic_router.utils.logger No LLM provided for dynamic route, will use OpenAI LLM default. Ensure API key is set in OPENAI_API_KEY environment variable.\u001b[0m\n" ] }, { "data": { "text/plain": [ - "RouteChoice(name='timezone_management', function_call=[{'function_name': 'get_time', 'arguments': '{\"timezone\":\"America/New_York\"}'}], similarity_score=None)" + "RouteChoice(name='timezone_management', function_call=[{'function_name': 'get_time', 'arguments': {'timezone': 'America/New_York'}}], similarity_score=None)" ] }, "execution_count": 25, @@ -1038,7 +1020,7 @@ "name": "stdout", "output_type": "stream", "text": [ - "15:07\n" + "16:45\n" ] } ], @@ -1062,14 +1044,14 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:19 INFO semantic_router.utils.logger Document 1 length: 61\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:19 INFO semantic_router.utils.logger Document 1 trunc length: 61\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:49 INFO semantic_router.utils.logger Document 1 length: 61\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:49 INFO semantic_router.utils.logger Document 1 trunc length: 61\u001b[0m\n" ] }, { "data": { "text/plain": [ - "RouteChoice(name='timezone_management', function_call=[{'function_name': 'get_time_difference', 'arguments': '{\"timezone1\":\"America/Los_Angeles\",\"timezone2\":\"Europe/Istanbul\"}'}], similarity_score=None)" + "RouteChoice(name='timezone_management', function_call=[{'function_name': 'get_time_difference', 'arguments': {'timezone1': 'America/Los_Angeles', 'timezone2': 'Europe/Istanbul'}}], similarity_score=None)" ] }, "execution_count": 27, @@ -1115,14 +1097,14 @@ "name": "stderr", "output_type": "stream", "text": [ - "\u001b[32m2024-05-01 23:07:21 INFO semantic_router.utils.logger Document 1 length: 72\u001b[0m\n", - "\u001b[32m2024-05-01 23:07:21 INFO semantic_router.utils.logger Document 1 trunc length: 72\u001b[0m\n" + "\u001b[32m2024-05-02 00:45:51 INFO semantic_router.utils.logger Document 1 length: 61\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:51 INFO semantic_router.utils.logger Document 1 trunc length: 61\u001b[0m\n" ] }, { "data": { "text/plain": [ - "RouteChoice(name='timezone_management', function_call=[{'function_name': 'convert_time', 'arguments': '{\"time\":\"23:02\",\"from_timezone\":\"Asia/Dubai\",\"to_timezone\":\"Asia/Tokyo\"}'}], similarity_score=None)" + "RouteChoice(name='timezone_management', function_call=[{'function_name': 'convert_time', 'arguments': {'time': '23:02', 'from_timezone': 'Asia/Dubai', 'to_timezone': 'Asia/Tokyo'}}], similarity_score=None)" ] }, "execution_count": 29, @@ -1131,7 +1113,7 @@ } ], "source": [ - "response = rl2(\"What is 23:02 Dubai time in Tokyo time. Please and thank you.\")\n", + "response = rl2(\"What is 23:02 Dubai time in Tokyo time? Please and thank you.\")\n", "response" ] }, @@ -1144,12 +1126,7 @@ "name": "stdout", "output_type": "stream", "text": [ - "Attempting to parse the time '23:02' and apply timezone 'Asia/Dubai'\n", - "Time parsed successfully: 1900-01-01 23:02:00+03:41:12\n", - "Converting time from 'Asia/Dubai' to 'Asia/Tokyo'\n", - "Time conversion successful: 1900-01-02 04:20:48+09:00\n", - "Formatted converted time: 04:20\n", - "04:20\n" + "04:02\n" ] } ], @@ -1157,12 +1134,74 @@ "parse_response(response)" ] }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### The Cool Bit - Testing `multi_function_route` - Multiple Functions at Once" + ] + }, { "cell_type": "code", - "execution_count": null, + "execution_count": 31, "metadata": {}, - "outputs": [], - "source": [] + "outputs": [ + { + "name": "stderr", + "output_type": "stream", + "text": [ + "\u001b[32m2024-05-02 00:45:52 INFO semantic_router.utils.logger Document 1 length: 142\u001b[0m\n", + "\u001b[32m2024-05-02 00:45:52 INFO semantic_router.utils.logger Document 1 trunc length: 142\u001b[0m\n" + ] + } + ], + "source": [ + "response = rl2(\"\"\"\n", + " What is the time in Prague?\n", + " What is the time difference between Frankfurt and Beijing?\n", + " What is 5:53 Lisbon time in Bangkok time?\n", + "\"\"\" \n", + ")" + ] + }, + { + "cell_type": "code", + "execution_count": 32, + "metadata": {}, + "outputs": [ + { + "data": { + "text/plain": [ + "RouteChoice(name='timezone_management', function_call=[{'function_name': 'get_time', 'arguments': {'timezone': 'Europe/Prague'}}, {'function_name': 'get_time_difference', 'arguments': {'timezone1': 'Europe/Berlin', 'timezone2': 'Asia/Shanghai'}}, {'function_name': 'convert_time', 'arguments': {'time': '05:53', 'from_timezone': 'Europe/Lisbon', 'to_timezone': 'Asia/Bangkok'}}], similarity_score=None)" + ] + }, + "execution_count": 32, + "metadata": {}, + "output_type": "execute_result" + } + ], + "source": [ + "response" + ] + }, + { + "cell_type": "code", + "execution_count": 33, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "22:45\n", + "The time difference between Europe/Berlin and Asia/Shanghai is 6.0 hours.\n", + "11:53\n" + ] + } + ], + "source": [ + "parse_response(response)" + ] } ], "metadata": { diff --git a/semantic_router/llms/base.py b/semantic_router/llms/base.py index 3170ccc2b8b438d0ddc4b8ae922df8456bc252e2..d3f207a187f8d9690c422f19d6b0f1a057b979c0 100644 --- a/semantic_router/llms/base.py +++ b/semantic_router/llms/base.py @@ -108,9 +108,9 @@ Return only JSON, stating the function name and the argument names with their co ### FORMATTING_INSTRUCTIONS Start ### Return a response in valid JSON format. Do not return any other explanation or text, just the JSON. - The JSON output should include a key 'function_name' with the value being the name of the function. + The JSON output should always be an array of JSON objects. If only one function is relevant, return an array with a single JSON object. + Each JSON object should include a key 'function_name' with the value being the name of the function. Under the key 'arguments', include a nested JSON object where the keys are the names of the arguments and the values are the values those arguments should take. - If multiple function schemas are relevant, return a list of JSON objects. ### FORMATTING_INSTRUCTIONS End ### ### EXAMPLE Start ### @@ -139,26 +139,26 @@ Return only JSON, stating the function name and the argument names with their co === EXAMPLE_INPUT_SCHEMA End === === EXAMPLE_OUTPUT Start === [ - { + {{ "function_name": "get_temperature", - "arguments": { + "arguments": {{ "location": "Hawaii", "degree": "Celsius" - } - }, - { + }} + }}, + {{ "function_name": "get_temperature", - "arguments": { + "arguments": {{ "location": "New York", "degree": "Celsius" - } - }, - { + }} + }}, + {{ "function_name": "get_humidity", - "arguments": { + "arguments": {{ "location": "Hawaii" - } - } + }} + }} ] === EXAMPLE_OUTPUT End === ### EXAMPLE End ### diff --git a/semantic_router/llms/openai.py b/semantic_router/llms/openai.py index c3cb347bebee25d065ee239bbecdb2824d5806a7..b830674017af7a5b50b591e8b483ff628b4679ef 100644 --- a/semantic_router/llms/openai.py +++ b/semantic_router/llms/openai.py @@ -49,9 +49,9 @@ class OpenAILLM(BaseLLM): ) tool_calls_info.append({ "function_name": tool_call.function.name, - "arguments": tool_call.function.arguments + "arguments": json.loads(tool_call.function.arguments) }) - return json.dumps(tool_calls_info) + return tool_calls_info def __call__( self, @@ -104,9 +104,7 @@ class OpenAILLM(BaseLLM): system_prompt = "You are an intelligent AI. Given a command or request from the user, call the function to complete the request." messages.append(Message(role="system", content=system_prompt)) messages.append(Message(role="user", content=query)) - function_inputs_str = self(messages=messages, function_schemas=function_schemas) - function_inputs = json.loads(function_inputs_str) - return function_inputs + return self(messages=messages, function_schemas=function_schemas) def get_schemas_openai(items: List[Callable]) -> List[Dict[str, Any]]: schemas = []