| import re |
| from duckduckgo_search import DDGS |
| from typing import List, Dict, Any |
|
|
| class BaseTool: |
| def __init__(self, name: str, description: str): |
| self.name = name |
| self.description = description |
|
|
| def run(self, *args, **kwargs) -> str: |
| raise NotImplementedError |
|
|
| class Calculator(BaseTool): |
| def __init__(self): |
| super().__init__( |
| name="Calculator", |
| description="Performs basic arithmetic. Input: math expression as string" |
| ) |
|
|
| def run(self, expression: str) -> str: |
| try: |
| expression = expression.replace(' ', '') |
| if not re.match(r'^[\d+\-*/.()]+$', expression): |
| return "Error: Invalid characters in expression" |
| result = eval(expression) |
| return str(result) |
| except Exception as e: |
| return f"Calculation error: {str(e)}" |
|
|
| class DocRetriever(BaseTool): |
| def __init__(self): |
| super().__init__( |
| name="DocRetriever", |
| description="Searches provided text. Input: 'query: <search_term>'" |
| ) |
| self.document = "" |
|
|
| def load_document(self, text: str): |
| self.document = text |
|
|
| def run(self, query: str) -> str: |
| if not self.document: |
| return "No document loaded" |
| |
| sentences = [s.strip() for s in self.document.split('.') if s] |
| results = [s for s in sentences if query.lower() in s.lower()] |
| return '. '.join(results[:3]) + '...' if results else "No matches found" |
|
|
| class WebSearcher(BaseTool): |
| def __init__(self): |
| super().__init__( |
| name="WebSearcher", |
| description="Searches the web. Input: search query" |
| ) |
|
|
| def run(self, query: str) -> str: |
| try: |
| with DDGS() as ddgs: |
| results = [r for r in ddgs.text(query, max_results=3)] |
| return '\n'.join([f"[{r['title']}]({r['href']}): {r['body']}" for r in results]) |
| except Exception as e: |
| return f"Search error: {str(e)}" |