universal-mcp-applications 0.1.13__py3-none-any.whl → 0.1.15__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of universal-mcp-applications might be problematic. Click here for more details.
- universal_mcp/applications/aws_s3/app.py +71 -71
- universal_mcp/applications/calendly/app.py +199 -199
- universal_mcp/applications/canva/app.py +189 -189
- universal_mcp/applications/domain_checker/app.py +31 -24
- universal_mcp/applications/e2b/app.py +6 -7
- universal_mcp/applications/elevenlabs/app.py +24 -20
- universal_mcp/applications/exa/app.py +25 -20
- universal_mcp/applications/falai/app.py +44 -41
- universal_mcp/applications/file_system/app.py +20 -12
- universal_mcp/applications/firecrawl/app.py +46 -47
- universal_mcp/applications/fireflies/app.py +79 -79
- universal_mcp/applications/fpl/app.py +83 -74
- universal_mcp/applications/github/README.md +0 -1028
- universal_mcp/applications/github/app.py +55 -50227
- universal_mcp/applications/google_calendar/app.py +63 -65
- universal_mcp/applications/google_docs/app.py +78 -78
- universal_mcp/applications/google_drive/app.py +361 -440
- universal_mcp/applications/google_gemini/app.py +34 -17
- universal_mcp/applications/google_mail/app.py +117 -117
- universal_mcp/applications/google_searchconsole/app.py +41 -47
- universal_mcp/applications/google_sheet/app.py +157 -164
- universal_mcp/applications/http_tools/app.py +16 -16
- universal_mcp/applications/linkedin/app.py +26 -31
- universal_mcp/applications/ms_teams/app.py +190 -190
- universal_mcp/applications/openai/app.py +55 -56
- universal_mcp/applications/outlook/app.py +71 -71
- universal_mcp/applications/perplexity/app.py +17 -17
- universal_mcp/applications/reddit/app.py +225 -4053
- universal_mcp/applications/replicate/app.py +40 -42
- universal_mcp/applications/resend/app.py +157 -154
- universal_mcp/applications/scraper/app.py +24 -24
- universal_mcp/applications/serpapi/app.py +18 -20
- universal_mcp/applications/sharepoint/app.py +46 -36
- universal_mcp/applications/slack/app.py +66 -66
- universal_mcp/applications/tavily/app.py +7 -7
- universal_mcp/applications/twitter/api_segments/compliance_api.py +17 -20
- universal_mcp/applications/twitter/api_segments/dm_conversations_api.py +35 -40
- universal_mcp/applications/twitter/api_segments/dm_events_api.py +18 -21
- universal_mcp/applications/twitter/api_segments/likes_api.py +19 -22
- universal_mcp/applications/twitter/api_segments/lists_api.py +59 -68
- universal_mcp/applications/twitter/api_segments/spaces_api.py +36 -42
- universal_mcp/applications/twitter/api_segments/trends_api.py +7 -8
- universal_mcp/applications/twitter/api_segments/tweets_api.py +159 -185
- universal_mcp/applications/twitter/api_segments/usage_api.py +5 -6
- universal_mcp/applications/twitter/api_segments/users_api.py +230 -264
- universal_mcp/applications/unipile/app.py +99 -105
- universal_mcp/applications/whatsapp/app.py +86 -82
- universal_mcp/applications/whatsapp_business/app.py +147 -147
- universal_mcp/applications/youtube/app.py +290 -290
- universal_mcp/applications/zenquotes/app.py +6 -6
- {universal_mcp_applications-0.1.13.dist-info → universal_mcp_applications-0.1.15.dist-info}/METADATA +2 -2
- {universal_mcp_applications-0.1.13.dist-info → universal_mcp_applications-0.1.15.dist-info}/RECORD +54 -54
- {universal_mcp_applications-0.1.13.dist-info → universal_mcp_applications-0.1.15.dist-info}/WHEEL +0 -0
- {universal_mcp_applications-0.1.13.dist-info → universal_mcp_applications-0.1.15.dist-info}/licenses/LICENSE +0 -0
|
@@ -48,8 +48,10 @@ class DomainCheckerApp(APIApplication):
|
|
|
48
48
|
def __init__(self, integration: Integration = None, **kwargs) -> None:
|
|
49
49
|
super().__init__(name="domain_checker", integration=integration, **kwargs)
|
|
50
50
|
|
|
51
|
-
async def
|
|
52
|
-
"""
|
|
51
|
+
async def _get_rdap_data(self, domain: str) -> dict[str, Any] | None:
|
|
52
|
+
"""
|
|
53
|
+
Fetches a domain's registration details from Registration Data Access Protocol (RDAP) servers. It dynamically selects the appropriate server URL based on the domain's TLD, with special handling for common ones. Returns the JSON data as a dictionary or None if the request fails or data is unavailable.
|
|
54
|
+
"""
|
|
53
55
|
try:
|
|
54
56
|
# Special case for .ch and .li domains
|
|
55
57
|
tld = domain.split(".")[-1].lower()
|
|
@@ -75,8 +77,10 @@ class DomainCheckerApp(APIApplication):
|
|
|
75
77
|
logger.error(f"RDAP error for {domain}: {e}")
|
|
76
78
|
return None
|
|
77
79
|
|
|
78
|
-
async def
|
|
79
|
-
"""
|
|
80
|
+
async def _check_dns(self, domain: str) -> bool:
|
|
81
|
+
"""
|
|
82
|
+
Performs a DNS lookup for a domain, checking first for an 'A' record and then an 'NS' record. It returns true if either record type exists, serving as a quick preliminary check to determine if a domain is actively configured on the internet.
|
|
83
|
+
"""
|
|
80
84
|
try:
|
|
81
85
|
dns.resolver.resolve(domain, "A")
|
|
82
86
|
return True
|
|
@@ -87,18 +91,18 @@ class DomainCheckerApp(APIApplication):
|
|
|
87
91
|
except:
|
|
88
92
|
return False
|
|
89
93
|
|
|
90
|
-
async def
|
|
94
|
+
async def check_domain_registration(self, domain: str) -> dict[str, Any]:
|
|
91
95
|
"""
|
|
92
|
-
|
|
93
|
-
|
|
96
|
+
Determines a domain's availability by querying DNS and RDAP servers. For registered domains, it returns details like registrar and key dates. This function provides a comprehensive analysis for a single, fully qualified domain name, unlike `check_keyword_across_tlds_tool` which checks a keyword across multiple domains.
|
|
97
|
+
|
|
94
98
|
This method performs a comprehensive domain availability check by first checking DNS records
|
|
95
99
|
and then querying RDAP (Registration Data Access Protocol) servers for detailed registration
|
|
96
100
|
information. It provides detailed information about registered domains including registrar,
|
|
97
101
|
registration date, and expiration date.
|
|
98
|
-
|
|
102
|
+
|
|
99
103
|
Args:
|
|
100
104
|
domain: String representing the domain name to check (e.g., "example.com")
|
|
101
|
-
|
|
105
|
+
|
|
102
106
|
Returns:
|
|
103
107
|
Dictionary containing domain availability information with the following keys:
|
|
104
108
|
- domain: The domain name that was checked
|
|
@@ -109,23 +113,23 @@ class DomainCheckerApp(APIApplication):
|
|
|
109
113
|
- has_dns: Boolean indicating if DNS records exist
|
|
110
114
|
- rdap_data_available: Boolean indicating if RDAP data was retrieved
|
|
111
115
|
- note: Additional information when needed
|
|
112
|
-
|
|
116
|
+
|
|
113
117
|
Raises:
|
|
114
118
|
DNSException: When DNS resolution fails due to network issues or invalid domain format
|
|
115
119
|
RequestException: When RDAP queries fail due to network issues or server errors
|
|
116
120
|
ValueError: When the domain parameter is empty or contains invalid characters
|
|
117
|
-
|
|
121
|
+
|
|
118
122
|
Tags:
|
|
119
123
|
domain, availability, registration, dns, rdap, important
|
|
120
124
|
"""
|
|
121
125
|
logger.info(f"Checking domain: {domain}")
|
|
122
126
|
|
|
123
127
|
# First check DNS
|
|
124
|
-
has_dns = await self.
|
|
128
|
+
has_dns = await self._check_dns(domain)
|
|
125
129
|
|
|
126
130
|
if has_dns:
|
|
127
131
|
# Domain exists, get RDAP data if possible
|
|
128
|
-
rdap_data = await self.
|
|
132
|
+
rdap_data = await self._get_rdap_data(domain)
|
|
129
133
|
|
|
130
134
|
if rdap_data:
|
|
131
135
|
# Extract data from RDAP
|
|
@@ -174,7 +178,7 @@ class DomainCheckerApp(APIApplication):
|
|
|
174
178
|
}
|
|
175
179
|
|
|
176
180
|
# Try RDAP one more time even if DNS not found
|
|
177
|
-
rdap_data = await self.
|
|
181
|
+
rdap_data = await self._get_rdap_data(domain)
|
|
178
182
|
if rdap_data:
|
|
179
183
|
return {
|
|
180
184
|
"domain": domain,
|
|
@@ -199,18 +203,18 @@ class DomainCheckerApp(APIApplication):
|
|
|
199
203
|
"note": "No DNS records or RDAP data found",
|
|
200
204
|
}
|
|
201
205
|
|
|
202
|
-
async def
|
|
206
|
+
async def find_available_domains_for_keyword(self, keyword: str) -> dict[str, Any]:
|
|
203
207
|
"""
|
|
204
|
-
Checks a keyword across
|
|
205
|
-
|
|
208
|
+
Checks a keyword's availability across a predefined list of popular TLDs. Using DNS and RDAP lookups, it generates a summary report of available and taken domains. This bulk-check differs from `check_domain_registration`, which deeply analyzes a single, fully-qualified domain.
|
|
209
|
+
|
|
206
210
|
This method systematically checks a given keyword across 14 popular TLDs including .com, .net,
|
|
207
211
|
.org, .io, .co, .app, .dev, .ai, .me, .info, .xyz, .online, .site, and .tech. It performs
|
|
208
212
|
DNS lookups and RDAP queries to determine domain availability and provides a comprehensive
|
|
209
213
|
report of available and taken domains.
|
|
210
|
-
|
|
214
|
+
|
|
211
215
|
Args:
|
|
212
216
|
keyword: String representing the keyword to check across TLDs (e.g., "myapp")
|
|
213
|
-
|
|
217
|
+
|
|
214
218
|
Returns:
|
|
215
219
|
Dictionary containing TLD availability information with the following keys:
|
|
216
220
|
- keyword: The keyword that was checked
|
|
@@ -220,12 +224,12 @@ class DomainCheckerApp(APIApplication):
|
|
|
220
224
|
- available_domains: List of available domain names
|
|
221
225
|
- taken_domains: List of taken domain names
|
|
222
226
|
- tlds_checked_list: Complete list of TLDs that were checked
|
|
223
|
-
|
|
227
|
+
|
|
224
228
|
Raises:
|
|
225
229
|
DNSException: When DNS resolution fails due to network issues or invalid domain format
|
|
226
230
|
RequestException: When RDAP queries fail due to network issues or server errors
|
|
227
231
|
ValueError: When the keyword parameter is empty or contains invalid characters
|
|
228
|
-
|
|
232
|
+
|
|
229
233
|
Tags:
|
|
230
234
|
tld, keyword, domain-search, availability, bulk-check, important
|
|
231
235
|
"""
|
|
@@ -237,11 +241,11 @@ class DomainCheckerApp(APIApplication):
|
|
|
237
241
|
# Check each TLD in sequence
|
|
238
242
|
for tld in TOP_TLDS:
|
|
239
243
|
domain = f"{keyword}.{tld}"
|
|
240
|
-
has_dns = await self.
|
|
244
|
+
has_dns = await self._check_dns(domain)
|
|
241
245
|
|
|
242
246
|
if not has_dns:
|
|
243
247
|
# Double-check with RDAP if no DNS
|
|
244
|
-
rdap_data = await self.
|
|
248
|
+
rdap_data = await self._get_rdap_data(domain)
|
|
245
249
|
if not rdap_data:
|
|
246
250
|
available.append(domain)
|
|
247
251
|
else:
|
|
@@ -263,4 +267,7 @@ class DomainCheckerApp(APIApplication):
|
|
|
263
267
|
"""
|
|
264
268
|
Lists the available tools (methods) for this application.
|
|
265
269
|
"""
|
|
266
|
-
return [
|
|
270
|
+
return [
|
|
271
|
+
self.check_domain_registration,
|
|
272
|
+
self.find_available_domains_for_keyword
|
|
273
|
+
]
|
|
@@ -35,8 +35,7 @@ class E2bApp(APIApplication):
|
|
|
35
35
|
@property
|
|
36
36
|
def e2b_api_key(self) -> str:
|
|
37
37
|
"""
|
|
38
|
-
|
|
39
|
-
Raises NotAuthorizedError if the key cannot be obtained.
|
|
38
|
+
A property that lazily retrieves and caches the E2B API key from the configured integration. It fetches the key on the first call, handles authentication failures, and raises `NotAuthorizedError` with actionable guidance if the key cannot be obtained.
|
|
40
39
|
"""
|
|
41
40
|
if self._e2b_api_key is None:
|
|
42
41
|
if not self.integration:
|
|
@@ -131,20 +130,20 @@ class E2bApp(APIApplication):
|
|
|
131
130
|
self, code: Annotated[str, "The Python code to execute."]
|
|
132
131
|
) -> str:
|
|
133
132
|
"""
|
|
134
|
-
Executes Python code in a sandbox
|
|
135
|
-
|
|
133
|
+
Executes a Python code string in a secure E2B sandbox. It authenticates using the configured API key, runs the code, and returns a formatted string containing the execution's output (stdout/stderr). It raises specific exceptions for authorization failures or general execution issues.
|
|
134
|
+
|
|
136
135
|
Args:
|
|
137
136
|
code: String containing the Python code to be executed in the sandbox.
|
|
138
|
-
|
|
137
|
+
|
|
139
138
|
Returns:
|
|
140
139
|
A string containing the formatted execution output/logs from running the code.
|
|
141
|
-
|
|
140
|
+
|
|
142
141
|
Raises:
|
|
143
142
|
ToolError: When there are issues with sandbox initialization or code execution,
|
|
144
143
|
or if the E2B SDK is not installed.
|
|
145
144
|
NotAuthorizedError: When API key authentication fails during sandbox setup.
|
|
146
145
|
ValueError: When provided code string is empty or invalid.
|
|
147
|
-
|
|
146
|
+
|
|
148
147
|
Tags:
|
|
149
148
|
execute, sandbox, code-execution, security, important
|
|
150
149
|
"""
|
|
@@ -17,11 +17,14 @@ class ElevenlabsApp(APIApplication):
|
|
|
17
17
|
|
|
18
18
|
@property
|
|
19
19
|
def client(self) -> ElevenLabs:
|
|
20
|
+
"""
|
|
21
|
+
A property that lazily initializes and returns an authenticated `ElevenLabs` SDK client. On first access, it retrieves the API key from integration credentials and caches the instance, raising a `NotAuthorizedError` if credentials are not found.
|
|
22
|
+
"""
|
|
20
23
|
if self._client is None:
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
api_key =
|
|
24
|
+
credentials = self.integration.get_credentials()
|
|
25
|
+
if not credentials:
|
|
26
|
+
raise NotAuthorizedError("No credentials found")
|
|
27
|
+
api_key = credentials.get("api_key") or credentials.get("API_KEY") or credentials.get("apiKey")
|
|
25
28
|
if not api_key:
|
|
26
29
|
raise NotAuthorizedError("No api key found")
|
|
27
30
|
self._client = ElevenLabs(api_key=api_key)
|
|
@@ -30,22 +33,22 @@ class ElevenlabsApp(APIApplication):
|
|
|
30
33
|
# def get_voices(self):
|
|
31
34
|
# return self.client.voices.list_voices()
|
|
32
35
|
|
|
33
|
-
async def
|
|
36
|
+
async def generate_speech_audio_url(
|
|
34
37
|
self,
|
|
35
38
|
text: str,
|
|
36
39
|
voice_id: str = "21m00Tcm4TlvDq8ikWAM",
|
|
37
40
|
model_id: str = "eleven_multilingual_v2",
|
|
38
41
|
) -> bytes:
|
|
39
42
|
"""
|
|
40
|
-
Converts text
|
|
41
|
-
|
|
43
|
+
Converts a text string into speech using the ElevenLabs API. The function then saves the generated audio to a temporary MP3 file and returns a public URL to access it, rather than the raw audio bytes.
|
|
44
|
+
|
|
42
45
|
Args:
|
|
43
46
|
text (str): The text to convert to speech.
|
|
44
47
|
voice_id (str): The ID of the voice to use.
|
|
45
48
|
model_id (str, optional): The model to use. Defaults to "eleven_multilingual_v2".
|
|
46
49
|
stability (float, optional): The stability of the voice.
|
|
47
50
|
similarity_boost (float, optional): The similarity boost of the voice.
|
|
48
|
-
|
|
51
|
+
|
|
49
52
|
Returns:
|
|
50
53
|
bytes: The audio data.
|
|
51
54
|
|
|
@@ -73,13 +76,11 @@ class ElevenlabsApp(APIApplication):
|
|
|
73
76
|
self, audio_file_path: str, language_code: str = "eng", diarize: bool = True
|
|
74
77
|
) -> str:
|
|
75
78
|
"""
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
This is a placeholder and will not work until the endpoint is available.
|
|
79
|
-
|
|
79
|
+
Transcribes an audio file into text using the ElevenLabs API. It supports language specification and speaker diarization, providing the inverse operation to the audio-generating `text_to_speech` method. Note: The docstring indicates this is a placeholder for an undocumented endpoint.
|
|
80
|
+
|
|
80
81
|
Args:
|
|
81
82
|
audio_file_path (str): The path to the audio file.
|
|
82
|
-
|
|
83
|
+
|
|
83
84
|
Returns:
|
|
84
85
|
str: The transcribed text.
|
|
85
86
|
|
|
@@ -102,13 +103,13 @@ class ElevenlabsApp(APIApplication):
|
|
|
102
103
|
model_id: str = "eleven_multilingual_sts_v2",
|
|
103
104
|
) -> bytes:
|
|
104
105
|
"""
|
|
105
|
-
|
|
106
|
-
|
|
106
|
+
Downloads an audio file from a URL and converts the speech into a specified target voice using the ElevenLabs API. This function transforms the speaker's voice in an existing recording and returns the new audio data as bytes, distinct from creating audio from text.
|
|
107
|
+
|
|
107
108
|
Args:
|
|
108
109
|
voice_id (str): The ID of the voice to use for the conversion.
|
|
109
110
|
audio_file_path (str): The path to the audio file to transform.
|
|
110
111
|
model_id (str, optional): The model to use. Defaults to "eleven_multilingual_sts_v2".
|
|
111
|
-
|
|
112
|
+
|
|
112
113
|
Returns:
|
|
113
114
|
bytes: The transformed audio data.
|
|
114
115
|
|
|
@@ -127,19 +128,22 @@ class ElevenlabsApp(APIApplication):
|
|
|
127
128
|
|
|
128
129
|
def list_tools(self):
|
|
129
130
|
return [
|
|
130
|
-
self.
|
|
131
|
+
self.generate_speech_audio_url,
|
|
131
132
|
self.speech_to_text,
|
|
132
133
|
self.speech_to_speech,
|
|
133
134
|
]
|
|
134
135
|
|
|
135
136
|
|
|
136
|
-
async def
|
|
137
|
+
async def demo_text_to_speech():
|
|
138
|
+
"""
|
|
139
|
+
A demonstration function that instantiates the `ElevenlabsApp` to test its `text_to_speech` method. It converts a sample string to audio and prints the resulting file URL to the console, serving as a basic usage example when the script is executed directly.
|
|
140
|
+
"""
|
|
137
141
|
app = ElevenlabsApp()
|
|
138
|
-
audio = await app.
|
|
142
|
+
audio = await app.generate_speech_audio_url("Hello, world!")
|
|
139
143
|
print(audio)
|
|
140
144
|
|
|
141
145
|
|
|
142
146
|
if __name__ == "__main__":
|
|
143
147
|
import asyncio
|
|
144
148
|
|
|
145
|
-
asyncio.run(
|
|
149
|
+
asyncio.run(demo_text_to_speech())
|
|
@@ -9,7 +9,7 @@ class ExaApp(APIApplication):
|
|
|
9
9
|
super().__init__(name="exa", integration=integration, **kwargs)
|
|
10
10
|
self.base_url = "https://api.exa.ai"
|
|
11
11
|
|
|
12
|
-
def
|
|
12
|
+
def search_with_filters(
|
|
13
13
|
self,
|
|
14
14
|
query,
|
|
15
15
|
useAutoprompt=None,
|
|
@@ -27,8 +27,8 @@ class ExaApp(APIApplication):
|
|
|
27
27
|
contents=None,
|
|
28
28
|
) -> dict[str, Any]:
|
|
29
29
|
"""
|
|
30
|
-
|
|
31
|
-
|
|
30
|
+
Executes a query against the Exa API's `/search` endpoint, returning a list of results. This function supports extensive filtering by search type, category, domains, publication dates, and specific text content to refine the search query and tailor the API's response.
|
|
31
|
+
|
|
32
32
|
Args:
|
|
33
33
|
query (string): The query string for the search. Example: 'Latest developments in LLM capabilities'.
|
|
34
34
|
useAutoprompt (boolean): Autoprompt converts your query to an Exa-style query. Enabled by default for auto search, optional for neural search, and not available for keyword search. Example: 'True'.
|
|
@@ -44,10 +44,10 @@ class ExaApp(APIApplication):
|
|
|
44
44
|
includeText (array): List of strings that must be present in webpage text of results. Currently, only 1 string is supported, of up to 5 words. Example: "['large language model']".
|
|
45
45
|
excludeText (array): List of strings that must not be present in webpage text of results. Currently, only 1 string is supported, of up to 5 words. Example: "['course']".
|
|
46
46
|
contents (object): contents
|
|
47
|
-
|
|
47
|
+
|
|
48
48
|
Returns:
|
|
49
49
|
dict[str, Any]: OK
|
|
50
|
-
|
|
50
|
+
|
|
51
51
|
Tags:
|
|
52
52
|
important
|
|
53
53
|
"""
|
|
@@ -74,7 +74,7 @@ class ExaApp(APIApplication):
|
|
|
74
74
|
response.raise_for_status()
|
|
75
75
|
return response.json()
|
|
76
76
|
|
|
77
|
-
def
|
|
77
|
+
def find_similar_by_url(
|
|
78
78
|
self,
|
|
79
79
|
url,
|
|
80
80
|
numResults=None,
|
|
@@ -89,8 +89,8 @@ class ExaApp(APIApplication):
|
|
|
89
89
|
contents=None,
|
|
90
90
|
) -> dict[str, Any]:
|
|
91
91
|
"""
|
|
92
|
-
Finds
|
|
93
|
-
|
|
92
|
+
Finds web pages semantically similar to a given URL. Unlike the `search` function, which uses a text query, this method takes a specific link and returns a list of related results, with options to filter by domain, publication date, and content.
|
|
93
|
+
|
|
94
94
|
Args:
|
|
95
95
|
url (string): The url for which you would like to find similar links. Example: 'https://arxiv.org/abs/2307.06435'.
|
|
96
96
|
numResults (integer): Number of results to return (up to thousands of results available for custom plans) Example: '10'.
|
|
@@ -103,10 +103,10 @@ class ExaApp(APIApplication):
|
|
|
103
103
|
includeText (array): List of strings that must be present in webpage text of results. Currently, only 1 string is supported, of up to 5 words. Example: "['large language model']".
|
|
104
104
|
excludeText (array): List of strings that must not be present in webpage text of results. Currently, only 1 string is supported, of up to 5 words. Example: "['course']".
|
|
105
105
|
contents (object): contents
|
|
106
|
-
|
|
106
|
+
|
|
107
107
|
Returns:
|
|
108
108
|
dict[str, Any]: OK
|
|
109
|
-
|
|
109
|
+
|
|
110
110
|
Tags:
|
|
111
111
|
important
|
|
112
112
|
"""
|
|
@@ -130,7 +130,7 @@ class ExaApp(APIApplication):
|
|
|
130
130
|
response.raise_for_status()
|
|
131
131
|
return response.json()
|
|
132
132
|
|
|
133
|
-
def
|
|
133
|
+
def fetch_page_content(
|
|
134
134
|
self,
|
|
135
135
|
urls,
|
|
136
136
|
ids=None,
|
|
@@ -144,8 +144,8 @@ class ExaApp(APIApplication):
|
|
|
144
144
|
extras=None,
|
|
145
145
|
) -> dict[str, Any]:
|
|
146
146
|
"""
|
|
147
|
-
|
|
148
|
-
|
|
147
|
+
Retrieves and processes content from a list of URLs, returning full text, summaries, or highlights. Unlike the search function which finds links, this function fetches the actual page content, with optional support for live crawling to get the most up-to-date information.
|
|
148
|
+
|
|
149
149
|
Args:
|
|
150
150
|
urls (array): Array of URLs to crawl (backwards compatible with 'ids' parameter). Example: "['https://arxiv.org/pdf/2307.06435']".
|
|
151
151
|
ids (array): Deprecated - use 'urls' instead. Array of document IDs obtained from searches. Example: "['https://arxiv.org/pdf/2307.06435']".
|
|
@@ -162,10 +162,10 @@ class ExaApp(APIApplication):
|
|
|
162
162
|
subpages (integer): The number of subpages to crawl. The actual number crawled may be limited by system constraints. Example: '1'.
|
|
163
163
|
subpageTarget (string): Keyword to find specific subpages of search results. Can be a single string or an array of strings, comma delimited. Example: 'sources'.
|
|
164
164
|
extras (object): Extra parameters to pass.
|
|
165
|
-
|
|
165
|
+
|
|
166
166
|
Returns:
|
|
167
167
|
dict[str, Any]: OK
|
|
168
|
-
|
|
168
|
+
|
|
169
169
|
Tags:
|
|
170
170
|
important
|
|
171
171
|
"""
|
|
@@ -190,17 +190,17 @@ class ExaApp(APIApplication):
|
|
|
190
190
|
|
|
191
191
|
def answer(self, query, stream=None, text=None, model=None) -> dict[str, Any]:
|
|
192
192
|
"""
|
|
193
|
-
|
|
194
|
-
|
|
193
|
+
Retrieves a direct, synthesized answer for a given query by calling the Exa `/answer` API endpoint. Unlike `search`, which returns web results, this function provides a conclusive response. It supports streaming, including source text, and selecting a search model.
|
|
194
|
+
|
|
195
195
|
Args:
|
|
196
196
|
query (string): The question or query to answer. Example: 'What is the latest valuation of SpaceX?'.
|
|
197
197
|
stream (boolean): If true, the response is returned as a server-sent events (SSS) stream.
|
|
198
198
|
text (boolean): If true, the response includes full text content in the search results
|
|
199
199
|
model (string): The search model to use for the answer. Exa passes only one query to exa, while exa-pro also passes 2 expanded queries to our search model.
|
|
200
|
-
|
|
200
|
+
|
|
201
201
|
Returns:
|
|
202
202
|
dict[str, Any]: OK
|
|
203
|
-
|
|
203
|
+
|
|
204
204
|
Tags:
|
|
205
205
|
important
|
|
206
206
|
"""
|
|
@@ -218,4 +218,9 @@ class ExaApp(APIApplication):
|
|
|
218
218
|
return response.json()
|
|
219
219
|
|
|
220
220
|
def list_tools(self):
|
|
221
|
-
return [
|
|
221
|
+
return [
|
|
222
|
+
self.search_with_filters,
|
|
223
|
+
self.find_similar_by_url,
|
|
224
|
+
self.fetch_page_content,
|
|
225
|
+
self.answer
|
|
226
|
+
]
|
|
@@ -28,6 +28,9 @@ class FalaiApp(APIApplication):
|
|
|
28
28
|
|
|
29
29
|
@property
|
|
30
30
|
def fal_client(self) -> AsyncClient:
|
|
31
|
+
"""
|
|
32
|
+
A cached property that lazily initializes an `AsyncClient` instance for API communication. It retrieves the API key from the configured integration, centralizing authentication for all Fal AI operations. Raises `NotAuthorizedError` if the key is missing.
|
|
33
|
+
"""
|
|
31
34
|
if self._fal_client is None:
|
|
32
35
|
credentials = self.integration.get_credentials()
|
|
33
36
|
logger.info(f"Credentials: {credentials}")
|
|
@@ -55,21 +58,21 @@ class FalaiApp(APIApplication):
|
|
|
55
58
|
hint: str | None = None,
|
|
56
59
|
) -> Any:
|
|
57
60
|
"""
|
|
58
|
-
|
|
59
|
-
|
|
61
|
+
Executes a Fal AI application synchronously, waiting for completion and returning the result directly. This method is suited for short-running tasks, unlike `submit` which queues a job for asynchronous processing and returns a request ID instead of the final output.
|
|
62
|
+
|
|
60
63
|
Args:
|
|
61
64
|
arguments: A dictionary of arguments for the application
|
|
62
65
|
application: The name or ID of the Fal application (defaults to 'fal-ai/flux/dev')
|
|
63
66
|
path: Optional subpath for the application endpoint
|
|
64
67
|
timeout: Optional timeout in seconds for the request
|
|
65
68
|
hint: Optional hint for runner selection
|
|
66
|
-
|
|
69
|
+
|
|
67
70
|
Returns:
|
|
68
71
|
The result of the application execution as a Python object (converted from JSON response)
|
|
69
|
-
|
|
72
|
+
|
|
70
73
|
Raises:
|
|
71
74
|
ToolError: Raised when the Fal API request fails, wrapping the original exception
|
|
72
|
-
|
|
75
|
+
|
|
73
76
|
Tags:
|
|
74
77
|
run, execute, ai, synchronous, fal, important
|
|
75
78
|
"""
|
|
@@ -98,8 +101,8 @@ class FalaiApp(APIApplication):
|
|
|
98
101
|
priority: Priority | None = None,
|
|
99
102
|
) -> str:
|
|
100
103
|
"""
|
|
101
|
-
Submits a
|
|
102
|
-
|
|
104
|
+
Submits a job to the Fal AI queue for asynchronous processing. It immediately returns a unique request ID for tracking the job's lifecycle with the `status`, `result`, and `cancel` methods. Unlike the synchronous `run` method, this function does not wait for the job's completion.
|
|
105
|
+
|
|
103
106
|
Args:
|
|
104
107
|
arguments: A dictionary of arguments for the application
|
|
105
108
|
application: The name or ID of the Fal application, defaulting to 'fal-ai/flux/dev'
|
|
@@ -107,13 +110,13 @@ class FalaiApp(APIApplication):
|
|
|
107
110
|
hint: Optional hint for runner selection
|
|
108
111
|
webhook_url: Optional URL to receive a webhook when the request completes
|
|
109
112
|
priority: Optional queue priority ('normal' or 'low')
|
|
110
|
-
|
|
113
|
+
|
|
111
114
|
Returns:
|
|
112
115
|
The request ID (str) of the submitted asynchronous job
|
|
113
|
-
|
|
116
|
+
|
|
114
117
|
Raises:
|
|
115
118
|
ToolError: Raised when the Fal API request fails, wrapping the original exception
|
|
116
|
-
|
|
119
|
+
|
|
117
120
|
Tags:
|
|
118
121
|
submit, async_job, start, ai, queue
|
|
119
122
|
"""
|
|
@@ -136,26 +139,26 @@ class FalaiApp(APIApplication):
|
|
|
136
139
|
f"Failed to submit Fal application {application}: {e}"
|
|
137
140
|
) from e
|
|
138
141
|
|
|
139
|
-
async def
|
|
142
|
+
async def check_status(
|
|
140
143
|
self,
|
|
141
144
|
request_id: str,
|
|
142
145
|
application: str = "fal-ai/flux/dev",
|
|
143
146
|
with_logs: bool = False,
|
|
144
147
|
) -> Status:
|
|
145
148
|
"""
|
|
146
|
-
Checks the
|
|
147
|
-
|
|
149
|
+
Checks the execution state (e.g., Queued, InProgress) of an asynchronous Fal AI job using its request ID. It provides a non-blocking way to monitor jobs initiated via `submit` without fetching the final `result`, and can optionally include logs.
|
|
150
|
+
|
|
148
151
|
Args:
|
|
149
152
|
request_id: The unique identifier of the submitted request, obtained from a previous submit operation
|
|
150
153
|
application: The name or ID of the Fal application (defaults to 'fal-ai/flux/dev')
|
|
151
154
|
with_logs: Boolean flag to include execution logs in the status response (defaults to False)
|
|
152
|
-
|
|
155
|
+
|
|
153
156
|
Returns:
|
|
154
157
|
A Status object containing the current state of the request (Queued, InProgress, or Completed)
|
|
155
|
-
|
|
158
|
+
|
|
156
159
|
Raises:
|
|
157
160
|
ToolError: Raised when the Fal API request fails or when the provided request ID is invalid
|
|
158
|
-
|
|
161
|
+
|
|
159
162
|
Tags:
|
|
160
163
|
status, check, async_job, monitoring, ai
|
|
161
164
|
"""
|
|
@@ -174,22 +177,22 @@ class FalaiApp(APIApplication):
|
|
|
174
177
|
f"Failed to get status for Fal request_id {request_id}: {e}"
|
|
175
178
|
) from e
|
|
176
179
|
|
|
177
|
-
async def
|
|
180
|
+
async def get_result(
|
|
178
181
|
self, request_id: str, application: str = "fal-ai/flux/dev"
|
|
179
182
|
) -> Any:
|
|
180
183
|
"""
|
|
181
|
-
|
|
182
|
-
|
|
184
|
+
Fetches the final output for an asynchronous job, identified by its request_id. This function blocks execution, waiting for the job initiated by `submit` to complete before returning the result. It complements the non-blocking `status` check by providing a synchronous way to get a completed job's data.
|
|
185
|
+
|
|
183
186
|
Args:
|
|
184
187
|
request_id: The unique identifier of the submitted request
|
|
185
188
|
application: The name or ID of the Fal application (defaults to 'fal-ai/flux/dev')
|
|
186
|
-
|
|
189
|
+
|
|
187
190
|
Returns:
|
|
188
191
|
The result of the application execution, converted from JSON response to Python data structures (dict/list)
|
|
189
|
-
|
|
192
|
+
|
|
190
193
|
Raises:
|
|
191
194
|
ToolError: When the Fal API request fails or the request does not complete successfully
|
|
192
|
-
|
|
195
|
+
|
|
193
196
|
Tags:
|
|
194
197
|
result, async-job, status, wait, ai
|
|
195
198
|
"""
|
|
@@ -212,18 +215,18 @@ class FalaiApp(APIApplication):
|
|
|
212
215
|
self, request_id: str, application: str = "fal-ai/flux/dev"
|
|
213
216
|
) -> None:
|
|
214
217
|
"""
|
|
215
|
-
Asynchronously cancels a running or queued Fal AI
|
|
216
|
-
|
|
218
|
+
Asynchronously cancels a running or queued Fal AI job identified by its `request_id`. This function complements the `submit` method, providing a way to terminate asynchronous tasks before completion. API errors during the cancellation process are wrapped in a `ToolError`.
|
|
219
|
+
|
|
217
220
|
Args:
|
|
218
221
|
request_id: The unique identifier of the submitted Fal AI request to cancel
|
|
219
222
|
application: The name or ID of the Fal application (defaults to 'fal-ai/flux/dev')
|
|
220
|
-
|
|
223
|
+
|
|
221
224
|
Returns:
|
|
222
225
|
None. The function doesn't return any value.
|
|
223
|
-
|
|
226
|
+
|
|
224
227
|
Raises:
|
|
225
228
|
ToolError: Raised when the cancellation request fails due to API errors or if the request cannot be cancelled
|
|
226
|
-
|
|
229
|
+
|
|
227
230
|
Tags:
|
|
228
231
|
cancel, async_job, ai, fal, management
|
|
229
232
|
"""
|
|
@@ -241,17 +244,17 @@ class FalaiApp(APIApplication):
|
|
|
241
244
|
|
|
242
245
|
async def upload_file(self, path: str) -> str:
|
|
243
246
|
"""
|
|
244
|
-
|
|
245
|
-
|
|
247
|
+
Asynchronously uploads a local file from a specified path to the Fal Content Delivery Network (CDN). Upon success, it returns a public URL for the file, making it accessible for use as input in other Fal AI application requests. A `ToolError` is raised on failure.
|
|
248
|
+
|
|
246
249
|
Args:
|
|
247
250
|
path: The absolute or relative path to the local file
|
|
248
|
-
|
|
251
|
+
|
|
249
252
|
Returns:
|
|
250
253
|
A string containing the public URL of the uploaded file on the CDN
|
|
251
|
-
|
|
254
|
+
|
|
252
255
|
Raises:
|
|
253
256
|
ToolError: If the file is not found or if the upload operation fails
|
|
254
|
-
|
|
257
|
+
|
|
255
258
|
Tags:
|
|
256
259
|
upload, file, cdn, storage, async, important
|
|
257
260
|
"""
|
|
@@ -265,7 +268,7 @@ class FalaiApp(APIApplication):
|
|
|
265
268
|
logger.error(f"Error uploading file {path} to Fal CDN: {e}", exc_info=True)
|
|
266
269
|
raise ToolError(f"Failed to upload file {path}: {e}") from e
|
|
267
270
|
|
|
268
|
-
async def
|
|
271
|
+
async def run_image_generation(
|
|
269
272
|
self,
|
|
270
273
|
prompt: str,
|
|
271
274
|
seed: int | None = 6252023,
|
|
@@ -277,8 +280,8 @@ class FalaiApp(APIApplication):
|
|
|
277
280
|
hint: str | None = None,
|
|
278
281
|
) -> Any:
|
|
279
282
|
"""
|
|
280
|
-
|
|
281
|
-
|
|
283
|
+
A specialized wrapper for the `run` method that synchronously generates images using the 'fal-ai/flux/dev' model. It simplifies image creation with common parameters like `prompt` and `seed`, waits for the task to complete, and returns the result containing image URLs and metadata.
|
|
284
|
+
|
|
282
285
|
Args:
|
|
283
286
|
prompt: The text prompt used to guide the image generation
|
|
284
287
|
seed: Random seed for reproducible image generation (default: 6252023)
|
|
@@ -288,13 +291,13 @@ class FalaiApp(APIApplication):
|
|
|
288
291
|
path: Subpath for the application endpoint (rarely used)
|
|
289
292
|
timeout: Maximum time in seconds to wait for the request to complete
|
|
290
293
|
hint: Hint string for runner selection
|
|
291
|
-
|
|
294
|
+
|
|
292
295
|
Returns:
|
|
293
296
|
A dictionary containing the generated image URLs and related metadata
|
|
294
|
-
|
|
297
|
+
|
|
295
298
|
Raises:
|
|
296
299
|
ToolError: When the image generation request fails or encounters an error
|
|
297
|
-
|
|
300
|
+
|
|
298
301
|
Tags:
|
|
299
302
|
generate, image, ai, async, important, flux, customizable, default
|
|
300
303
|
"""
|
|
@@ -324,9 +327,9 @@ class FalaiApp(APIApplication):
|
|
|
324
327
|
return [
|
|
325
328
|
self.run,
|
|
326
329
|
self.submit,
|
|
327
|
-
self.
|
|
328
|
-
self.
|
|
330
|
+
self.check_status,
|
|
331
|
+
self.get_result,
|
|
329
332
|
self.cancel,
|
|
330
333
|
self.upload_file,
|
|
331
|
-
self.
|
|
334
|
+
self.run_image_generation,
|
|
332
335
|
]
|