webscout 8.3.5__py3-none-any.whl → 8.3.7__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 webscout might be problematic. Click here for more details.

Files changed (159) hide show
  1. webscout/AIutel.py +2 -0
  2. webscout/Bard.py +12 -6
  3. webscout/DWEBS.py +66 -57
  4. webscout/Provider/{UNFINISHED → AISEARCH}/PERPLEXED_search.py +34 -74
  5. webscout/Provider/AISEARCH/__init__.py +18 -11
  6. webscout/Provider/AISEARCH/scira_search.py +3 -1
  7. webscout/Provider/Aitopia.py +2 -3
  8. webscout/Provider/Andi.py +3 -3
  9. webscout/Provider/ChatGPTClone.py +1 -1
  10. webscout/Provider/ChatSandbox.py +1 -0
  11. webscout/Provider/Cloudflare.py +1 -1
  12. webscout/Provider/Cohere.py +1 -0
  13. webscout/Provider/Deepinfra.py +13 -10
  14. webscout/Provider/ExaAI.py +1 -1
  15. webscout/Provider/ExaChat.py +1 -80
  16. webscout/Provider/Flowith.py +6 -1
  17. webscout/Provider/Gemini.py +7 -5
  18. webscout/Provider/GeminiProxy.py +1 -0
  19. webscout/Provider/GithubChat.py +4 -1
  20. webscout/Provider/Groq.py +1 -1
  21. webscout/Provider/HeckAI.py +8 -4
  22. webscout/Provider/Jadve.py +23 -38
  23. webscout/Provider/K2Think.py +308 -0
  24. webscout/Provider/Koboldai.py +8 -186
  25. webscout/Provider/LambdaChat.py +2 -4
  26. webscout/Provider/Nemotron.py +3 -4
  27. webscout/Provider/Netwrck.py +6 -8
  28. webscout/Provider/OLLAMA.py +1 -0
  29. webscout/Provider/OPENAI/Cloudflare.py +6 -7
  30. webscout/Provider/OPENAI/FalconH1.py +2 -7
  31. webscout/Provider/OPENAI/FreeGemini.py +6 -8
  32. webscout/Provider/OPENAI/{monochat.py → K2Think.py} +180 -77
  33. webscout/Provider/OPENAI/NEMOTRON.py +3 -6
  34. webscout/Provider/OPENAI/PI.py +5 -4
  35. webscout/Provider/OPENAI/Qwen3.py +2 -3
  36. webscout/Provider/OPENAI/README.md +2 -1
  37. webscout/Provider/OPENAI/TogetherAI.py +52 -57
  38. webscout/Provider/OPENAI/TwoAI.py +3 -4
  39. webscout/Provider/OPENAI/__init__.py +17 -56
  40. webscout/Provider/OPENAI/ai4chat.py +313 -303
  41. webscout/Provider/OPENAI/base.py +9 -29
  42. webscout/Provider/OPENAI/chatgpt.py +7 -2
  43. webscout/Provider/OPENAI/chatgptclone.py +4 -7
  44. webscout/Provider/OPENAI/chatsandbox.py +84 -59
  45. webscout/Provider/OPENAI/deepinfra.py +12 -6
  46. webscout/Provider/OPENAI/e2b.py +60 -8
  47. webscout/Provider/OPENAI/flowith.py +4 -3
  48. webscout/Provider/OPENAI/generate_api_key.py +48 -0
  49. webscout/Provider/OPENAI/heckai.py +4 -1
  50. webscout/Provider/OPENAI/netwrck.py +9 -12
  51. webscout/Provider/OPENAI/refact.py +274 -0
  52. webscout/Provider/OPENAI/scirachat.py +6 -0
  53. webscout/Provider/OPENAI/textpollinations.py +3 -14
  54. webscout/Provider/OPENAI/toolbaz.py +14 -10
  55. webscout/Provider/OpenGPT.py +1 -1
  56. webscout/Provider/Openai.py +150 -402
  57. webscout/Provider/PI.py +1 -0
  58. webscout/Provider/Perplexitylabs.py +1 -2
  59. webscout/Provider/QwenLM.py +107 -89
  60. webscout/Provider/STT/__init__.py +17 -2
  61. webscout/Provider/{Llama3.py → Sambanova.py} +9 -10
  62. webscout/Provider/StandardInput.py +1 -1
  63. webscout/Provider/TTI/__init__.py +18 -12
  64. webscout/Provider/TTI/bing.py +14 -2
  65. webscout/Provider/TTI/together.py +10 -9
  66. webscout/Provider/TTS/README.md +0 -1
  67. webscout/Provider/TTS/__init__.py +18 -11
  68. webscout/Provider/TTS/base.py +479 -159
  69. webscout/Provider/TTS/deepgram.py +409 -156
  70. webscout/Provider/TTS/elevenlabs.py +425 -111
  71. webscout/Provider/TTS/freetts.py +317 -140
  72. webscout/Provider/TTS/gesserit.py +192 -128
  73. webscout/Provider/TTS/murfai.py +248 -113
  74. webscout/Provider/TTS/openai_fm.py +347 -129
  75. webscout/Provider/TTS/speechma.py +620 -586
  76. webscout/Provider/TeachAnything.py +1 -0
  77. webscout/Provider/TextPollinationsAI.py +5 -15
  78. webscout/Provider/TogetherAI.py +136 -142
  79. webscout/Provider/TwoAI.py +53 -309
  80. webscout/Provider/TypliAI.py +2 -1
  81. webscout/Provider/{GizAI.py → UNFINISHED/GizAI.py} +1 -1
  82. webscout/Provider/UNFINISHED/VercelAIGateway.py +339 -0
  83. webscout/Provider/Venice.py +2 -1
  84. webscout/Provider/VercelAI.py +1 -0
  85. webscout/Provider/WiseCat.py +2 -1
  86. webscout/Provider/WrDoChat.py +2 -1
  87. webscout/Provider/__init__.py +18 -174
  88. webscout/Provider/ai4chat.py +1 -1
  89. webscout/Provider/akashgpt.py +7 -10
  90. webscout/Provider/cerebras.py +194 -38
  91. webscout/Provider/chatglm.py +170 -83
  92. webscout/Provider/cleeai.py +1 -2
  93. webscout/Provider/deepseek_assistant.py +1 -1
  94. webscout/Provider/elmo.py +1 -1
  95. webscout/Provider/geminiapi.py +1 -1
  96. webscout/Provider/granite.py +1 -1
  97. webscout/Provider/hermes.py +1 -3
  98. webscout/Provider/julius.py +1 -0
  99. webscout/Provider/learnfastai.py +1 -1
  100. webscout/Provider/llama3mitril.py +1 -1
  101. webscout/Provider/llmchat.py +1 -1
  102. webscout/Provider/llmchatco.py +1 -1
  103. webscout/Provider/meta.py +3 -3
  104. webscout/Provider/oivscode.py +2 -2
  105. webscout/Provider/scira_chat.py +51 -124
  106. webscout/Provider/searchchat.py +1 -0
  107. webscout/Provider/sonus.py +1 -1
  108. webscout/Provider/toolbaz.py +15 -11
  109. webscout/Provider/turboseek.py +31 -22
  110. webscout/Provider/typefully.py +2 -1
  111. webscout/Provider/x0gpt.py +1 -0
  112. webscout/Provider/yep.py +2 -1
  113. webscout/conversation.py +22 -20
  114. webscout/sanitize.py +14 -10
  115. webscout/scout/README.md +20 -23
  116. webscout/scout/core/crawler.py +125 -38
  117. webscout/scout/core/scout.py +26 -5
  118. webscout/tempid.py +6 -0
  119. webscout/version.py +1 -1
  120. webscout/webscout_search.py +13 -6
  121. webscout/webscout_search_async.py +10 -8
  122. webscout/yep_search.py +13 -5
  123. {webscout-8.3.5.dist-info → webscout-8.3.7.dist-info}/METADATA +3 -1
  124. {webscout-8.3.5.dist-info → webscout-8.3.7.dist-info}/RECORD +132 -155
  125. webscout/Provider/AllenAI.py +0 -440
  126. webscout/Provider/Blackboxai.py +0 -793
  127. webscout/Provider/FreeGemini.py +0 -250
  128. webscout/Provider/Glider.py +0 -225
  129. webscout/Provider/Hunyuan.py +0 -283
  130. webscout/Provider/MCPCore.py +0 -322
  131. webscout/Provider/MiniMax.py +0 -207
  132. webscout/Provider/OPENAI/BLACKBOXAI.py +0 -1045
  133. webscout/Provider/OPENAI/MiniMax.py +0 -298
  134. webscout/Provider/OPENAI/autoproxy.py +0 -1067
  135. webscout/Provider/OPENAI/c4ai.py +0 -394
  136. webscout/Provider/OPENAI/copilot.py +0 -305
  137. webscout/Provider/OPENAI/glider.py +0 -330
  138. webscout/Provider/OPENAI/mcpcore.py +0 -431
  139. webscout/Provider/OPENAI/multichat.py +0 -378
  140. webscout/Provider/Reka.py +0 -214
  141. webscout/Provider/TTS/sthir.py +0 -94
  142. webscout/Provider/UNFINISHED/fetch_together_models.py +0 -90
  143. webscout/Provider/asksteve.py +0 -220
  144. webscout/Provider/copilot.py +0 -422
  145. webscout/Provider/freeaichat.py +0 -294
  146. webscout/Provider/koala.py +0 -182
  147. webscout/Provider/lmarena.py +0 -198
  148. webscout/Provider/monochat.py +0 -275
  149. webscout/Provider/multichat.py +0 -375
  150. webscout/Provider/scnet.py +0 -244
  151. webscout/Provider/talkai.py +0 -194
  152. /webscout/Provider/{Marcus.py → UNFINISHED/Marcus.py} +0 -0
  153. /webscout/Provider/{Qodo.py → UNFINISHED/Qodo.py} +0 -0
  154. /webscout/Provider/{XenAI.py → UNFINISHED/XenAI.py} +0 -0
  155. /webscout/Provider/{samurai.py → UNFINISHED/samurai.py} +0 -0
  156. {webscout-8.3.5.dist-info → webscout-8.3.7.dist-info}/WHEEL +0 -0
  157. {webscout-8.3.5.dist-info → webscout-8.3.7.dist-info}/entry_points.txt +0 -0
  158. {webscout-8.3.5.dist-info → webscout-8.3.7.dist-info}/licenses/LICENSE.md +0 -0
  159. {webscout-8.3.5.dist-info → webscout-8.3.7.dist-info}/top_level.txt +0 -0
@@ -1,793 +0,0 @@
1
- import requests
2
- import random
3
- import string
4
- import base64
5
- from datetime import datetime, timedelta
6
- from typing import Any, Dict, Union, Generator, List
7
- from webscout.AIutel import Optimizers, Conversation, AwesomePrompts
8
- from webscout.AIbase import Provider
9
- from webscout import exceptions
10
- from webscout.litagent import LitAgent
11
- def to_data_uri(image_data):
12
- """Convert image data to a data URI format"""
13
- if isinstance(image_data, str):
14
- # Assume it's already a data URI
15
- return image_data
16
-
17
- # Encode binary data to base64
18
- encoded = base64.b64encode(image_data).decode('utf-8')
19
-
20
- # Determine MIME type (simplified)
21
- mime_type = "image/jpeg" # Default
22
- if image_data.startswith(b'\x89PNG'):
23
- mime_type = "image/png"
24
- elif image_data.startswith(b'\xff\xd8'):
25
- mime_type = "image/jpeg"
26
- elif image_data.startswith(b'GIF'):
27
- mime_type = "image/gif"
28
-
29
- return f"data:{mime_type};base64,{encoded}"
30
-
31
-
32
- class BLACKBOXAI(Provider):
33
- """
34
- BlackboxAI provider for interacting with the Blackbox API.
35
- Supports synchronous operations with multiple models.
36
- """
37
- url = "https://www.blackbox.ai"
38
- api_endpoint = "https://www.blackbox.ai/api/chat"
39
-
40
-
41
- # Default model (remains the same as per original class)
42
- default_model = "GPT-4.1"
43
- default_vision_model = default_model
44
-
45
- # New OpenRouter models list
46
- openrouter_models = [
47
- "Deepcoder 14B Preview",
48
- "DeepHermes 3 Llama 3 8B Preview",
49
- "DeepSeek R1 Zero",
50
- "Dolphin3.0 Mistral 24B",
51
- "Dolphin3.0 R1 Mistral 24B",
52
- "Flash 3",
53
- "Gemini 2.0 Flash Experimental",
54
- "Gemma 2 9B",
55
- "Gemma 3 12B",
56
- "Gemma 3 1B",
57
- "Gemma 3 27B",
58
- "Gemma 3 4B",
59
- "Kimi VL A3B Thinking",
60
- "Llama 3.1 8B Instruct",
61
- "Llama 3.1 Nemotron Ultra 253B v1",
62
- "Llama 3.2 11B Vision Instruct",
63
- "Llama 3.2 1B Instruct",
64
- "Llama 3.2 3B Instruct",
65
- "Llama 3.3 70B Instruct",
66
- "Llama 3.3 Nemotron Super 49B v1",
67
- "Llama 4 Maverick",
68
- "Llama 4 Scout",
69
- "Mistral 7B Instruct",
70
- "Mistral Nemo",
71
- "Mistral Small 3",
72
- "Mistral Small 3.1 24B",
73
- "Molmo 7B D",
74
- "Moonlight 16B A3B Instruct",
75
- "Qwen2.5 72B Instruct",
76
- "Qwen2.5 7B Instruct",
77
- "Qwen2.5 Coder 32B Instruct",
78
- "Qwen2.5 VL 32B Instruct",
79
- "Qwen2.5 VL 3B Instruct",
80
- "Qwen2.5 VL 72B Instruct",
81
- "Qwen2.5-VL 7B Instruct",
82
- "Qwerky 72B",
83
- "QwQ 32B",
84
- "QwQ 32B Preview",
85
- "QwQ 32B RpR v1",
86
- "R1",
87
- "R1 Distill Llama 70B",
88
- "R1 Distill Qwen 14B",
89
- "R1 Distill Qwen 32B",
90
- ]
91
-
92
- # New base models list
93
- models = [
94
- default_model,
95
- "gpt-4.1-mini", # Added new model
96
- "o3-mini",
97
- "gpt-4.1-nano",
98
- "Claude Opus 4", # Added Claude Opus 4
99
- "Claude Sonnet 4", # Added Claude Sonnet 4
100
- "Claude-sonnet-3.7",
101
- "Claude-sonnet-3.5",
102
- "Grok 3", # Added Grok 3
103
- "Gemini 2.5 Pro", # Added Gemini 2.5 Pro
104
- "UI-TARS 72B", # Added UI-TARS 72B
105
- "DeepSeek-R1",
106
- "Mistral-Small-24B-Instruct-2501",
107
- *openrouter_models,
108
- # Trending agent modes (names)
109
- 'Python Agent', 'HTML Agent', 'Builder Agent', 'Java Agent', 'JavaScript Agent',
110
- 'React Agent', 'Android Agent', 'Flutter Agent', 'Next.js Agent', 'AngularJS Agent',
111
- 'Swift Agent', 'MongoDB Agent', 'PyTorch Agent', 'Xcode Agent', 'Azure Agent',
112
- 'Bitbucket Agent', 'DigitalOcean Agent', 'Docker Agent', 'Electron Agent',
113
- 'Erlang Agent', 'FastAPI Agent', 'Firebase Agent', 'Flask Agent', 'Git Agent',
114
- 'Gitlab Agent', 'Go Agent', 'Godot Agent', 'Google Cloud Agent', 'Heroku Agent'
115
- ]
116
-
117
- # Models that support vision capabilities
118
- vision_models = [default_vision_model, 'o3-mini', "Llama 3.2 11B Vision Instruct", "Gemini 2.5 Pro", "Claude Sonnet 4", "Claude Opus 4", "UI-TARS 72B"] # Added Llama vision, Gemini 2.5 Pro, Claude Sonnet 4, Claude Opus 4, and UI-TARS 72B
119
-
120
- # Models that can be directly selected by users
121
- userSelectedModel = ['o3-mini', 'Claude Opus 4', 'Claude Sonnet 4', 'Claude-sonnet-3.7', 'Claude-sonnet-3.5', 'Grok 3', 'Gemini 2.5 Pro', 'UI-TARS 72B', 'DeepSeek-R1', 'Mistral-Small-24B-Instruct-2501'] + openrouter_models
122
-
123
- # Agent mode configurations
124
- agentMode = {
125
- # OpenRouter Free
126
- 'Deepcoder 14B Preview': {'mode': True, 'id': "agentica-org/deepcoder-14b-preview:free", 'name': "Deepcoder 14B Preview"},
127
- 'DeepHermes 3 Llama 3 8B Preview': {'mode': True, 'id': "nousresearch/deephermes-3-llama-3-8b-preview:free", 'name': "DeepHermes 3 Llama 3 8B Preview"},
128
- 'DeepSeek R1 Zero': {'mode': True, 'id': "deepseek/deepseek-r1-zero:free", 'name': "DeepSeek R1 Zero"},
129
- 'Dolphin3.0 Mistral 24B': {'mode': True, 'id': "cognitivecomputations/dolphin3.0-mistral-24b:free", 'name': "Dolphin3.0 Mistral 24B"},
130
- 'Dolphin3.0 R1 Mistral 24B': {'mode': True, 'id': "cognitivecomputations/dolphin3.0-r1-mistral-24b:free", 'name': "Dolphin3.0 R1 Mistral 24B"},
131
- 'Flash 3': {'mode': True, 'id': "rekaai/reka-flash-3:free", 'name': "Flash 3"},
132
- 'Gemini 2.0 Flash Experimental': {'mode': True, 'id': "google/gemini-2.0-flash-exp:free", 'name': "Gemini 2.0 Flash Experimental"},
133
- 'Gemma 2 9B': {'mode': True, 'id': "google/gemma-2-9b-it:free", 'name': "Gemma 2 9B"},
134
- 'Gemma 3 12B': {'mode': True, 'id': "google/gemma-3-12b-it:free", 'name': "Gemma 3 12B"},
135
- 'Gemma 3 1B': {'mode': True, 'id': "google/gemma-3-1b-it:free", 'name': "Gemma 3 1B"},
136
- 'Gemma 3 27B': {'mode': True, 'id': "google/gemma-3-27b-it:free", 'name': "Gemma 3 27B"},
137
- 'Gemma 3 4B': {'mode': True, 'id': "google/gemma-3-4b-it:free", 'name': "Gemma 3 4B"},
138
- 'Kimi VL A3B Thinking': {'mode': True, 'id': "moonshotai/kimi-vl-a3b-thinking:free", 'name': "Kimi VL A3B Thinking"},
139
- 'Llama 3.1 8B Instruct': {'mode': True, 'id': "meta-llama/llama-3.1-8b-instruct:free", 'name': "Llama 3.1 8B Instruct"},
140
- 'Llama 3.1 Nemotron Ultra 253B v1': {'mode': True, 'id': "nvidia/llama-3.1-nemotron-ultra-253b-v1:free", 'name': "Llama 3.1 Nemotron Ultra 253B v1"},
141
- 'Llama 3.2 11B Vision Instruct': {'mode': True, 'id': "meta-llama/llama-3.2-11b-vision-instruct:free", 'name': "Llama 3.2 11B Vision Instruct"},
142
- 'Llama 3.2 1B Instruct': {'mode': True, 'id': "meta-llama/llama-3.2-1b-instruct:free", 'name': "Llama 3.2 1B Instruct"},
143
- 'Llama 3.2 3B Instruct': {'mode': True, 'id': "meta-llama/llama-3.2-3b-instruct:free", 'name': "Llama 3.2 3B Instruct"},
144
- 'Llama 3.3 70B Instruct': {'mode': True, 'id': "meta-llama/llama-3.3-70b-instruct:free", 'name': "Llama 3.3 70B Instruct"},
145
- 'Llama 3.3 Nemotron Super 49B v1': {'mode': True, 'id': "nvidia/llama-3.3-nemotron-super-49b-v1:free", 'name': "Llama 3.3 Nemotron Super 49B v1"},
146
- 'Llama 4 Maverick': {'mode': True, 'id': "meta-llama/llama-4-maverick:free", 'name': "Llama 4 Maverick"},
147
- 'Llama 4 Scout': {'mode': True, 'id': "meta-llama/llama-4-scout:free", 'name': "Llama 4 Scout"},
148
- 'Mistral 7B Instruct': {'mode': True, 'id': "mistralai/mistral-7b-instruct:free", 'name': "Mistral 7B Instruct"},
149
- 'Mistral Nemo': {'mode': True, 'id': "mistralai/mistral-nemo:free", 'name': "Mistral Nemo"},
150
- 'Mistral Small 3': {'mode': True, 'id': "mistralai/mistral-small-24b-instruct-2501:free", 'name': "Mistral Small 3"}, # Matches Mistral-Small-24B-Instruct-2501
151
- 'Mistral Small 3.1 24B': {'mode': True, 'id': "mistralai/mistral-small-3.1-24b-instruct:free", 'name': "Mistral Small 3.1 24B"},
152
- 'Molmo 7B D': {'mode': True, 'id': "allenai/molmo-7b-d:free", 'name': "Molmo 7B D"},
153
- 'Moonlight 16B A3B Instruct': {'mode': True, 'id': "moonshotai/moonlight-16b-a3b-instruct:free", 'name': "Moonlight 16B A3B Instruct"},
154
- 'Qwen2.5 72B Instruct': {'mode': True, 'id': "qwen/qwen-2.5-72b-instruct:free", 'name': "Qwen2.5 72B Instruct"},
155
- 'Qwen2.5 7B Instruct': {'mode': True, 'id': "qwen/qwen-2.5-7b-instruct:free", 'name': "Qwen2.5 7B Instruct"},
156
- 'Qwen2.5 Coder 32B Instruct': {'mode': True, 'id': "qwen/qwen-2.5-coder-32b-instruct:free", 'name': "Qwen2.5 Coder 32B Instruct"},
157
- 'Qwen2.5 VL 32B Instruct': {'mode': True, 'id': "qwen/qwen2.5-vl-32b-instruct:free", 'name': "Qwen2.5 VL 32B Instruct"},
158
- 'Qwen2.5 VL 3B Instruct': {'mode': True, 'id': "qwen/qwen2.5-vl-3b-instruct:free", 'name': "Qwen2.5 VL 3B Instruct"},
159
- 'Qwen2.5 VL 72B Instruct': {'mode': True, 'id': "qwen/qwen2.5-vl-72b-instruct:free", 'name': "Qwen2.5 VL 72B Instruct"},
160
- 'Qwen2.5-VL 7B Instruct': {'mode': True, 'id': "qwen/qwen-2.5-vl-7b-instruct:free", 'name': "Qwen2.5-VL 7B Instruct"},
161
- 'Qwerky 72B': {'mode': True, 'id': "featherless/qwerky-72b:free", 'name': "Qwerky 72B"},
162
- 'QwQ 32B': {'mode': True, 'id': "qwen/qwq-32b:free", 'name': "QwQ 32B"},
163
- 'QwQ 32B Preview': {'mode': True, 'id': "qwen/qwq-32b-preview:free", 'name': "QwQ 32B Preview"},
164
- 'QwQ 32B RpR v1': {'mode': True, 'id': "arliai/qwq-32b-arliai-rpr-v1:free", 'name': "QwQ 32B RpR v1"},
165
- 'R1': {'mode': True, 'id': "deepseek/deepseek-r1:free", 'name': "R1"}, # Matches DeepSeek-R1
166
- 'R1 Distill Llama 70B': {'mode': True, 'id': "deepseek/deepseek-r1-distill-llama-70b:free", 'name': "R1 Distill Llama 70B"},
167
- 'R1 Distill Qwen 14B': {'mode': True, 'id': "deepseek/deepseek-r1-distill-qwen-14b:free", 'name': "R1 Distill Qwen 14B"},
168
- 'R1 Distill Qwen 32B': {'mode': True, 'id': "deepseek/deepseek-r1-distill-qwen-32b:free", 'name': "R1 Distill Qwen 32B"},
169
- # Default models from the new list
170
- 'Claude Opus 4': {'mode': True, 'id': "anthropic/claude-opus-4", 'name': "Claude Opus 4"},
171
- 'Claude Sonnet 4': {'mode': True, 'id': "anthropic/claude-sonnet-4", 'name': "Claude Sonnet 4"},
172
- 'Claude-sonnet-3.7': {'mode': True, 'id': "Claude-sonnet-3.7", 'name': "Claude-sonnet-3.7"},
173
- 'Claude-sonnet-3.5': {'mode': True, 'id': "Claude-sonnet-3.5", 'name': "Claude-sonnet-3.5"},
174
- 'Grok 3': {'mode': True, 'id': "x-ai/grok-3-beta", 'name': "Grok 3"},
175
- 'Gemini 2.5 Pro': {'mode': True, 'id': "google/gemini-2.5-pro-preview-03-25", 'name': "Gemini 2.5 Pro"},
176
- 'UI-TARS 72B': {'mode': True, 'id': "bytedance-research/ui-tars-72b:free", 'name': "UI-TARS 72B"},
177
- 'DeepSeek-R1': {'mode': True, 'id': "deepseek-reasoner", 'name': "DeepSeek-R1"}, # This is 'R1' in openrouter, but 'DeepSeek-R1' in base models
178
- 'Mistral-Small-24B-Instruct-2501': {'mode': True, 'id': "mistralai/Mistral-Small-24B-Instruct-2501", 'name': "Mistral-Small-24B-Instruct-2501"},
179
- # Add default_model if it's not covered and has an agent mode
180
- default_model: {'mode': True, 'id': "openai/gpt-4.1", 'name': default_model}, # Assuming GPT-4.1 is agent-compatible
181
- 'o3-mini': {'mode': True, 'id': "o3-mini", 'name': "o3-mini"}, # Assuming o3-mini is agent-compatible
182
- 'gpt-4.1-nano': {'mode': True, 'id': "gpt-4.1-nano", 'name': "gpt-4.1-nano"}, # Assuming gpt-4.1-nano is agent-compatible
183
- 'gpt-4.1-mini': {'mode': True, 'id': "gpt-4.1-mini", 'name': "gpt-4.1-mini"}, # Added agent mode for gpt-4.1-mini
184
- }
185
-
186
- # Trending agent modes
187
- trendingAgentMode = {
188
- 'Python Agent': {'mode': True, 'id': "python"},
189
- 'HTML Agent': {'mode': True, 'id': "html"},
190
- 'Builder Agent': {'mode': True, 'id': "builder"},
191
- 'Java Agent': {'mode': True, 'id': "java"},
192
- 'JavaScript Agent': {'mode': True, 'id': "javascript"},
193
- 'React Agent': {'mode': True, 'id': "react"},
194
- 'Android Agent': {'mode': True, 'id': "android"},
195
- 'Flutter Agent': {'mode': True, 'id': "flutter"},
196
- 'Next.js Agent': {'mode': True, 'id': "next.js"},
197
- 'AngularJS Agent': {'mode': True, 'id': "angularjs"},
198
- 'Swift Agent': {'mode': True, 'id': "swift"},
199
- 'MongoDB Agent': {'mode': True, 'id': "mongodb"},
200
- 'PyTorch Agent': {'mode': True, 'id': "pytorch"},
201
- 'Xcode Agent': {'mode': True, 'id': "xcode"},
202
- 'Azure Agent': {'mode': True, 'id': "azure"},
203
- 'Bitbucket Agent': {'mode': True, 'id': "bitbucket"},
204
- 'DigitalOcean Agent': {'mode': True, 'id': "digitalocean"},
205
- 'Docker Agent': {'mode': True, 'id': "docker"},
206
- 'Electron Agent': {'mode': True, 'id': "electron"},
207
- 'Erlang Agent': {'mode': True, 'id': "erlang"},
208
- 'FastAPI Agent': {'mode': True, 'id': "fastapi"},
209
- 'Firebase Agent': {'mode': True, 'id': "firebase"},
210
- 'Flask Agent': {'mode': True, 'id': "flask"},
211
- 'Git Agent': {'mode': True, 'id': "git"},
212
- 'Gitlab Agent': {'mode': True, 'id': "gitlab"},
213
- 'Go Agent': {'mode': True, 'id': "go"},
214
- 'Godot Agent': {'mode': True, 'id': "godot"},
215
- 'Google Cloud Agent': {'mode': True, 'id': "googlecloud"},
216
- 'Heroku Agent': {'mode': True, 'id': "heroku"},
217
- }
218
-
219
- # Complete list of all models (for authorized users) - used for AVAILABLE_MODELS
220
- _all_models = list(dict.fromkeys([
221
- *models, # Includes default_model, o3-mini, etc., and openrouter_models and agent names
222
- *list(agentMode.keys()), # Ensure all agentMode keys are included
223
- *list(trendingAgentMode.keys()) # Ensure all trendingAgentMode keys are included
224
- ]))
225
-
226
- AVAILABLE_MODELS = {name: name for name in _all_models}
227
- # Update AVAILABLE_MODELS to use names from agentMode if available
228
- for model_name_key in agentMode:
229
- if model_name_key in AVAILABLE_MODELS: # Check if the key from agentMode is in _all_models
230
- AVAILABLE_MODELS[model_name_key] = agentMode[model_name_key].get('name', model_name_key)
231
-
232
-
233
- # Model aliases for easier reference
234
- model_aliases = {
235
- "gpt-4": default_model, # default_model is "GPT-4.1"
236
- "gpt-4.1": default_model,
237
- "gpt-4o": default_model, # Defaulting to GPT-4.1 as per previous logic if specific GPT-4o handling isn't defined elsewhere
238
- "gpt-4o-mini": default_model, # Defaulting
239
- "claude-opus-4": "Claude Opus 4",
240
- "claude-4-opus": "Claude Opus 4",
241
- "claude-sonnet-4": "Claude Sonnet 4",
242
- "claude-4-sonnet": "Claude Sonnet 4",
243
- "claude-3.7-sonnet": "Claude-sonnet-3.7",
244
- "claude-3.5-sonnet": "Claude-sonnet-3.5",
245
- "grok-3": "Grok 3",
246
- "grok3": "Grok 3",
247
- "gemini-2.5-pro": "Gemini 2.5 Pro",
248
- "gemini-2.5": "Gemini 2.5 Pro",
249
- "ui-tars-72b": "UI-TARS 72B",
250
- "ui-tars": "UI-TARS 72B",
251
- # "deepseek-r1": "DeepSeek-R1", # This is in base models, maps to R1 or DeepSeek R1 Zero in agentMode
252
- #
253
- "deepcoder-14b": "Deepcoder 14B Preview",
254
- "deephermes-3-8b": "DeepHermes 3 Llama 3 8B Preview",
255
- "deepseek-r1-zero": "DeepSeek R1 Zero",
256
- "deepseek-r1": "R1", # Alias for R1 (which is deepseek/deepseek-r1:free)
257
- "dolphin-3.0-24b": "Dolphin3.0 Mistral 24B",
258
- "dolphin-3.0-r1-24b": "Dolphin3.0 R1 Mistral 24B",
259
- "reka-flash": "Flash 3",
260
- "gemini-2.0-flash": "Gemini 2.0 Flash Experimental",
261
- "gemma-2-9b": "Gemma 2 9B",
262
- "gemma-3-12b": "Gemma 3 12B",
263
- "gemma-3-1b": "Gemma 3 1B",
264
- "gemma-3-27b": "Gemma 3 27B",
265
- "gemma-3-4b": "Gemma 3 4B",
266
- "kimi-vl-a3b-thinking": "Kimi VL A3B Thinking",
267
- "llama-3.1-8b": "Llama 3.1 8B Instruct",
268
- "nemotron-253b": "Llama 3.1 Nemotron Ultra 253B v1",
269
- "llama-3.2-11b": "Llama 3.2 11B Vision Instruct",
270
- "llama-3.2-1b": "Llama 3.2 1B Instruct",
271
- "llama-3.2-3b": "Llama 3.2 3B Instruct",
272
- "llama-3.3-70b": "Llama 3.3 70B Instruct",
273
- "nemotron-49b": "Llama 3.3 Nemotron Super 49B v1",
274
- "llama-4-maverick": "Llama 4 Maverick",
275
- "llama-4-scout": "Llama 4 Scout",
276
- "mistral-7b": "Mistral 7B Instruct",
277
- "mistral-nemo": "Mistral Nemo",
278
- "mistral-small-24b": "Mistral Small 3", # Alias for "Mistral Small 3"
279
- "mistral-small-24b-instruct-2501": "Mistral-Small-24B-Instruct-2501", # Specific name
280
- "mistral-small-3.1-24b": "Mistral Small 3.1 24B",
281
- "molmo-7b": "Molmo 7B D",
282
- "moonlight-16b": "Moonlight 16B A3B Instruct",
283
- "qwen-2.5-72b": "Qwen2.5 72B Instruct",
284
- "qwen-2.5-7b": "Qwen2.5 7B Instruct",
285
- "qwen-2.5-coder-32b": "Qwen2.5 Coder 32B Instruct",
286
- "qwen-2.5-vl-32b": "Qwen2.5 VL 32B Instruct",
287
- "qwen-2.5-vl-3b": "Qwen2.5 VL 3B Instruct",
288
- "qwen-2.5-vl-72b": "Qwen2.5 VL 72B Instruct",
289
- "qwen-2.5-vl-7b": "Qwen2.5-VL 7B Instruct",
290
- "qwerky-72b": "Qwerky 72B",
291
- "qwq-32b": "QwQ 32B",
292
- "qwq-32b-preview": "QwQ 32B Preview",
293
- "qwq-32b-arliai": "QwQ 32B RpR v1",
294
- "deepseek-r1-distill-llama-70b": "R1 Distill Llama 70B",
295
- "deepseek-r1-distill-qwen-14b": "R1 Distill Qwen 14B",
296
- "deepseek-r1-distill-qwen-32b": "R1 Distill Qwen 32B",
297
- }
298
-
299
- def __init__(
300
- self,
301
- is_conversation: bool = True,
302
- max_tokens: int = 8000,
303
- timeout: int = 30,
304
- intro: str = None,
305
- filepath: str = None,
306
- update_file: bool = True,
307
- proxies: dict = {},
308
- history_offset: int = 10250,
309
- act: str = None,
310
- model: str = "gpt-4.1",
311
- system_message: str = "You are a helpful AI assistant."
312
- ):
313
- """Initialize BlackboxAI with enhanced configuration options."""
314
- self.session = requests.Session()
315
- self.max_tokens_to_sample = max_tokens
316
- self.is_conversation = is_conversation
317
- self.timeout = timeout
318
- self.last_response = {}
319
- self.model = self.get_model(model)
320
- self.system_message = system_message
321
-
322
- self.headers = {
323
- "Content-Type": "application/json",
324
- "Accept": "*/*",
325
- }
326
- self.cookies = {
327
- 'cfzs_amplitude': self.generate_id(32),
328
- 'cfz_amplitude': self.generate_id(32),
329
- '__cf_bm': self.generate_id(32),
330
- }
331
-
332
- self.__available_optimizers = [
333
- method for method in dir(Optimizers)
334
- if callable(getattr(Optimizers, method)) and not method.startswith("__")
335
- ]
336
-
337
- Conversation.intro = (
338
- AwesomePrompts().get_act(
339
- act, raise_not_found=True, default=None, case_insensitive=True
340
- )
341
- if act
342
- else intro or Conversation.intro
343
- )
344
-
345
- self.conversation = Conversation(
346
- is_conversation, self.max_tokens_to_sample, filepath, update_file
347
- )
348
- self.conversation.history_offset = history_offset
349
- self.session.proxies = proxies
350
-
351
- @classmethod
352
- def get_model(cls, model: str) -> str:
353
- """Resolve model name from alias"""
354
- # Convert to lowercase for case-insensitive matching
355
- model_lower = model.lower()
356
-
357
- # Check aliases (case-insensitive)
358
- for alias, target in cls.model_aliases.items():
359
- if model_lower == alias.lower():
360
- model = target
361
- break
362
-
363
- # Check available models (case-insensitive)
364
- for available_model, target in cls.AVAILABLE_MODELS.items():
365
- if model_lower == available_model.lower() or model == target:
366
- return target
367
-
368
- # If we get here, the model wasn't found
369
- raise ValueError(f"Unknown model: {model}. Available models: {', '.join(cls.AVAILABLE_MODELS)}")
370
-
371
- @classmethod
372
- def generate_session(cls, email: str = None, id_length: int = 21, days_ahead: int = 30) -> dict:
373
- """
374
- Generate a dynamic session with proper ID and expiry format using a specific email.
375
- Uses a large hardcoded list of names and domains for diversity.
376
-
377
- Args:
378
- email: The email to use for this session (optional, will be generated if not provided)
379
- id_length: Length of the numeric ID (default: 21)
380
- days_ahead: Number of days ahead for expiry (default: 30)
381
-
382
- Returns:
383
- dict: A session dictionary with user information and expiry
384
- """
385
- # Large list of first and last names
386
- first_names = [
387
- "Alex", "Jordan", "Taylor", "Morgan", "Casey", "Riley", "Avery", "Quinn", "Skyler", "Dakota",
388
- "Jamie", "Cameron", "Drew", "Harper", "Peyton", "Reese", "Rowan", "Sawyer", "Shawn", "Terry",
389
- "Robin", "Kendall", "Finley", "Blake", "Charlie", "Emerson", "Hayden", "Jesse", "Kai", "Lane",
390
- "Logan", "Marley", "Micah", "Parker", "Phoenix", "Remy", "Rory", "Sage", "Shiloh", "Spencer",
391
- "Sydney", "Tatum", "Teagan", "Tristan", "Val", "Winter", "Zion", "Bailey", "Brett", "Case",
392
- "Corey", "Devon", "Eden", "Ellis", "Frankie", "Gray", "Indigo", "Jaden", "Jules", "Justice",
393
- "Kieran", "Lake", "Lennon", "Linden", "Luca", "Milan", "Monroe", "Oakley", "Perry", "Quincy",
394
- "Reagan", "Reed", "Rene", "River", "Robin", "Sasha", "Shane", "Shawn", "Sky", "Sterling",
395
- "Storm", "Toby", "Vesper", "Wren", "Zane", "Zuri", "Ainsley", "Arden", "Aspen", "Blaine", "Briar",
396
- "Campbell", "Cleo", "Cruz", "Dallas", "Darby", "Denver", "Echo", "Emery", "Everest", "Hollis",
397
- "Indy", "Joss", "Karsen", "Kit", "Laken", "Linden", "Lyle", "Marlow", "Merritt", "Nico", "Onyx",
398
- "Pax", "Peyton", "Quill", "Raleigh", "Reeve", "Ridley", "Rio", "Rylan", "Sailor", "Scout", "Shia",
399
- "Sonny", "Story", "Tanner", "Tate", "Tegan", "Tiernan", "True", "Vaughn", "Wynn", "Zephyr",
400
- # Add more names as needed for diversity
401
- ]
402
- last_names = [
403
- "Smith", "Johnson", "Williams", "Brown", "Jones", "Miller", "Davis", "Garcia", "Rodriguez", "Wilson",
404
- "Martinez", "Anderson", "Taylor", "Thomas", "Hernandez", "Moore", "Martin", "Jackson", "Thompson", "White",
405
- "Lopez", "Lee", "Gonzalez", "Harris", "Clark", "Lewis", "Robinson", "Walker", "Perez", "Hall",
406
- "Young", "Allen", "Sanchez", "Wright", "King", "Scott", "Green", "Baker", "AdAMS", "Nelson",
407
- "Carter", "Mitchell", "Perez", "Roberts", "Turner", "Phillips", "Campbell", "Parker", "Evans", "Edwards",
408
- "Collins", "Stewart", "Sanchez", "Morris", "Rogers", "Reed", "Cook", "Morgan", "Bell", "Murphy",
409
- "Bailey", "Rivera", "Cooper", "Richardson", "Cox", "Howard", "Ward", "Torres", "Peterson", "Gray",
410
- "Ramirez", "James", "Watson", "Brooks", "Kelly", "Sanders", "Price", "Bennett", "Wood", "Barnes",
411
- "Ross", "Henderson", "Coleman", "Jenkins", "Perry", "Powell", "Long", "Patterson", "Hughes", "Flores",
412
- "Washington", "Butler", "Simmons", "Foster", "Gonzales", "Bryant", "Alexander", "Russell", "Griffin", "Diaz",
413
- # Add more last names as needed
414
- ]
415
- # Large list of fake domains
416
- fake_domains = [
417
- "example.com", "mailinator.com", "fakemail.com", "tempmail.net", "yopmail.com", "testmail.org", "maildrop.cc",
418
- "inboxkitten.com", "guerrillamail.com", "sharklasers.com", "mailnesia.com", "dispostable.com", "getnada.com",
419
- "10minutemail.com", "throwawaymail.com", "mailcatch.com", "spambog.com", "mintemail.com", "mail-temp.com",
420
- "fakeinbox.com", "mytrashmail.com", "trashmail.com", "mailnull.com", "spamgourmet.com", "mailhazard.com",
421
- "mailbox52.ga", "mailpoof.com", "mailtothis.com", "nowmymail.com", "mailimate.com", "mailboxy.fun",
422
- "mailbolt.net", "mailblip.com", "mailbucket.org", "mailchimp.biz", "mailclark.ai", "maildog.info",
423
- "maildrop.cc", "maildu.de", "maileater.com", "mailexpire.com", "mailforspam.com", "mailfreeonline.com",
424
- "mailhub24.com", "mailimate.com", "mailin8r.com", "mailinator.net", "mailismagic.com", "mailjunk.cf",
425
- "mailmate.com", "mailme24.com", "mailmoat.com", "mailnator.com", "mailnesia.com", "mailnull.com",
426
- "mailpick.biz", "mailrock.biz", "mailsac.com", "mailseal.de", "mailtemp.net", "mailtothis.com",
427
- "mailtrash.net", "mailtv.net", "mailup.net", "mailwire.net", "mailzilla.com", "meltmail.com",
428
- "moakt.com", "my10minutemail.com", "mytemp.email", "neomailbox.com", "nospamfor.us", "objectmail.com",
429
- "oneoffemail.com", "owlpic.com", "pookmail.com", "proxymail.eu", "rcpt.at", "sharklasers.com",
430
- "smellfear.com", "sogetthis.com", "spam4.me", "spamavert.com", "spambob.com", "spambog.com",
431
- "spambox.us", "spamcannon.com", "spamday.com", "spamex.com", "spamfree24.com", "spamgourmet.com",
432
- "spamhole.com", "spaminator.de", "spamkill.info", "spaml.com", "spammotel.com", "spamobox.com",
433
- "spamspot.com", "superrito.com", "teleworm.us", "temp-mail.org", "temp-mail.ru", "tempail.com",
434
- "tempe-mail.com", "tempemail.co.za", "tempinbox.com", "tempmail.eu", "tempmail.net", "tempmail.us",
435
- "tempomail.fr", "temporaryemail.net", "thankyou2010.com", "thisisnotmyrealemail.com", "throwam.com",
436
- "throwawayemailaddress.com", "trash-mail.com", "trash2009.com", "trashdevil.com", "trashemail.de",
437
- "trashmail.at", "trashmail.com", "trashmail.me", "trashmail.net", "trashymail.com", "trbvm.com",
438
- "yepmail.net", "yopmail.com", "zoemail.net"
439
- # Add more as needed
440
- ]
441
- name = f"{random.choice(first_names)} {random.choice(last_names)}"
442
- if not email:
443
- domain = random.choice(fake_domains)
444
- email = f"{name.lower().replace(' ','.')}{random.randint(1,9999)}@{domain}"
445
-
446
- # Generate numeric ID - using Google-like ID format
447
- numeric_id = ''.join(random.choice('0123456789') for _ in range(id_length))
448
-
449
- # Generate future expiry date
450
- future_date = datetime.now() + timedelta(days=days_ahead)
451
- expiry = future_date.strftime('%Y-%m-%dT%H:%M:%S.%f')[:-3] + 'Z'
452
-
453
- # Generate random image ID for the new URL format
454
- chars = string.ascii_letters + string.digits + "-"
455
- random_img_id = ''.join(random.choice(chars) for _ in range(48))
456
- image_url = f"https://lh3.googleusercontent.com/a/ACg8oc{random_img_id}=s96-c"
457
-
458
- return {
459
- "user": {
460
- "name": name,
461
- "email": email,
462
- "image": image_url,
463
- "id": numeric_id
464
- },
465
- "expires": expiry,
466
- "isNewUser": False
467
- }
468
-
469
- @classmethod
470
- def generate_id(cls, length: int = 7) -> str:
471
- """Generate a random ID of specified length"""
472
- chars = string.ascii_letters + string.digits
473
- return ''.join(random.choice(chars) for _ in range(length))
474
-
475
- def _make_request(
476
- self,
477
- messages: List[Dict[str, str]],
478
- stream: bool = False,
479
- temperature: float = None,
480
- top_p: float = None,
481
- max_tokens: int = None,
482
- media: List = None
483
- ) -> Generator[str, None, None]:
484
- """Make synchronous request to BlackboxAI API."""
485
- # Generate a chat ID for this conversation
486
- chat_id = self.generate_id()
487
-
488
- # Format messages for the API
489
- current_messages = []
490
- for i, msg in enumerate(messages):
491
- msg_id = chat_id if i == 0 and msg["role"] == "user" else self.generate_id()
492
- current_msg = {
493
- "id": msg_id,
494
- "content": msg["content"],
495
- "role": msg["role"]
496
- }
497
- current_messages.append(current_msg)
498
-
499
- # Add image data if provided
500
- if media:
501
- current_messages[-1]['data'] = {
502
- "imagesData": [
503
- {
504
- "filePath": f"/{image_name}",
505
- "contents": to_data_uri(image)
506
- } for image, image_name in media
507
- ],
508
- "fileText": "",
509
- "title": ""
510
- }
511
-
512
- # Generate a random email for the session
513
- chars = string.ascii_lowercase + string.digits
514
- random_team = ''.join(random.choice(chars) for _ in range(8))
515
- # Use a random domain from the fake_domains set for the request email
516
- fake_domains = [
517
- "example.com", "mailinator.com", "fakemail.com", "tempmail.net", "yopmail.com", "testmail.org", "maildrop.cc",
518
- "inboxkitten.com", "guerrillamail.com", "sharklasers.com", "mailnesia.com", "dispostable.com", "getnada.com",
519
- "10minutemail.com", "throwawaymail.com", "mailcatch.com", "spambog.com", "mintemail.com", "mail-temp.com",
520
- "fakeinbox.com", "mytrashmail.com", "trashmail.com", "mailnull.com", "spamgourmet.com", "mailhazard.com",
521
- "mailbox52.ga", "mailpoof.com", "mailtothis.com", "nowmymail.com", "mailimate.com", "mailboxy.fun",
522
- "mailbolt.net", "mailblip.com", "mailbucket.org", "mailchimp.biz", "mailclark.ai", "maildog.info",
523
- "maildrop.cc", "maildu.de", "maileater.com", "mailexpire.com", "mailforspam.com", "mailfreeonline.com",
524
- "mailhub24.com", "mailimate.com", "mailin8r.com", "mailinator.net", "mailismagic.com", "mailjunk.cf",
525
- "mailmate.com", "mailme24.com", "mailmoat.com", "mailnator.com", "mailnesia.com", "mailnull.com",
526
- "mailpick.biz", "mailrock.biz", "mailsac.com", "mailseal.de", "mailtemp.net", "mailtothis.com",
527
- "mailtrash.net", "mailtv.net", "mailup.net", "mailwire.net", "mailzilla.com", "meltmail.com",
528
- "moakt.com", "my10minutemail.com", "mytemp.email", "neomailbox.com", "nospamfor.us", "objectmail.com",
529
- "oneoffemail.com", "owlpic.com", "pookmail.com", "proxymail.eu", "rcpt.at", "sharklasers.com",
530
- "smellfear.com", "sogetthis.com", "spam4.me", "spamavert.com", "spambob.com", "spambog.com",
531
- "spambox.us", "spamcannon.com", "spamday.com", "spamex.com", "spamfree24.com", "spamgourmet.com",
532
- "spamhole.com", "spaminator.de", "spamkill.info", "spaml.com", "spammotel.com", "spamobox.com",
533
- "spamspot.com", "superrito.com", "teleworm.us", "temp-mail.org", "temp-mail.ru", "tempail.com",
534
- "tempe-mail.com", "tempemail.co.za", "tempinbox.com", "tempmail.eu", "tempmail.net", "tempmail.us",
535
- "tempomail.fr", "temporaryemail.net", "thankyou2010.com", "thisisnotmyrealemail.com", "throwam.com",
536
- "throwawayemailaddress.com", "trash-mail.com", "trash2009.com", "trashdevil.com", "trashemail.de",
537
- "trashmail.at", "trashmail.com", "trashmail.me", "trashmail.net", "trashymail.com", "trbvm.com",
538
- "yepmail.net", "yopmail.com", "zoemail.net"
539
- # Add more as needed
540
- ]
541
- domain = random.choice(fake_domains)
542
- request_email = f"{random_team}@{domain}"
543
-
544
- # Generate a session with the email
545
- session_data = self.generate_session(request_email)
546
-
547
- # Prepare the request data based on the working example
548
- data = {
549
- "messages": current_messages,
550
- "agentMode": self.agentMode.get(self.model, {}) if self.model in self.agentMode else {},
551
- "id": chat_id,
552
- "previewToken": None,
553
- "userId": None,
554
- "codeModelMode": True,
555
- "trendingAgentMode": {},
556
- "isMicMode": False,
557
- "userSystemPrompt": self.system_message,
558
- "maxTokens": max_tokens or self.max_tokens_to_sample,
559
- "playgroundTopP": top_p,
560
- "playgroundTemperature": temperature,
561
- "isChromeExt": False,
562
- "githubToken": "",
563
- "clickedAnswer2": False,
564
- "clickedAnswer3": False,
565
- "clickedForceWebSearch": False,
566
- "visitFromDelta": False,
567
- "isMemoryEnabled": False,
568
- "mobileClient": False,
569
- "userSelectedModel": self.model if self.model in self.userSelectedModel else None,
570
- "validated": "00f37b34-a166-4efb-bce5-1312d87f2f94", # Using a fixed validated value from the example
571
- "imageGenerationMode": False,
572
- "webSearchModePrompt": False,
573
- "deepSearchMode": False,
574
- "designerMode": False,
575
- "domains": None,
576
- "vscodeClient": False,
577
- "codeInterpreterMode": False,
578
- "customProfile": {
579
- "name": "",
580
- "occupation": "",
581
- "traits": [],
582
- "additionalInfo": "",
583
- "enableNewChats": False
584
- },
585
- "webSearchModeOption": {
586
- "autoMode": True,
587
- "webMode": False,
588
- "offlineMode": False
589
- },
590
- "session": session_data,
591
- "isPremium": True,
592
- "subscriptionCache": {
593
- "status": "PREMIUM",
594
- "customerId": "cus_" + ''.join(random.choice(string.ascii_letters + string.digits) for _ in range(14)),
595
- "expiryTimestamp": int((datetime.now() + timedelta(days=30)).timestamp()),
596
- "lastChecked": int(datetime.now().timestamp() * 1000),
597
- "isTrialSubscription": True
598
- },
599
- "beastMode": False,
600
- "reasoningMode": False,
601
- "designerMode": False,
602
- "workspaceId": ""
603
- }
604
-
605
- # Use LitAgent to generate a realistic browser fingerprint for headers
606
- agent = LitAgent()
607
- fingerprint = agent.generate_fingerprint("chrome")
608
- headers = {
609
- 'accept': fingerprint['accept'],
610
- 'accept-encoding': 'gzip, deflate, br, zstd',
611
- 'accept-language': fingerprint['accept_language'],
612
- 'content-type': 'application/json',
613
- 'origin': 'https://www.blackbox.ai',
614
- 'referer': 'https://www.blackbox.ai/',
615
- 'sec-ch-ua': fingerprint['sec_ch_ua'],
616
- 'sec-ch-ua-mobile': '?0',
617
- 'sec-ch-ua-platform': f'"{fingerprint["platform"]}"',
618
- 'sec-fetch-dest': 'empty',
619
- 'sec-fetch-mode': 'cors',
620
- 'sec-fetch-site': 'same-origin',
621
- 'user-agent': fingerprint['user_agent']
622
- }
623
-
624
- try:
625
- response = self.session.post(
626
- self.api_endpoint,
627
- json=data,
628
- headers=headers,
629
- stream=stream,
630
- timeout=self.timeout
631
- )
632
-
633
- if not response.ok:
634
- error_msg = f"API request failed: {response.status_code} - {response.text}"
635
-
636
- # Check for service suspension
637
- if response.status_code == 503 and "service has been suspended" in response.text.lower():
638
- error_msg = "BlackboxAI service has been suspended by its owner. Please try again later or use a different provider."
639
-
640
- # Check for API endpoint issues
641
- if response.status_code == 403 and "replace" in response.text.lower() and "api.blackbox.ai" in response.text:
642
- error_msg = "BlackboxAI API endpoint issue. Please check the API endpoint configuration."
643
-
644
- raise exceptions.FailedToGenerateResponseError(error_msg)
645
-
646
- if stream:
647
- buffer = ""
648
- chunk_size = 32
649
- for chunk in response.iter_content(chunk_size=chunk_size):
650
- if not chunk:
651
- continue
652
- text = chunk.decode(errors="ignore")
653
- buffer += text
654
- while len(buffer) >= chunk_size:
655
- out = buffer[:chunk_size]
656
- buffer = buffer[chunk_size:]
657
- if out.strip():
658
- yield out
659
- if buffer.strip():
660
- yield buffer
661
- else:
662
- response_text = response.text
663
- if "You have reached your request limit for the hour" in response_text:
664
- raise exceptions.RatelimitE("Rate limit exceeded")
665
- yield response_text
666
-
667
- except requests.exceptions.RequestException as e:
668
- raise exceptions.ProviderConnectionError(f"Connection error: {str(e)}")
669
-
670
- def ask(
671
- self,
672
- prompt: str,
673
- stream: bool = False,
674
- temperature: float = None,
675
- top_p: float = None,
676
- max_tokens: int = None,
677
- optimizer: str = None,
678
- conversationally: bool = False,
679
- media: List = None
680
- ) -> Union[Dict[str, str], Generator[Dict[str, str], None, None]]:
681
- """Send a prompt to BlackboxAI API and return the response."""
682
- conversation_prompt = self.conversation.gen_complete_prompt(prompt)
683
- if optimizer:
684
- if optimizer in self.__available_optimizers:
685
- conversation_prompt = getattr(Optimizers, optimizer)(
686
- conversation_prompt if conversationally else prompt
687
- )
688
- else:
689
- raise ValueError(f"Optimizer is not one of {self.__available_optimizers}")
690
-
691
- messages = [
692
- {"role": "system", "content": self.system_message},
693
- {"role": "user", "content": conversation_prompt}
694
- ]
695
-
696
- def for_stream():
697
- for text in self._make_request(
698
- messages,
699
- stream=True,
700
- temperature=temperature,
701
- top_p=top_p,
702
- max_tokens=max_tokens,
703
- media=media
704
- ):
705
- yield {"text": text}
706
-
707
- def for_non_stream():
708
- response_text = next(self._make_request(
709
- messages,
710
- stream=False,
711
- temperature=temperature,
712
- top_p=top_p,
713
- max_tokens=max_tokens,
714
- media=media
715
- ))
716
- self.last_response = {"text": response_text}
717
- return self.last_response
718
-
719
- return for_stream() if stream else for_non_stream()
720
-
721
- def chat(
722
- self,
723
- prompt: str,
724
- stream: bool = False,
725
- temperature: float = None,
726
- top_p: float = None,
727
- max_tokens: int = None,
728
- optimizer: str = None,
729
- conversationally: bool = False,
730
- media: List = None
731
- ) -> Union[str, Generator[str, None, None]]:
732
- """Generate response as string."""
733
-
734
- def for_stream():
735
- for response in self.ask(
736
- prompt,
737
- stream=True,
738
- temperature=temperature,
739
- top_p=top_p,
740
- max_tokens=max_tokens,
741
- optimizer=optimizer,
742
- conversationally=conversationally,
743
- media=media
744
- ):
745
- yield self.get_message(response)
746
-
747
- def for_non_stream():
748
- return self.get_message(
749
- self.ask(
750
- prompt,
751
- stream=False,
752
- temperature=temperature,
753
- top_p=top_p,
754
- max_tokens=max_tokens,
755
- optimizer=optimizer,
756
- conversationally=conversationally,
757
- media=media
758
- )
759
- )
760
-
761
- return for_stream() if stream else for_non_stream()
762
-
763
- def get_message(self, response: Dict[str, Any]) -> str:
764
- """Extract message from response dictionary."""
765
- assert isinstance(response, dict), "Response should be of dict data-type only"
766
- return response["text"].replace('\\n', '\n').replace('\\n\\n', '\n\n')
767
-
768
- if __name__ == "__main__":
769
- # print("-" * 80)
770
- # print(f"{'Model':<50} {'Status':<10} {'Response'}")
771
- # print("-" * 80)
772
-
773
- # for model in BLACKBOXAI.AVAILABLE_MODELS:
774
- # try:
775
- # test_ai = BLACKBOXAI(model=model, timeout=60)
776
- # response = test_ai.chat("Say 'Hello' in one word")
777
- # response_text = response
778
-
779
- # if response_text and len(response_text.strip()) > 0:
780
- # status = "✓"
781
- # # Truncate response if too long
782
- # display_text = response_text.strip()[:50] + "..." if len(response_text.strip()) > 50 else response_text.strip()
783
- # else:
784
- # status = "✗"
785
- # display_text = "Empty or invalid response"
786
- # print(f"{model:<50} {status:<10} {display_text}")
787
- # except Exception as e:
788
- # print(f"{model:<50} {'✗':<10} {str(e)}")
789
-
790
- ai = BLACKBOXAI(model="gpt-4.1", timeout=60)
791
- response = ai.chat("tell me about humans", stream=True)
792
- for line in response:
793
- print(line, end="", flush=True)