File size: 9,720 Bytes
6692c96 12c47a4 783d369 12c47a4 783d369 12c47a4 fc21e56 12c47a4 8eea4d3 12c47a4 8eea4d3 12c47a4 8eea4d3 12c47a4 8eea4d3 12c47a4 8eea4d3 12c47a4 783d369 12c47a4 783d369 12c47a4 783d369 12c47a4 887480a 25e2c90 887480a 25e2c90 887480a 25e2c90 887480a b477d60 12c47a4 36a7313 12c47a4 b477d60 55eb2ba 12c47a4 8a5e198 12c47a4 36a7313 12c47a4 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 |
from smolagents import DuckDuckGoSearchTool, GoogleSearchTool
from youtube_transcript_api import YouTubeTranscriptApi
from supadata import Supadata, SupadataError
import wikipedia
from wikipedia_tables_parser import fetch_wikipedia_tables
import pandas as pd
from typing import Any
import os
from dotenv import load_dotenv
load_dotenv()
import importlib.util
import sys
import io
import contextlib
from llama_index.llms.openrouter import OpenRouter
from llama_index.core.types import ChatMessage
llm = OpenRouter(
api_key=os.getenv("OPENROUTER_API_KEY"),
model="google/gemini-2.5-flash-preview",
temperature=0.7,
)
supadata = Supadata(api_key=os.getenv("SUPADATA_API_KEY"))
def reverse_text(text: str, **kwargs) -> str:
"""
Returns the reversed version of the text.
If you receive some unknown text, that can't be recognized and analyzed, then you need to use this tool to make it clear.
Args:
text: text to be reversed
Return:
The reversed text.
"""
try:
print(text[::-1])
return text[::-1]
except Exception as e:
raise ValueError(f"Can't reverse text: {e}")
def fetch_historical_event_data(event_name: str, year: str, **kwargs) -> str:
"""
Fetches data about historical event that occured in certain year.
Some examples of events: Olympics games, Footbal games, NBA etc.
Args:
event_name: String name of the event
year: String year of the event
Return:
String with data about the event
"""
result = wikipedia.page(f"{event_name} in {year}")
url = result.url
content = result.content
try:
tables = pd.read_html(url)
except Exception as e:
tables = fetch_wikipedia_tables(url)
result = f"Content: {content}\nTables: {tables}"
return result
def classify_fruit_vegitable(item: str, **kwargs) -> str:
"""
Classifies items to fruits and vegitables
Args:
item: Item to classify
Returns:
Text with explanation whether it is a fruit or vegetable.
"""
response = llm.chat(
messages=[
ChatMessage(
content=f"Classify whether it is fruit or vegetable: {item}. Return only `fruit` or `vegetable` without explanations"
)
]
)
return response.message.content
def web_search(query: str, **kwargs) -> str:
"""
Returns web search results for the provided query.
Don't use it for Wikipedia queries. For Wikipedia queries use wikipedia_search tool.
Important, query is human-language string input, not the URL or key.
Args:
query: query to search in WEB
Return:
String with web search results.
"""
result = DuckDuckGoSearchTool().forward(query)
# result = GoogleSearchTool(provider="serpapi").forward(query)
print(result)
return result
def wikipedia_search(query: str, **kwargs) -> Any:
"""
Returns wikipedia search results for the provided query.
Args:
query: query to search in WIKIPEDIA
Return:
Wikipedia search results.
"""
result = wikipedia.page(query)
url = result.url
content = result.content
try:
tables = pd.read_html(url)
except:
tables = fetch_wikipedia_tables(url)
result = f"Content: {content}\nTables: {tables}"
return result
def multiply(a: float, b: float, **kwargs) -> float:
"""
Multiply two numbers.
Args:
a: First number
b: Second number
Return:
The product of the two numbers.
"""
return a * b
def compute_sum(values: list[int | float], **kwargs) -> float:
"""
Computes sum of provided values
Args:
values: list of integer or float values
Return:
Sum of the values
"""
return sum(values)
def length(iterable: Any, **kwargs) -> int:
"""
Return the length of an iterable.
Args:
iterable: Any iterable
Return:
The length of the iterable.
"""
return len(iterable)
def execute_python_file(file_path: str) -> Any:
"""
Executes a Python file and returns its result.
This function takes a path to a Python file, executes it by importing it as a module,
and returns the result. The file should contain a function call that produces
the result to be returned. This version also executes code under the
'if __name__ == "__main__":' block.
Args:
file_path (str): Path to the Python file to execute.
Returns:
Any: The result of executing the Python file. If the file sets a variable
named 'result', that value will be returned.
Raises:
FileNotFoundError: If the specified file does not exist.
ImportError: If there was an error importing the Python file.
Example:
>>> # If example.py contains: result = 2 + 3
>>> execute_python_file('example.py')
5
"""
# Verify file exists
if not os.path.isfile(file_path):
raise FileNotFoundError(f"File not found: {file_path}")
# Get the directory and filename
file_dir = os.path.dirname(os.path.abspath(file_path))
file_name = os.path.basename(file_path)
module_name = file_name.replace(".py", "")
# Store original sys.path and add the file's directory
original_sys_path = sys.path.copy()
sys.path.insert(0, file_dir)
# Prepare stdout/stderr capture
stdout_capture = io.StringIO()
stderr_capture = io.StringIO()
# First approach: Import normally to get module definitions
try:
spec = importlib.util.spec_from_file_location(module_name, file_path)
if spec is None or spec.loader is None:
raise ImportError(f"Could not load module spec from {file_path}")
module = importlib.util.module_from_spec(spec)
sys.modules[module_name] = module
# Execute the module
with contextlib.redirect_stdout(stdout_capture), contextlib.redirect_stderr(
stderr_capture
):
spec.loader.exec_module(module)
# After module is loaded, directly execute the main block by reading the file
# and executing the content with __name__ = "__main__"
with open(file_path, "r") as f:
file_content = f.read()
# Create a namespace with everything from the module
namespace = {**module.__dict__}
namespace["__name__"] = "__main__"
exec(file_content, namespace)
if hasattr(module, "result"):
return module.result
else:
output = stdout_capture.getvalue().strip()
print(f"RESULT PYTHON: {output}")
return output
except Exception as e:
error_output = stderr_capture.getvalue()
if error_output:
raise type(e)(f"{str(e)}\nProgram output: {error_output}") from None
else:
raise
finally:
sys.path = original_sys_path
if module_name in sys.modules:
del sys.modules[module_name]
def trascript_youtube(video_id: str, **kwargs) -> str:
"""
Returns transcript of YouTube video.
Args:
video_id: ID of youtube video (Pass in the video ID, NOT the video URL. For a video with the URL https://www.youtube.com/watch?v=12345 the ID is 12345.)
Return:
Transcript of YouTube video.
"""
transcript = supadata.youtube.transcript(video_id=video_id, lang="en")
return transcript.content
def read_excel(path: str, **kwargs) -> pd.DataFrame:
"""
Reads xlsx file
Args:
path: path to xlsx file
Return:
Pandas dataframe
"""
return pd.read_excel(path)
def pandas_column_sum(
pandas_column_values: list[int | float], column_name: str, **kwargs
) -> float:
"""
Computes sum on pandas dataframe column
Args:
pandas_column_values: List with float or integer pandas values
column_name: Name of the column
Return:
Sum of the column
"""
return sum(pandas_column_values)
def final_answer(answer: str, **kwargs) -> str:
"""
Prepare the final answer for the user. It should be always used as a last step.
Args:
answer: The answer to format and return to the user
Return:
The final answer.
"""
resp = llm.chat(
messages=[
ChatMessage(
content=f"""
Final answer from agent: {answer}
Make final answer as short as possible.
Final answer should be a number or as few words as possible or a comma separated list of numbers and/or strings. If you are asked for a number, don't use comma to write your number neither use units such as $ or percent sign unless specified otherwise. If you are asked for a string, don't use articles, neither abbreviations (e.g. for cities), and write the digits in plain text unless specified otherwise. If you are asked for a comma separated list, apply the above rules depending of whether the element to be put in the list is a number or a string.
There might be requested exact number, then you need to compress the output so that it was only number without any comments or explanations (float or integer).
And on the other hand, the question might request some exact string value. Don't explain it, just return this value (For example, insted of `In response to the question, desired person is X` return only `X`)
Again, you don't need to modify or solve answer, you just need to format it properly.
"""
)
]
)
return resp.message.content
# print(wikipedia_search("Mercedes Sosa studio albums"))
# execute_python_file("f918266a-b3e0-4914-865d-4faa564f1aef.py")
|