camel-ai 0.1.5.5__py3-none-any.whl → 0.1.5.9__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 camel-ai might be problematic. Click here for more details.

Files changed (97) hide show
  1. camel/__init__.py +1 -1
  2. camel/agents/chat_agent.py +3 -3
  3. camel/agents/critic_agent.py +1 -1
  4. camel/agents/deductive_reasoner_agent.py +4 -4
  5. camel/agents/embodied_agent.py +1 -1
  6. camel/agents/knowledge_graph_agent.py +13 -17
  7. camel/agents/role_assignment_agent.py +1 -1
  8. camel/agents/search_agent.py +4 -5
  9. camel/agents/task_agent.py +5 -6
  10. camel/configs/__init__.py +15 -0
  11. camel/configs/gemini_config.py +98 -0
  12. camel/configs/groq_config.py +119 -0
  13. camel/configs/litellm_config.py +1 -1
  14. camel/configs/mistral_config.py +81 -0
  15. camel/configs/ollama_config.py +1 -1
  16. camel/configs/openai_config.py +1 -1
  17. camel/configs/vllm_config.py +103 -0
  18. camel/configs/zhipuai_config.py +1 -1
  19. camel/embeddings/__init__.py +2 -0
  20. camel/embeddings/mistral_embedding.py +89 -0
  21. camel/interpreters/__init__.py +2 -0
  22. camel/interpreters/ipython_interpreter.py +167 -0
  23. camel/models/__init__.py +10 -0
  24. camel/models/anthropic_model.py +7 -2
  25. camel/models/azure_openai_model.py +152 -0
  26. camel/models/base_model.py +9 -2
  27. camel/models/gemini_model.py +215 -0
  28. camel/models/groq_model.py +131 -0
  29. camel/models/litellm_model.py +26 -4
  30. camel/models/mistral_model.py +169 -0
  31. camel/models/model_factory.py +33 -5
  32. camel/models/ollama_model.py +21 -2
  33. camel/models/open_source_model.py +11 -3
  34. camel/models/openai_model.py +7 -2
  35. camel/models/stub_model.py +4 -4
  36. camel/models/vllm_model.py +138 -0
  37. camel/models/zhipuai_model.py +7 -4
  38. camel/prompts/__init__.py +2 -2
  39. camel/prompts/task_prompt_template.py +4 -4
  40. camel/prompts/{descripte_video_prompt.py → video_description_prompt.py} +1 -1
  41. camel/retrievers/auto_retriever.py +2 -0
  42. camel/storages/graph_storages/neo4j_graph.py +5 -0
  43. camel/toolkits/__init__.py +36 -0
  44. camel/toolkits/base.py +1 -1
  45. camel/toolkits/code_execution.py +1 -1
  46. camel/toolkits/github_toolkit.py +3 -2
  47. camel/toolkits/google_maps_toolkit.py +367 -0
  48. camel/toolkits/math_toolkit.py +79 -0
  49. camel/toolkits/open_api_toolkit.py +548 -0
  50. camel/toolkits/retrieval_toolkit.py +76 -0
  51. camel/toolkits/search_toolkit.py +326 -0
  52. camel/toolkits/slack_toolkit.py +308 -0
  53. camel/toolkits/twitter_toolkit.py +522 -0
  54. camel/toolkits/weather_toolkit.py +173 -0
  55. camel/types/enums.py +163 -30
  56. camel/utils/__init__.py +4 -0
  57. camel/utils/async_func.py +1 -1
  58. camel/utils/token_counting.py +182 -40
  59. {camel_ai-0.1.5.5.dist-info → camel_ai-0.1.5.9.dist-info}/METADATA +43 -3
  60. camel_ai-0.1.5.9.dist-info/RECORD +165 -0
  61. camel/functions/__init__.py +0 -51
  62. camel/functions/google_maps_function.py +0 -335
  63. camel/functions/math_functions.py +0 -61
  64. camel/functions/open_api_function.py +0 -508
  65. camel/functions/retrieval_functions.py +0 -61
  66. camel/functions/search_functions.py +0 -298
  67. camel/functions/slack_functions.py +0 -286
  68. camel/functions/twitter_function.py +0 -479
  69. camel/functions/weather_functions.py +0 -144
  70. camel_ai-0.1.5.5.dist-info/RECORD +0 -155
  71. /camel/{functions → toolkits}/open_api_specs/biztoc/__init__.py +0 -0
  72. /camel/{functions → toolkits}/open_api_specs/biztoc/ai-plugin.json +0 -0
  73. /camel/{functions → toolkits}/open_api_specs/biztoc/openapi.yaml +0 -0
  74. /camel/{functions → toolkits}/open_api_specs/coursera/__init__.py +0 -0
  75. /camel/{functions → toolkits}/open_api_specs/coursera/openapi.yaml +0 -0
  76. /camel/{functions → toolkits}/open_api_specs/create_qr_code/__init__.py +0 -0
  77. /camel/{functions → toolkits}/open_api_specs/create_qr_code/openapi.yaml +0 -0
  78. /camel/{functions → toolkits}/open_api_specs/klarna/__init__.py +0 -0
  79. /camel/{functions → toolkits}/open_api_specs/klarna/openapi.yaml +0 -0
  80. /camel/{functions → toolkits}/open_api_specs/nasa_apod/__init__.py +0 -0
  81. /camel/{functions → toolkits}/open_api_specs/nasa_apod/openapi.yaml +0 -0
  82. /camel/{functions → toolkits}/open_api_specs/outschool/__init__.py +0 -0
  83. /camel/{functions → toolkits}/open_api_specs/outschool/ai-plugin.json +0 -0
  84. /camel/{functions → toolkits}/open_api_specs/outschool/openapi.yaml +0 -0
  85. /camel/{functions → toolkits}/open_api_specs/outschool/paths/__init__.py +0 -0
  86. /camel/{functions → toolkits}/open_api_specs/outschool/paths/get_classes.py +0 -0
  87. /camel/{functions → toolkits}/open_api_specs/outschool/paths/search_teachers.py +0 -0
  88. /camel/{functions → toolkits}/open_api_specs/security_config.py +0 -0
  89. /camel/{functions → toolkits}/open_api_specs/speak/__init__.py +0 -0
  90. /camel/{functions → toolkits}/open_api_specs/speak/openapi.yaml +0 -0
  91. /camel/{functions → toolkits}/open_api_specs/web_scraper/__init__.py +0 -0
  92. /camel/{functions → toolkits}/open_api_specs/web_scraper/ai-plugin.json +0 -0
  93. /camel/{functions → toolkits}/open_api_specs/web_scraper/openapi.yaml +0 -0
  94. /camel/{functions → toolkits}/open_api_specs/web_scraper/paths/__init__.py +0 -0
  95. /camel/{functions → toolkits}/open_api_specs/web_scraper/paths/scraper.py +0 -0
  96. /camel/{functions → toolkits}/openai_function.py +0 -0
  97. {camel_ai-0.1.5.5.dist-info → camel_ai-0.1.5.9.dist-info}/WHEEL +0 -0
@@ -1,479 +0,0 @@
1
- # =========== Copyright 2023 @ CAMEL-AI.org. All Rights Reserved. ===========
2
- # Licensed under the Apache License, Version 2.0 (the “License”);
3
- # you may not use this file except in compliance with the License.
4
- # You may obtain a copy of the License at
5
- #
6
- # http://www.apache.org/licenses/LICENSE-2.0
7
- #
8
- # Unless required by applicable law or agreed to in writing, software
9
- # distributed under the License is distributed on an “AS IS” BASIS,
10
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11
- # See the License for the specific language governing permissions and
12
- # limitations under the License.
13
- # =========== Copyright 2023 @ CAMEL-AI.org. All Rights Reserved. ===========
14
- import datetime
15
- import os
16
- from http import HTTPStatus
17
- from http.client import responses
18
- from typing import List, Optional, Tuple, Union
19
-
20
- import requests
21
-
22
- from camel.functions import OpenAIFunction
23
- from camel.utils import dependencies_required
24
-
25
- TWEET_TEXT_LIMIT = 280
26
-
27
-
28
- def get_twitter_api_key() -> Tuple[str, str]:
29
- r"""Retrieve the Twitter API key and secret from environment variables.
30
-
31
- Returns:
32
- Tuple[str, str]: A tuple containing the Twitter API key and secret.
33
-
34
- Raises:
35
- ValueError: If the API key or secret is not found in the environment
36
- variables.
37
- """
38
- # Get `TWITTER_CONSUMER_KEY` and `TWITTER_CONSUMER_SECRET` here:
39
- # https://developer.twitter.com/en/portal/products/free
40
- TWITTER_CONSUMER_KEY = os.environ.get("TWITTER_CONSUMER_KEY")
41
- TWITTER_CONSUMER_SECRET = os.environ.get("TWITTER_CONSUMER_SECRET")
42
-
43
- if not TWITTER_CONSUMER_KEY or not TWITTER_CONSUMER_SECRET:
44
- missing_keys = ", ".join(
45
- [
46
- "TWITTER_CONSUMER_KEY" if not TWITTER_CONSUMER_KEY else "",
47
- "TWITTER_CONSUMER_SECRET"
48
- if not TWITTER_CONSUMER_SECRET
49
- else "",
50
- ]
51
- ).strip(", ")
52
- raise ValueError(
53
- f"{missing_keys} not found in environment variables. Get them "
54
- "here: `https://developer.twitter.com/en/portal/products/free`."
55
- )
56
- return TWITTER_CONSUMER_KEY, TWITTER_CONSUMER_SECRET
57
-
58
-
59
- @dependencies_required('requests_oauthlib')
60
- def get_oauth_session() -> requests.Session:
61
- r'''Initiates an OAuth1Session with Twitter's API and returns it.
62
-
63
- The function first fetches a request token, then prompts the user to
64
- authorize the application. After the user has authorized the application
65
- and provided a verifier (PIN), the function fetches an access token.
66
- Finally, a new OAuth1Session is created with the access token and returned.
67
-
68
- Raises:
69
- RuntimeError: If an error occurs while fetching the OAuth access token
70
- or the OAuth request token.
71
-
72
- Returns:
73
- requests_oauthlib.OAuth1Session: An OAuth1Session object authenticated
74
- with the user's access token.
75
-
76
- Reference:
77
- https://github.com/twitterdev/Twitter-API-v2-sample-code/blob/main/Manage-Tweets/create_tweet.py
78
- https://github.com/twitterdev/Twitter-API-v2-sample-code/blob/main/User-Lookup/get_users_me_user_context.py
79
- '''
80
- from requests_oauthlib import OAuth1Session
81
-
82
- consumer_key, consumer_secret = get_twitter_api_key()
83
-
84
- # Get request token
85
- request_token_url = (
86
- "https://api.twitter.com/oauth/request_token"
87
- "?oauth_callback=oob&x_auth_access_type=write"
88
- )
89
- oauth = OAuth1Session(consumer_key, client_secret=consumer_secret)
90
-
91
- try:
92
- fetch_response = oauth.fetch_request_token(request_token_url)
93
- except Exception as e:
94
- raise RuntimeError(
95
- f"Error occurred while fetching the OAuth access token: {e}"
96
- )
97
-
98
- resource_owner_key = fetch_response.get("oauth_token")
99
- resource_owner_secret = fetch_response.get("oauth_token_secret")
100
-
101
- # Get authorization
102
- base_authorization_url = "https://api.twitter.com/oauth/authorize"
103
- authorization_url = oauth.authorization_url(base_authorization_url)
104
- print("Please go here and authorize: %s" % authorization_url)
105
- verifier = input("Paste the PIN here: ")
106
-
107
- # Get the access token
108
- access_token_url = "https://api.twitter.com/oauth/access_token"
109
- oauth = OAuth1Session(
110
- consumer_key,
111
- client_secret=consumer_secret,
112
- resource_owner_key=resource_owner_key,
113
- resource_owner_secret=resource_owner_secret,
114
- verifier=verifier,
115
- )
116
-
117
- try:
118
- oauth_tokens = oauth.fetch_access_token(access_token_url)
119
- except Exception as e:
120
- raise RuntimeError(
121
- f"Error occurred while fetching the OAuth request token: {e}"
122
- )
123
-
124
- # Create a new OAuth1Session with the access token
125
- oauth = OAuth1Session(
126
- consumer_key,
127
- client_secret=consumer_secret,
128
- resource_owner_key=oauth_tokens["oauth_token"],
129
- resource_owner_secret=oauth_tokens["oauth_token_secret"],
130
- )
131
- return oauth
132
-
133
-
134
- def handle_http_error(response: requests.Response) -> str:
135
- r"""Handles the HTTP response by checking the status code and returning an
136
- appropriate message if there is an error.
137
-
138
- Args:
139
- response (requests.Response): The HTTP response to handle.
140
-
141
- Returns:
142
- str: A string describing the error, if any. If there is no error, the
143
- function returns an "Unexpected Exception" message.
144
-
145
- Reference:
146
- https://github.com/tweepy/tweepy/blob/master/tweepy/client.py#L64
147
- """
148
- if response.status_code in responses:
149
- # For 5xx server errors, return "Twitter Server Error"
150
- if 500 <= response.status_code < 600:
151
- return "Twitter Server Error"
152
- else:
153
- error_message = responses[response.status_code] + " Error"
154
- return error_message
155
- elif not 200 <= response.status_code < 300:
156
- return "HTTP Exception"
157
- else:
158
- return "Unexpected Exception"
159
-
160
-
161
- def create_tweet(
162
- *,
163
- text: str,
164
- poll_options: Optional[List[str]] = None,
165
- poll_duration_minutes: Optional[int] = None,
166
- quote_tweet_id: Optional[Union[int, str]] = None,
167
- ) -> str:
168
- r"""Creates a new tweet, optionally including a poll or a quote tweet, or
169
- simply a text-only tweet.
170
-
171
- This function sends a POST request to the Twitter API to create a new
172
- tweet. The tweet can be a text-only tweet, or optionally include a poll or
173
- be a quote tweet. A confirmation prompt is presented to the user before the
174
- tweet is created.
175
-
176
- Args:
177
- text (str): The text of the tweet. The Twitter character limit for a
178
- single tweet is 280 characters.
179
- poll_options (Optional[List[str]]): A list of poll options for a tweet
180
- with a poll.
181
- poll_duration_minutes (Optional[int]): Duration of the poll in minutes
182
- for a tweet with a poll. This is only required if the request
183
- includes poll_options.
184
- quote_tweet_id (Optional[Union[int, str]]): Link to the tweet being
185
- quoted.
186
-
187
- Note:
188
- You can only provide either the `quote_tweet_id` parameter or the pair
189
- of `poll_duration_minutes` and `poll_options` parameters, not both.
190
-
191
- Returns:
192
- str: A message indicating the success of the tweet creation, including
193
- the tweet ID and text. If the request to the Twitter API is not
194
- successful, the return is an error message.
195
-
196
- Reference:
197
- https://developer.twitter.com/en/docs/twitter-api/tweets/manage-tweets/api-reference/post-tweets
198
- https://github.com/xdevplatform/Twitter-API-v2-sample-code/blob/main/Manage-Tweets/create_tweet.py
199
- """
200
- # validate text
201
- if text is None:
202
- return "Text cannot be None"
203
- elif len(text) > TWEET_TEXT_LIMIT:
204
- return "Text must not exceed 280 characters."
205
-
206
- # Validate poll options and duration
207
- if (poll_options is None) != (poll_duration_minutes is None):
208
- return (
209
- "Error: Both `poll_options` and `poll_duration_minutes` must "
210
- "be provided together or not at all."
211
- )
212
-
213
- # Validate exclusive parameters
214
- if quote_tweet_id is not None and (poll_options or poll_duration_minutes):
215
- return (
216
- "Error: Cannot provide both `quote_tweet_id` and "
217
- "(`poll_options` or `poll_duration_minutes`)."
218
- )
219
-
220
- # Print the parameters that are not None
221
- params = {
222
- "text": text,
223
- "poll_options": poll_options,
224
- "poll_duration_minutes": poll_duration_minutes,
225
- "quote_tweet_id": quote_tweet_id,
226
- }
227
- print("You are going to create a tweet with following parameters:")
228
- for key, value in params.items():
229
- if value is not None:
230
- print(f"{key}: {value}")
231
-
232
- # Add a confirmation prompt at the beginning of the function
233
- confirm = input("Are you sure you want to create this tweet? (yes/no): ")
234
- if confirm.lower() != "yes":
235
- return "Execution cancelled by the user."
236
-
237
- oauth = get_oauth_session()
238
- json_data = {}
239
-
240
- if poll_options is not None and poll_duration_minutes is not None:
241
- json_data["poll"] = {
242
- "options": poll_options,
243
- "duration_minutes": poll_duration_minutes,
244
- }
245
-
246
- if quote_tweet_id is not None:
247
- json_data["quote_tweet_id"] = str(quote_tweet_id) # type: ignore[assignment]
248
-
249
- json_data["text"] = text # type: ignore[assignment]
250
-
251
- # Making the request
252
- response = oauth.post(
253
- "https://api.twitter.com/2/tweets",
254
- json=json_data,
255
- )
256
-
257
- if response.status_code != HTTPStatus.CREATED:
258
- error_type = handle_http_error(response)
259
- # use string concatenation to satisfy flake8
260
- return (
261
- "Request returned a(n) "
262
- + str(error_type)
263
- + ": "
264
- + str(response.status_code)
265
- + " "
266
- + response.text
267
- )
268
-
269
- # Saving the response as JSON
270
- json_response = response.json()
271
-
272
- tweet_id = json_response["data"]["id"]
273
- tweet_text = json_response["data"]["text"]
274
-
275
- response_str = (
276
- f"Create tweet successful. "
277
- f"The tweet ID is: {tweet_id}. "
278
- f"The tweet text is: '{tweet_text}'."
279
- )
280
-
281
- return response_str
282
-
283
-
284
- def delete_tweet(tweet_id: str) -> str:
285
- r"""Deletes a tweet with the specified ID for an authorized user.
286
-
287
- This function sends a DELETE request to the Twitter API to delete
288
- a tweet with the specified ID. Before sending the request, it
289
- prompts the user to confirm the deletion.
290
-
291
- Args:
292
- tweet_id (str): The ID of the tweet to delete.
293
-
294
- Returns:
295
- str: A message indicating the result of the deletion. If the
296
- deletion was successful, the message includes the ID of the
297
- deleted tweet. If the deletion was not successful, the message
298
- includes an error message.
299
-
300
- Reference:
301
- https://developer.twitter.com/en/docs/twitter-api/tweets/manage-tweets/api-reference/delete-tweets-id
302
- """
303
- # Print the parameters that are not None
304
- if tweet_id is not None:
305
- print(
306
- f"You are going to delete a tweet with the following "
307
- f"ID: {tweet_id}"
308
- )
309
-
310
- # Add a confirmation prompt at the beginning of the function
311
- confirm = input("Are you sure you want to delete this tweet? (yes/no): ")
312
- if confirm.lower() != "yes":
313
- return "Execution cancelled by the user."
314
-
315
- oauth = get_oauth_session()
316
-
317
- # Making the request
318
- response = oauth.delete(
319
- f"https://api.twitter.com/2/tweets/{tweet_id}",
320
- )
321
-
322
- if response.status_code != HTTPStatus.OK:
323
- error_type = handle_http_error(response)
324
- # use string concatenation to satisfy flake8
325
- return (
326
- "Request returned a(n) "
327
- + str(error_type)
328
- + ": "
329
- + str(response.status_code)
330
- + " "
331
- + response.text
332
- )
333
-
334
- # Saving the response as JSON
335
- json_response = response.json()
336
- # `deleted_status` may be True or False. Defaults to False if not found.
337
- deleted_status = json_response.get("data", {}).get("deleted", False)
338
- response_str = (
339
- f"Delete tweet successful: {deleted_status}. "
340
- f"The tweet ID is: {tweet_id}. "
341
- )
342
- return response_str
343
-
344
-
345
- def get_my_user_profile() -> str:
346
- r"""Retrieves and formats the authenticated user's Twitter profile info.
347
-
348
- This function sends a GET request to the Twitter API to retrieve the
349
- authenticated user's profile information, including their pinned tweet.
350
- It then formats this information into a readable report.
351
-
352
- Returns:
353
- str: A formatted report of the authenticated user's Twitter profile
354
- information. This includes their ID, name, username, description,
355
- location, most recent tweet ID, profile image URL, account creation
356
- date, protection status, verification type, public metrics, and
357
- pinned tweet information. If the request to the Twitter API is not
358
- successful, the return is an error message.
359
-
360
- Reference:
361
- https://developer.twitter.com/en/docs/twitter-api/users/lookup/api-reference/get-users-me
362
- """
363
- oauth = get_oauth_session()
364
-
365
- tweet_fields = ["created_at", "text"]
366
- user_fields = [
367
- "created_at",
368
- "description",
369
- "id",
370
- "location",
371
- "most_recent_tweet_id",
372
- "name",
373
- "pinned_tweet_id",
374
- "profile_image_url",
375
- "protected",
376
- "public_metrics",
377
- "url",
378
- "username",
379
- "verified_type",
380
- ]
381
- params = {
382
- "expansions": "pinned_tweet_id",
383
- "tweet.fields": ",".join(tweet_fields),
384
- "user.fields": ",".join(user_fields),
385
- }
386
-
387
- response = oauth.get("https://api.twitter.com/2/users/me", params=params)
388
-
389
- if response.status_code != HTTPStatus.OK:
390
- error_type = handle_http_error(response)
391
- error_message = "Request returned a(n) {}: {} {}".format(
392
- error_type, response.status_code, response.text
393
- )
394
- return error_message
395
-
396
- json_response = response.json()
397
-
398
- user_info = json_response.get('data', {})
399
- tweets = json_response.get('includes', {}).get('tweets', [{}])[0]
400
-
401
- user_report = ""
402
- user_report += f"ID: {user_info['id']}. "
403
- user_report += f"Name: {user_info['name']}. "
404
- user_report += f"Username: {user_info['username']}. "
405
-
406
- # Define the part of keys that need to be repeatedly processed
407
- user_info_keys = [
408
- 'description',
409
- 'location',
410
- 'most_recent_tweet_id',
411
- 'profile_image_url',
412
- ]
413
- for key in user_info_keys:
414
- value = user_info.get(key)
415
- if user_info.get(key):
416
- user_report += f"{key.replace('_', ' ').capitalize()}: {value}. "
417
-
418
- if 'created_at' in user_info:
419
- created_at = datetime.datetime.strptime(
420
- user_info['created_at'], "%Y-%m-%dT%H:%M:%S.%fZ"
421
- )
422
- date_str = created_at.strftime('%B %d, %Y at %H:%M:%S')
423
- user_report += f"Account created at: {date_str}. "
424
-
425
- protection_status = "private" if user_info['protected'] else "public"
426
- user_report += f"Protected: This user's Tweets are {protection_status}. "
427
-
428
- verification_messages = {
429
- 'blue': (
430
- "The user has a blue verification, typically reserved for "
431
- "public figures, celebrities, or global brands. "
432
- ),
433
- 'business': (
434
- "The user has a business verification, typically "
435
- "reserved for businesses and corporations. "
436
- ),
437
- 'government': (
438
- "The user has a government verification, typically "
439
- "reserved for government officials or entities. "
440
- ),
441
- 'none': "The user is not verified. ",
442
- }
443
- verification_type = user_info.get('verified_type', 'none')
444
- user_report += (
445
- f"Verified type: {verification_messages.get(verification_type)}"
446
- )
447
-
448
- if 'public_metrics' in user_info:
449
- user_report += "Public metrics: "
450
- metrics = user_info['public_metrics']
451
- user_report += (
452
- f"The user has {metrics.get('followers_count', 0)} followers, "
453
- f"is following {metrics.get('following_count', 0)} users, "
454
- f"has made {metrics.get('tweet_count', 0)} tweets, "
455
- f"is listed in {metrics.get('listed_count', 0)} lists, "
456
- f"and has received {metrics.get('like_count', 0)} likes. "
457
- )
458
-
459
- if 'pinned_tweet_id' in user_info:
460
- user_report += f"Pinned tweet ID: {user_info['pinned_tweet_id']}. "
461
-
462
- if 'created_at' in tweets and 'text' in tweets:
463
- user_report += "\nPinned tweet information: "
464
- tweet_created_at = datetime.datetime.strptime(
465
- tweets['created_at'], "%Y-%m-%dT%H:%M:%S.%fZ"
466
- )
467
- user_report += (
468
- f"Pinned tweet created at "
469
- f"{tweet_created_at.strftime('%B %d, %Y at %H:%M:%S')} "
470
- f"with text: '{tweets['text']}'."
471
- )
472
-
473
- return user_report
474
-
475
-
476
- TWITTER_FUNCS: List[OpenAIFunction] = [
477
- OpenAIFunction(func) # type: ignore[arg-type]
478
- for func in [create_tweet, delete_tweet, get_my_user_profile]
479
- ]
@@ -1,144 +0,0 @@
1
- # =========== Copyright 2023 @ CAMEL-AI.org. All Rights Reserved. ===========
2
- # Licensed under the Apache License, Version 2.0 (the “License”);
3
- # you may not use this file except in compliance with the License.
4
- # You may obtain a copy of the License at
5
- #
6
- # http://www.apache.org/licenses/LICENSE-2.0
7
- #
8
- # Unless required by applicable law or agreed to in writing, software
9
- # distributed under the License is distributed on an “AS IS” BASIS,
10
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11
- # See the License for the specific language governing permissions and
12
- # limitations under the License.
13
- # =========== Copyright 2023 @ CAMEL-AI.org. All Rights Reserved. ===========
14
- import os
15
- from typing import List, Literal
16
-
17
- from camel.functions.openai_function import OpenAIFunction
18
- from camel.utils import dependencies_required
19
-
20
-
21
- def get_openweathermap_api_key() -> str:
22
- r"""Retrieve the OpenWeatherMap API key from environment variables.
23
-
24
- Returns:
25
- str: The OpenWeatherMap API key.
26
-
27
- Raises:
28
- ValueError: If the API key is not found in the environment variables.
29
- """
30
- # Get `OPENWEATHERMAP_API_KEY` here: https://openweathermap.org
31
- OPENWEATHERMAP_API_KEY = os.environ.get('OPENWEATHERMAP_API_KEY')
32
- if not OPENWEATHERMAP_API_KEY:
33
- raise ValueError(
34
- "`OPENWEATHERMAP_API_KEY` not found in environment "
35
- "variables. Get `OPENWEATHERMAP_API_KEY` here: "
36
- "`https://openweathermap.org`."
37
- )
38
- return OPENWEATHERMAP_API_KEY
39
-
40
-
41
- @dependencies_required('pyowm')
42
- def get_weather_data(
43
- city: str,
44
- temp_units: Literal['kelvin', 'celsius', 'fahrenheit'] = 'kelvin',
45
- wind_units: Literal[
46
- 'meters_sec', 'miles_hour', 'knots', 'beaufort'
47
- ] = 'meters_sec',
48
- visibility_units: Literal['meters', 'miles'] = 'meters',
49
- time_units: Literal['unix', 'iso', 'date'] = 'unix',
50
- ) -> str:
51
- r"""Fetch and return a comprehensive weather report for a given city as a
52
- string. The report includes current weather conditions, temperature,
53
- wind details, visibility, and sunrise/sunset times, all formatted as
54
-
55
- The function interacts with the OpenWeatherMap API to retrieve the data.
56
-
57
- Args:
58
- city (str): The name of the city for which the weather information
59
- is desired. Format "City, CountryCode" (e.g., "Paris, FR"
60
- for Paris, France). If the country code is not provided,
61
- the API will search for the city in all countries, which
62
- may yield incorrect results if multiple cities with the
63
- same name exist.
64
- temp_units (Literal['kelvin', 'celsius', 'fahrenheit']): Units for
65
- temperature. (default: :obj:`kelvin`)
66
- wind_units (Literal['meters_sec', 'miles_hour', 'knots', 'beaufort']):
67
- Units for wind speed. (default: :obj:`meters_sec`)
68
- visibility_units (Literal['meters', 'miles']): Units for visibility
69
- distance. (default: :obj:`meters`)
70
- time_units (Literal['unix', 'iso', 'date']): Format for sunrise and
71
- sunset times. (default: :obj:`unix`)
72
-
73
- Returns:
74
- str: A string containing the fetched weather data, formatted in a
75
- readable manner. If an error occurs, a message indicating the
76
- error will be returned instead.
77
-
78
- Example of return string:
79
- "Weather in Paris, FR: 15°C, feels like 13°C. Max temp: 17°C, Min temp
80
- : 12°C.
81
- Wind: 5 m/s at 270 degrees. Visibility: 10 kilometers.
82
- Sunrise at 05:46:05 (UTC), Sunset at 18:42:20 (UTC)."
83
-
84
- Note:
85
- Please ensure that the API key is valid and has permissions to access
86
- the weather data.
87
- """
88
- # NOTE: This tool may not work as expected since the input arguments like
89
- # `time_units` should be enum types which are not supported yet.
90
- import pyowm
91
-
92
- OPENWEATHERMAP_API_KEY = get_openweathermap_api_key()
93
- owm = pyowm.OWM(OPENWEATHERMAP_API_KEY)
94
- mgr = owm.weather_manager()
95
-
96
- try:
97
- observation = mgr.weather_at_place(city)
98
- weather = observation.weather
99
-
100
- # Temperature
101
- temperature = weather.temperature(temp_units)
102
-
103
- # Wind
104
- wind_data = observation.weather.wind(unit=wind_units)
105
- wind_speed = wind_data.get('speed')
106
- # 'N/A' if the degree is not available
107
- wind_deg = wind_data.get('deg', 'N/A')
108
-
109
- # Visibility
110
- visibility_distance = observation.weather.visibility_distance
111
- visibility = (
112
- str(visibility_distance)
113
- if visibility_units == 'meters'
114
- else str(observation.weather.visibility(unit='miles'))
115
- )
116
-
117
- # Sunrise and Sunset
118
- sunrise_time = str(weather.sunrise_time(timeformat=time_units))
119
- sunset_time = str(weather.sunset_time(timeformat=time_units))
120
-
121
- # Compile all the weather details into a report string
122
- weather_report = (
123
- f"Weather in {city}: {temperature['temp']}°{temp_units.title()}, "
124
- f"feels like {temperature['feels_like']}°{temp_units.title()}. "
125
- f"Max temp: {temperature['temp_max']}°{temp_units.title()}, "
126
- f"Min temp: {temperature['temp_min']}°{temp_units.title()}. "
127
- f"Wind: {wind_speed} {wind_units} at {wind_deg} degrees. "
128
- f"Visibility: {visibility} {visibility_units}. "
129
- f"Sunrise at {sunrise_time}, Sunset at {sunset_time}."
130
- )
131
-
132
- return weather_report
133
-
134
- except Exception as e:
135
- error_message = (
136
- f"An error occurred while fetching weather data for {city}: "
137
- f"{e!s}."
138
- )
139
- return error_message
140
-
141
-
142
- WEATHER_FUNCS: List[OpenAIFunction] = [
143
- OpenAIFunction(func) for func in [get_weather_data]
144
- ]