1minai-webapi 1.0.0__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.
|
@@ -0,0 +1,773 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: 1minai_webapi
|
|
3
|
+
Version: 1.0.0
|
|
4
|
+
Summary: Async Python wrapper for the 1min.ai web app
|
|
5
|
+
Project-URL: Homepage, https://github.com/cyber-wojtek/1MinAI-API
|
|
6
|
+
Project-URL: Issues, https://github.com/cyber-wojtek/1MinAI-API/issues
|
|
7
|
+
License: MIT
|
|
8
|
+
License-File: LICENSE
|
|
9
|
+
Keywords: 1min.ai,ai,async,claude,client,gemini,image-generation,llm,openai,reverse-engineered,speech-to-text,text-to-speech,unofficial,video-generation,wrapper
|
|
10
|
+
Classifier: Development Status :: 4 - Beta
|
|
11
|
+
Classifier: Framework :: AsyncIO
|
|
12
|
+
Classifier: Intended Audience :: Developers
|
|
13
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
14
|
+
Classifier: Programming Language :: Python :: 3
|
|
15
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
19
|
+
Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
|
|
20
|
+
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
21
|
+
Classifier: Typing :: Typed
|
|
22
|
+
Requires-Python: >=3.10
|
|
23
|
+
Requires-Dist: aiohttp>=3.9.0
|
|
24
|
+
Provides-Extra: dev
|
|
25
|
+
Requires-Dist: mypy>=1.10; extra == 'dev'
|
|
26
|
+
Requires-Dist: pytest-asyncio>=0.23; extra == 'dev'
|
|
27
|
+
Requires-Dist: pytest>=8.0; extra == 'dev'
|
|
28
|
+
Requires-Dist: ruff>=0.4; extra == 'dev'
|
|
29
|
+
Description-Content-Type: text/markdown
|
|
30
|
+
|
|
31
|
+
# 1MinAI-API
|
|
32
|
+
|
|
33
|
+
An unofficial **async Python client** for the [1min.AI](https://1min.ai) web interface.
|
|
34
|
+
|
|
35
|
+
> **Disclaimer:** This library reverse-engineers the 1min.AI browser API. It is not affiliated with or endorsed by 1min.AI. Use responsibly.
|
|
36
|
+
---
|
|
37
|
+
|
|
38
|
+
## Features
|
|
39
|
+
|
|
40
|
+
- **Multi-turn conversations** — stateful `ChatSession` keeps context across turns automatically
|
|
41
|
+
- **Streaming** — yield tokens in real time via Server-Sent Events
|
|
42
|
+
- **Web search grounding** — live data, toggleable per-session or per-request
|
|
43
|
+
- **30+ chat models** — GPT, Claude, Gemini, Grok, DeepSeek, Llama, Mistral, Qwen, and more
|
|
44
|
+
- **Image generation** — Flux, DALL-E, GPT-Image, Gemini, Grok, Stable Diffusion, Recraft, Leonardo, and more
|
|
45
|
+
- **Image editing** — upscale, background removal/replacement, inpainting, variations, face swap, sketch-to-image, 3D, object removal, text removal, outpainting
|
|
46
|
+
- **Text to speech** — OpenAI TTS and ElevenLabs
|
|
47
|
+
- **Speech to text** — Whisper, GPT-4o Transcribe, ElevenLabs, Google STT
|
|
48
|
+
- **Voice tools** — isolate, clone, change, and design voices; generate sound effects
|
|
49
|
+
- **Video generation** — Kling, Sora, Veo, Luma Ray, Wan, and more; text-to-video and image-to-video
|
|
50
|
+
- **Music generation** — Google Lyria, Suno, Udio, MusicGen
|
|
51
|
+
- **Code generation** — GPT Codex, Qwen3 Coder, Grok Code, DeepSeek Coder, Claude
|
|
52
|
+
- **Content tools** — grammar, paraphrase, rewrite, summarise, expand, shorten, translate, blog/email/social/ad copy, YouTube tools, document translation
|
|
53
|
+
- **Asset API** — upload local files or public URLs (images, PDFs, audio, video) for use across all endpoints
|
|
54
|
+
- **Conversation management** — create, list, fetch history, and delete server-side threads
|
|
55
|
+
- **Credit estimation** — pre-flight cost check before sending a request
|
|
56
|
+
- **Async-first** — built on `aiohttp`, zero blocking calls
|
|
57
|
+
|
|
58
|
+
---
|
|
59
|
+
|
|
60
|
+
## Related projects
|
|
61
|
+
|
|
62
|
+
### ChatAI Console
|
|
63
|
+
|
|
64
|
+
A full-featured self-hosted web UI that supports Claude, ChatWithAI.app, and 1min.AI accounts.
|
|
65
|
+
|
|
66
|
+
**Features:**
|
|
67
|
+
- Multi-account management — Claude, ChatWithAI.app, and 1min.AI accounts in one place
|
|
68
|
+
- Real-time streaming with artifact rendering
|
|
69
|
+
- File upload and canvas preview panel
|
|
70
|
+
- Google OAuth sign-in flow
|
|
71
|
+
- Credit tracking and usage history
|
|
72
|
+
- Local conversation storage with pinning
|
|
73
|
+
|
|
74
|
+
---
|
|
75
|
+
|
|
76
|
+
## Installation
|
|
77
|
+
|
|
78
|
+
Requires Python **3.10+**.
|
|
79
|
+
|
|
80
|
+
```sh
|
|
81
|
+
pip install oneminai-webapi
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
---
|
|
85
|
+
|
|
86
|
+
## Authentication
|
|
87
|
+
|
|
88
|
+
### API key
|
|
89
|
+
|
|
90
|
+
1. Sign in at [app.1min.ai](https://app.1min.ai).
|
|
91
|
+
2. Go to **Settings → API** and copy your key.
|
|
92
|
+
3. Pass it to `OneMinAIClient`.
|
|
93
|
+
|
|
94
|
+
```python
|
|
95
|
+
client = OneMinAIClient("YOUR_API_KEY")
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
Store it in an environment variable rather than hardcoding it:
|
|
99
|
+
|
|
100
|
+
```python
|
|
101
|
+
import os
|
|
102
|
+
client = OneMinAIClient(os.environ["ONEMINAI_API_KEY"])
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
> Keep your key secret — it grants full access to your 1min.AI account and credits.
|
|
106
|
+
|
|
107
|
+
### OAuth (Google access token)
|
|
108
|
+
|
|
109
|
+
If you already have a Google OAuth2 access token (`ya29.…`) — for example obtained via a browser extension — pass it directly:
|
|
110
|
+
|
|
111
|
+
```python
|
|
112
|
+
client = OneMinAIClient()
|
|
113
|
+
user = await client.oauth_login("ya29.a0AQvPy…")
|
|
114
|
+
# all subsequent calls are authenticated automatically
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
The JWT returned by 1min.AI is stored internally. No API key is needed when using this flow.
|
|
118
|
+
|
|
119
|
+
---
|
|
120
|
+
|
|
121
|
+
## Quick start
|
|
122
|
+
|
|
123
|
+
```python
|
|
124
|
+
import asyncio
|
|
125
|
+
from oneminai_webapi import OneMinAIClient
|
|
126
|
+
|
|
127
|
+
async def main():
|
|
128
|
+
async with OneMinAIClient("YOUR_API_KEY") as client:
|
|
129
|
+
r = await client.generate_content("What is the capital of Poland?")
|
|
130
|
+
print(r.text) # "Warsaw"
|
|
131
|
+
|
|
132
|
+
asyncio.run(main())
|
|
133
|
+
```
|
|
134
|
+
|
|
135
|
+
The `async with` block closes the underlying HTTP session automatically. For manual lifecycle management:
|
|
136
|
+
|
|
137
|
+
```python
|
|
138
|
+
client = OneMinAIClient("YOUR_API_KEY")
|
|
139
|
+
try:
|
|
140
|
+
r = await client.generate_content("Hello!")
|
|
141
|
+
print(r.text)
|
|
142
|
+
finally:
|
|
143
|
+
await client.close()
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
---
|
|
147
|
+
|
|
148
|
+
## Usage
|
|
149
|
+
|
|
150
|
+
### Single-turn generation
|
|
151
|
+
|
|
152
|
+
```python
|
|
153
|
+
r = await client.generate_content("Translate 'hello' to Japanese.")
|
|
154
|
+
print(r.text) # "こんにちは"
|
|
155
|
+
print(r.model) # "gpt-4.1-nano"
|
|
156
|
+
print(str(r)) # same as r.text
|
|
157
|
+
```
|
|
158
|
+
|
|
159
|
+
Attach images or documents:
|
|
160
|
+
|
|
161
|
+
```python
|
|
162
|
+
asset = await client.upload_asset("chart.png")
|
|
163
|
+
r = await client.generate_content(
|
|
164
|
+
"Describe what you see in this chart.",
|
|
165
|
+
images=[asset.asset_key],
|
|
166
|
+
)
|
|
167
|
+
|
|
168
|
+
doc = await client.upload_asset("report.pdf")
|
|
169
|
+
r2 = await client.generate_content(
|
|
170
|
+
"Summarise this document.",
|
|
171
|
+
files=[doc.file_id],
|
|
172
|
+
)
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
---
|
|
176
|
+
|
|
177
|
+
### Streaming
|
|
178
|
+
|
|
179
|
+
```python
|
|
180
|
+
async for chunk in client.generate_content_stream("Write me a haiku."):
|
|
181
|
+
print(chunk.text_delta, end="", flush=True)
|
|
182
|
+
print()
|
|
183
|
+
```
|
|
184
|
+
|
|
185
|
+
---
|
|
186
|
+
|
|
187
|
+
### Multi-turn chat
|
|
188
|
+
|
|
189
|
+
`start_chat()` returns a `ChatSession` that tracks context automatically:
|
|
190
|
+
|
|
191
|
+
```python
|
|
192
|
+
chat = client.start_chat()
|
|
193
|
+
|
|
194
|
+
r1 = await chat.send_message("My name is Alice.")
|
|
195
|
+
r2 = await chat.send_message("What is my name?") # → "Your name is Alice."
|
|
196
|
+
print(r2.text)
|
|
197
|
+
```
|
|
198
|
+
|
|
199
|
+
Streaming within a session:
|
|
200
|
+
|
|
201
|
+
```python
|
|
202
|
+
async for chunk in chat.send_message_stream("Write a short poem about it."):
|
|
203
|
+
print(chunk.text_delta, end="", flush=True)
|
|
204
|
+
print()
|
|
205
|
+
|
|
206
|
+
# Context persists across streaming and non-streaming turns
|
|
207
|
+
r3 = await chat.send_message("Now explain it line by line.")
|
|
208
|
+
```
|
|
209
|
+
|
|
210
|
+
---
|
|
211
|
+
|
|
212
|
+
### Web search
|
|
213
|
+
|
|
214
|
+
```python
|
|
215
|
+
# Enable for every turn in the session
|
|
216
|
+
chat = client.start_chat(web_search=True, num_of_site=5)
|
|
217
|
+
r = await chat.send_message("What AI models were released this week?")
|
|
218
|
+
|
|
219
|
+
# Or enable per-request only
|
|
220
|
+
chat2 = client.start_chat()
|
|
221
|
+
r2 = await chat2.send_message("Latest Python release?", web_search=True)
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
---
|
|
225
|
+
|
|
226
|
+
### Model selection
|
|
227
|
+
|
|
228
|
+
```python
|
|
229
|
+
from oneminai_webapi.constants import ChatModel
|
|
230
|
+
|
|
231
|
+
# Via enum
|
|
232
|
+
r = await client.generate_content("Hello!", model=ChatModel.CLAUDE_SONNET_4_6)
|
|
233
|
+
|
|
234
|
+
# Via raw string — any model ID from the catalog works
|
|
235
|
+
r2 = await client.generate_content("Hello!", model="gemini-2.5-flash")
|
|
236
|
+
|
|
237
|
+
# Session-level default
|
|
238
|
+
chat = client.start_chat(model=ChatModel.GPT_4O)
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
Available chat models (partial list — use `list_models()` for the full live catalog):
|
|
242
|
+
|
|
243
|
+
| Enum | Model ID |
|
|
244
|
+
|---|---|
|
|
245
|
+
| `ChatModel.GPT_4_1_NANO` | `gpt-4.1-nano` |
|
|
246
|
+
| `ChatModel.GPT_4_1_MINI` | `gpt-4.1-mini` |
|
|
247
|
+
| `ChatModel.GPT_4_1` | `gpt-4.1` |
|
|
248
|
+
| `ChatModel.GPT_4O` | `gpt-4o` |
|
|
249
|
+
| `ChatModel.GPT_4O_MINI` | `gpt-4o-mini` |
|
|
250
|
+
| `ChatModel.GPT_5` | `gpt-5` |
|
|
251
|
+
| `ChatModel.O3` | `o3` |
|
|
252
|
+
| `ChatModel.O4_MINI` | `o4-mini` |
|
|
253
|
+
| `ChatModel.CLAUDE_HAIKU_4_5` | `claude-haiku-4-5-20251001` |
|
|
254
|
+
| `ChatModel.CLAUDE_SONNET_4_6` | `claude-sonnet-4-6` |
|
|
255
|
+
| `ChatModel.CLAUDE_OPUS_4_6` | `claude-opus-4-6` |
|
|
256
|
+
| `ChatModel.GEMINI_2_5_FLASH` | `gemini-2.5-flash` |
|
|
257
|
+
| `ChatModel.GEMINI_2_5_PRO` | `gemini-2.5-pro` |
|
|
258
|
+
| `ChatModel.GROK_3` | `grok-3` |
|
|
259
|
+
| `ChatModel.GROK_4` | `grok-4-0709` |
|
|
260
|
+
| `ChatModel.DEEPSEEK_CHAT` | `deepseek-chat` |
|
|
261
|
+
| `ChatModel.DEEPSEEK_REASONER` | `deepseek-reasoner` |
|
|
262
|
+
| `ChatModel.LLAMA_4_SCOUT` | `meta/llama-4-scout-instruct` |
|
|
263
|
+
| `ChatModel.MISTRAL_LARGE` | `mistral-large-latest` |
|
|
264
|
+
| `ChatModel.SONAR_PRO` | `sonar-pro` |
|
|
265
|
+
|
|
266
|
+
---
|
|
267
|
+
|
|
268
|
+
### Persistent server-side conversations
|
|
269
|
+
|
|
270
|
+
```python
|
|
271
|
+
# Create a named thread
|
|
272
|
+
conv = await client.create_conversation("Research session")
|
|
273
|
+
|
|
274
|
+
# Chat within it — history is stored server-side
|
|
275
|
+
r = await client.chat(
|
|
276
|
+
"What is quantum entanglement?",
|
|
277
|
+
conversation_id=conv.conversation_id,
|
|
278
|
+
)
|
|
279
|
+
|
|
280
|
+
# Fetch full message history
|
|
281
|
+
messages = await client.get_conversation_messages(conv.conversation_id)
|
|
282
|
+
for msg in messages:
|
|
283
|
+
print(f"[{msg.role}]: {msg.content}")
|
|
284
|
+
|
|
285
|
+
# List all threads
|
|
286
|
+
all_convs = await client.list_conversations()
|
|
287
|
+
|
|
288
|
+
# Delete when done
|
|
289
|
+
await client.delete_conversation(conv.conversation_id)
|
|
290
|
+
```
|
|
291
|
+
|
|
292
|
+
---
|
|
293
|
+
|
|
294
|
+
### Image generation
|
|
295
|
+
|
|
296
|
+
```python
|
|
297
|
+
from oneminai_webapi.constants import ImageModel
|
|
298
|
+
|
|
299
|
+
result = await client.generate_image(
|
|
300
|
+
"A serene mountain lake at golden hour, photorealistic",
|
|
301
|
+
model=ImageModel.FLUX_1_1_PRO,
|
|
302
|
+
width=1024,
|
|
303
|
+
height=1024,
|
|
304
|
+
num_images=2,
|
|
305
|
+
)
|
|
306
|
+
|
|
307
|
+
print(result.image.url) # first image URL
|
|
308
|
+
for img in result.images:
|
|
309
|
+
await img.save("./outputs") # download all to disk
|
|
310
|
+
```
|
|
311
|
+
|
|
312
|
+
---
|
|
313
|
+
|
|
314
|
+
### Image editing
|
|
315
|
+
|
|
316
|
+
```python
|
|
317
|
+
asset = await client.upload_asset("photo.jpg")
|
|
318
|
+
|
|
319
|
+
upscaled = await client.upscale_image(asset.asset_key, scale=2)
|
|
320
|
+
no_bg = await client.remove_background(asset.asset_key)
|
|
321
|
+
new_bg = await client.replace_background(asset.asset_key, "A sunny beach at sunset")
|
|
322
|
+
edited = await client.edit_image(asset.asset_key, "Make the sky purple")
|
|
323
|
+
inpainted = await client.inpaint_image(asset.asset_key, mask.asset_key, "A red rose")
|
|
324
|
+
extended = await client.extend_image(asset.asset_key, direction="right")
|
|
325
|
+
variants = await client.create_image_variation(asset.asset_key, num_images=4)
|
|
326
|
+
swapped = await client.swap_face(face_img.asset_key, target_img.asset_key)
|
|
327
|
+
rendered = await client.sketch_to_image(sketch.asset_key, "A cozy cottage")
|
|
328
|
+
model_3d = await client.image_to_3d(asset.asset_key)
|
|
329
|
+
clean = await client.remove_text_from_image(asset.asset_key)
|
|
330
|
+
replaced = await client.search_and_replace_in_image(asset.asset_key, "red car", "blue bicycle")
|
|
331
|
+
|
|
332
|
+
prompt = await client.image_to_prompt(asset.asset_key)
|
|
333
|
+
print(prompt.text)
|
|
334
|
+
```
|
|
335
|
+
|
|
336
|
+
---
|
|
337
|
+
|
|
338
|
+
### Text to speech
|
|
339
|
+
|
|
340
|
+
```python
|
|
341
|
+
from oneminai_webapi.constants import TTSModel, TTSVoice
|
|
342
|
+
|
|
343
|
+
audio = await client.text_to_speech(
|
|
344
|
+
"Hello, this is a test.",
|
|
345
|
+
model=TTSModel.OPENAI_TTS_1_HD,
|
|
346
|
+
voice=TTSVoice.NOVA,
|
|
347
|
+
speed=1.0,
|
|
348
|
+
)
|
|
349
|
+
await audio.save("./outputs", verbose=True)
|
|
350
|
+
|
|
351
|
+
# ElevenLabs — pass voice name as a plain string
|
|
352
|
+
el = await client.text_to_speech(
|
|
353
|
+
"Sounds natural.",
|
|
354
|
+
model=TTSModel.ELEVENLABS,
|
|
355
|
+
voice="Rachel",
|
|
356
|
+
)
|
|
357
|
+
|
|
358
|
+
# Sound effects
|
|
359
|
+
sfx = await client.text_to_sound(
|
|
360
|
+
"Heavy rain on a tin roof, distant thunder",
|
|
361
|
+
duration=10.0,
|
|
362
|
+
)
|
|
363
|
+
```
|
|
364
|
+
|
|
365
|
+
---
|
|
366
|
+
|
|
367
|
+
### Speech to text
|
|
368
|
+
|
|
369
|
+
```python
|
|
370
|
+
from oneminai_webapi.constants import STTModel
|
|
371
|
+
|
|
372
|
+
asset = await client.upload_asset("recording.mp3")
|
|
373
|
+
|
|
374
|
+
result = await client.speech_to_text(asset.asset_key, model=STTModel.WHISPER_1)
|
|
375
|
+
print(result.text)
|
|
376
|
+
|
|
377
|
+
translated = await client.translate_audio(asset.asset_key, "English")
|
|
378
|
+
captions = await client.generate_captions(asset.asset_key)
|
|
379
|
+
```
|
|
380
|
+
|
|
381
|
+
---
|
|
382
|
+
|
|
383
|
+
### Voice tools
|
|
384
|
+
|
|
385
|
+
```python
|
|
386
|
+
clean = await client.isolate_voice(audio.asset_key)
|
|
387
|
+
changed = await client.change_voice(audio.asset_key, target_voice="Josh")
|
|
388
|
+
cloned = await client.clone_voice(audio.asset_key, name="MyVoice")
|
|
389
|
+
designed = await client.design_voice(
|
|
390
|
+
"A calm, middle-aged British woman with a warm tone",
|
|
391
|
+
sample_text="Hello, how can I help you today?",
|
|
392
|
+
)
|
|
393
|
+
```
|
|
394
|
+
|
|
395
|
+
---
|
|
396
|
+
|
|
397
|
+
### Video generation
|
|
398
|
+
|
|
399
|
+
```python
|
|
400
|
+
from oneminai_webapi.constants import VideoModel
|
|
401
|
+
|
|
402
|
+
video = await client.generate_video(
|
|
403
|
+
"Drone shot rising over snow-capped mountains at dawn",
|
|
404
|
+
model=VideoModel.KLING,
|
|
405
|
+
duration=5,
|
|
406
|
+
aspect_ratio="16:9",
|
|
407
|
+
)
|
|
408
|
+
await video.save("./outputs")
|
|
409
|
+
|
|
410
|
+
asset = await client.upload_asset("frame.jpg")
|
|
411
|
+
vid2 = await client.image_to_video(
|
|
412
|
+
asset.asset_key,
|
|
413
|
+
prompt="Camera slowly pans left, leaves gently swaying",
|
|
414
|
+
model=VideoModel.LUMA,
|
|
415
|
+
)
|
|
416
|
+
|
|
417
|
+
swapped = await client.swap_face_in_video(video.video_url, face_img.asset_key)
|
|
418
|
+
```
|
|
419
|
+
|
|
420
|
+
---
|
|
421
|
+
|
|
422
|
+
### Music generation
|
|
423
|
+
|
|
424
|
+
```python
|
|
425
|
+
from oneminai_webapi.constants import MusicModel
|
|
426
|
+
|
|
427
|
+
track = await client.generate_music(
|
|
428
|
+
"Upbeat lo-fi hip hop, 90 BPM, warm piano chords",
|
|
429
|
+
model=MusicModel.LYRIA_2,
|
|
430
|
+
)
|
|
431
|
+
await track.save("./outputs")
|
|
432
|
+
|
|
433
|
+
score = await client.generate_music(
|
|
434
|
+
"Epic cinematic orchestral, building tension",
|
|
435
|
+
instrumental=True,
|
|
436
|
+
duration=30.0,
|
|
437
|
+
)
|
|
438
|
+
```
|
|
439
|
+
|
|
440
|
+
---
|
|
441
|
+
|
|
442
|
+
### Code generation
|
|
443
|
+
|
|
444
|
+
```python
|
|
445
|
+
from oneminai_webapi.constants import CodeModel
|
|
446
|
+
|
|
447
|
+
result = await client.generate_code(
|
|
448
|
+
"Async HTTP client with exponential-backoff retry using aiohttp.",
|
|
449
|
+
model=CodeModel.CLAUDE_SONNET_4_6,
|
|
450
|
+
)
|
|
451
|
+
print(result.text)
|
|
452
|
+
|
|
453
|
+
# With live web search to reference latest docs
|
|
454
|
+
result2 = await client.generate_code(
|
|
455
|
+
"FastAPI endpoint validating JWT with PyJWT 2.x.",
|
|
456
|
+
web_search=True,
|
|
457
|
+
)
|
|
458
|
+
```
|
|
459
|
+
|
|
460
|
+
---
|
|
461
|
+
|
|
462
|
+
### Content tools
|
|
463
|
+
|
|
464
|
+
```python
|
|
465
|
+
# Text editing
|
|
466
|
+
corrected = await client.check_grammar("its a beautifull day!")
|
|
467
|
+
paraphrased = await client.paraphrase("Text to rewrite.", tone="casual")
|
|
468
|
+
rewritten = await client.rewrite("Formal text.", tone="friendly")
|
|
469
|
+
summary = await client.summarize(long_article)
|
|
470
|
+
expanded = await client.expand_content("Short stub.")
|
|
471
|
+
shortened = await client.shorten_content(verbose_text)
|
|
472
|
+
|
|
473
|
+
# Translation & detection
|
|
474
|
+
polish = await client.translate("Good morning", "Polish")
|
|
475
|
+
detection = await client.detect_ai_content(suspicious_text)
|
|
476
|
+
|
|
477
|
+
# SEO
|
|
478
|
+
keywords = await client.research_keywords("async Python AI")
|
|
479
|
+
|
|
480
|
+
# Content generation
|
|
481
|
+
article = await client.generate_blog_article("AI trends in 2025")
|
|
482
|
+
email = await client.generate_email("Partnership proposal to Acme Corp")
|
|
483
|
+
reply = await client.generate_email_reply(original_email, "Accept politely")
|
|
484
|
+
tweet = await client.generate_social_post("Launch day!", platform="x")
|
|
485
|
+
linkedin = await client.generate_social_post("We shipped v1!", platform="linkedin")
|
|
486
|
+
fb_ad = await client.generate_ad_copy("Fast async Python SDK", platform="facebook")
|
|
487
|
+
slides = await client.generate_presentation("The future of AI in 2026")
|
|
488
|
+
|
|
489
|
+
# YouTube
|
|
490
|
+
yt_summary = await client.summarize_youtube("https://youtu.be/dQw4w9WgXcQ")
|
|
491
|
+
yt_script = await client.transcribe_youtube("https://youtu.be/dQw4w9WgXcQ")
|
|
492
|
+
yt_polish = await client.translate_youtube("https://youtu.be/dQw4w9WgXcQ", "Polish")
|
|
493
|
+
|
|
494
|
+
# Document translation
|
|
495
|
+
doc = await client.upload_asset("contract.pdf")
|
|
496
|
+
translated = await client.translate_document(doc.file_id, "Spanish")
|
|
497
|
+
```
|
|
498
|
+
|
|
499
|
+
---
|
|
500
|
+
|
|
501
|
+
### Asset upload
|
|
502
|
+
|
|
503
|
+
```python
|
|
504
|
+
import oneminai_webapi
|
|
505
|
+
|
|
506
|
+
# Local file
|
|
507
|
+
asset = await client.upload_asset(
|
|
508
|
+
"report.pdf",
|
|
509
|
+
asset_type=oneminai_webapi.AssetType.DOCUMENT,
|
|
510
|
+
)
|
|
511
|
+
|
|
512
|
+
# Raw bytes
|
|
513
|
+
asset2 = await client.upload_asset(
|
|
514
|
+
data=some_bytes,
|
|
515
|
+
filename="image.png",
|
|
516
|
+
mime_type="image/png",
|
|
517
|
+
asset_type=oneminai_webapi.AssetType.IMAGE,
|
|
518
|
+
)
|
|
519
|
+
|
|
520
|
+
# Public URL
|
|
521
|
+
asset3 = await client.upload_asset_from_url("https://example.com/photo.jpg")
|
|
522
|
+
|
|
523
|
+
# Use in chat
|
|
524
|
+
reply = await client.generate_content(
|
|
525
|
+
"Summarise this document.",
|
|
526
|
+
files=[asset.file_id], # file_id for documents in chat
|
|
527
|
+
)
|
|
528
|
+
|
|
529
|
+
# Use in image APIs
|
|
530
|
+
upscaled = await client.upscale_image(asset2.asset_key) # asset_key for media
|
|
531
|
+
```
|
|
532
|
+
|
|
533
|
+
`AssetRecord` fields:
|
|
534
|
+
|
|
535
|
+
| Field | Description |
|
|
536
|
+
|---|---|
|
|
537
|
+
| `asset_key` | Key for image / video / audio API calls |
|
|
538
|
+
| `file_id` | UUID for `files=[]` in chat attachments |
|
|
539
|
+
| `asset_type` | `"DOCUMENT"`, `"IMAGE"`, `"AUDIO"`, `"VIDEO"` |
|
|
540
|
+
|
|
541
|
+
---
|
|
542
|
+
|
|
543
|
+
### Account & credits
|
|
544
|
+
|
|
545
|
+
```python
|
|
546
|
+
user = await client.get_current_user()
|
|
547
|
+
print(user.email, user.plan, user.credit)
|
|
548
|
+
|
|
549
|
+
balance = await client.get_team_credits()
|
|
550
|
+
|
|
551
|
+
estimate = await client.estimate_chat_cost(
|
|
552
|
+
"Write a long essay about quantum computing.",
|
|
553
|
+
models=["gpt-4o", "claude-sonnet-4-6"],
|
|
554
|
+
web_search=True,
|
|
555
|
+
)
|
|
556
|
+
print(f"Estimated: {estimate.total_estimated_credit} credits")
|
|
557
|
+
|
|
558
|
+
models = await client.list_models(feature="UNIFY_CHAT_WITH_AI")
|
|
559
|
+
```
|
|
560
|
+
|
|
561
|
+
---
|
|
562
|
+
|
|
563
|
+
## Logging
|
|
564
|
+
|
|
565
|
+
```python
|
|
566
|
+
import oneminai_webapi
|
|
567
|
+
oneminai_webapi.set_log_level("DEBUG") # DEBUG | INFO | WARNING | ERROR
|
|
568
|
+
```
|
|
569
|
+
|
|
570
|
+
---
|
|
571
|
+
|
|
572
|
+
## Error handling
|
|
573
|
+
|
|
574
|
+
```python
|
|
575
|
+
from oneminai_webapi.exceptions import (
|
|
576
|
+
AuthenticationError, # 401 — invalid or missing API key / token
|
|
577
|
+
RateLimitError, # 429 — too many requests
|
|
578
|
+
ValidationError, # 422 — bad request payload
|
|
579
|
+
APIError, # any other 4xx / 5xx
|
|
580
|
+
AssetUploadError, # file upload failed
|
|
581
|
+
OAuthError, # OAuth login failed
|
|
582
|
+
)
|
|
583
|
+
|
|
584
|
+
try:
|
|
585
|
+
r = await client.generate_content("Hello!")
|
|
586
|
+
except AuthenticationError:
|
|
587
|
+
print("Invalid API key.")
|
|
588
|
+
except RateLimitError as e:
|
|
589
|
+
print(f"Rate limited — retry in {e.retry_after_s}s")
|
|
590
|
+
except ValidationError as e:
|
|
591
|
+
print(f"Validation error: {e.details}")
|
|
592
|
+
except APIError as e:
|
|
593
|
+
print(f"API error {e.status_code}: {e}")
|
|
594
|
+
```
|
|
595
|
+
|
|
596
|
+
---
|
|
597
|
+
|
|
598
|
+
## API reference
|
|
599
|
+
|
|
600
|
+
### `OneMinAIClient`
|
|
601
|
+
|
|
602
|
+
#### Chat
|
|
603
|
+
|
|
604
|
+
| Method | Description |
|
|
605
|
+
|---|---|
|
|
606
|
+
| `generate_content(prompt, ...)` | Single-turn, full response |
|
|
607
|
+
| `generate_content_stream(prompt, ...)` | Single-turn, streamed |
|
|
608
|
+
| `chat(prompt, *, stream, ...)` | Low-level chat primitive |
|
|
609
|
+
| `start_chat(model, ...)` | Create a `ChatSession` |
|
|
610
|
+
|
|
611
|
+
#### Conversations
|
|
612
|
+
|
|
613
|
+
| Method | Description |
|
|
614
|
+
|---|---|
|
|
615
|
+
| `create_conversation(title)` | Create a server-side thread |
|
|
616
|
+
| `list_conversations()` | List all threads |
|
|
617
|
+
| `get_conversation(conv_id)` | Fetch thread metadata |
|
|
618
|
+
| `get_conversation_messages(conv_id)` | Fetch message history |
|
|
619
|
+
| `delete_conversation(conv_id)` | Delete a thread |
|
|
620
|
+
|
|
621
|
+
#### Images
|
|
622
|
+
|
|
623
|
+
| Method | Description |
|
|
624
|
+
|---|---|
|
|
625
|
+
| `generate_image(prompt, ...)` | Text-to-image |
|
|
626
|
+
| `edit_image(image_url, prompt, ...)` | Edit with instruction |
|
|
627
|
+
| `create_image_variation(image_url, ...)` | Generate variations |
|
|
628
|
+
| `extend_image(image_url, direction, ...)` | Outpaint / extend canvas |
|
|
629
|
+
| `inpaint_image(image_url, mask_url, prompt, ...)` | Inpaint masked region |
|
|
630
|
+
| `upscale_image(image_url, scale, ...)` | Upscale 2× or 4× |
|
|
631
|
+
| `remove_background(image_url, ...)` | Background removal |
|
|
632
|
+
| `replace_background(image_url, prompt, ...)` | Background replacement |
|
|
633
|
+
| `remove_object_from_image(image_url, ...)` | Object removal |
|
|
634
|
+
| `remove_text_from_image(image_url)` | Text overlay removal |
|
|
635
|
+
| `swap_face(source_url, target_url, ...)` | Face swap |
|
|
636
|
+
| `sketch_to_image(sketch_url, prompt, ...)` | Sketch → image |
|
|
637
|
+
| `image_to_3d(image_url, ...)` | Image → 3D model |
|
|
638
|
+
| `image_to_prompt(image_url, ...)` | Reverse-engineer prompt |
|
|
639
|
+
| `search_and_replace_in_image(image_url, ...)` | Find & replace object |
|
|
640
|
+
|
|
641
|
+
#### Audio
|
|
642
|
+
|
|
643
|
+
| Method | Description |
|
|
644
|
+
|---|---|
|
|
645
|
+
| `text_to_speech(text, ...)` | TTS |
|
|
646
|
+
| `speech_to_text(audio_url, ...)` | STT / transcription |
|
|
647
|
+
| `translate_audio(audio_url, language, ...)` | Transcribe + translate |
|
|
648
|
+
| `generate_captions(audio_or_video_url, ...)` | Captions / subtitles |
|
|
649
|
+
| `text_to_sound(prompt, ...)` | Sound effect generation |
|
|
650
|
+
| `isolate_voice(audio_url)` | Voice isolation |
|
|
651
|
+
| `change_voice(audio_url, target_voice)` | Voice conversion |
|
|
652
|
+
| `clone_voice(audio_url, name, ...)` | Voice cloning |
|
|
653
|
+
| `design_voice(description, ...)` | Voice design |
|
|
654
|
+
|
|
655
|
+
#### Video
|
|
656
|
+
|
|
657
|
+
| Method | Description |
|
|
658
|
+
|---|---|
|
|
659
|
+
| `generate_video(prompt, ...)` | Text-to-video |
|
|
660
|
+
| `image_to_video(image_url, ...)` | Image-to-video |
|
|
661
|
+
| `swap_face_in_video(video_url, face_url)` | Face swap in video |
|
|
662
|
+
|
|
663
|
+
#### Music
|
|
664
|
+
|
|
665
|
+
| Method | Description |
|
|
666
|
+
|---|---|
|
|
667
|
+
| `generate_music(prompt, ...)` | Music generation |
|
|
668
|
+
|
|
669
|
+
#### Code & content
|
|
670
|
+
|
|
671
|
+
| Method | Description |
|
|
672
|
+
|---|---|
|
|
673
|
+
| `generate_code(prompt, ...)` | Code generation |
|
|
674
|
+
| `check_grammar(text)` | Grammar correction |
|
|
675
|
+
| `paraphrase(text, ...)` | Paraphrase |
|
|
676
|
+
| `rewrite(text, ...)` | Rewrite |
|
|
677
|
+
| `summarize(text, ...)` | Summarisation |
|
|
678
|
+
| `expand_content(text, ...)` | Content expansion |
|
|
679
|
+
| `shorten_content(text, ...)` | Content shortening |
|
|
680
|
+
| `translate(text, target_language, ...)` | Translation |
|
|
681
|
+
| `detect_ai_content(text)` | AI content detection |
|
|
682
|
+
| `research_keywords(topic, ...)` | SEO keyword research |
|
|
683
|
+
| `generate_blog_article(prompt, ...)` | Blog article |
|
|
684
|
+
| `generate_email(prompt, ...)` | Email |
|
|
685
|
+
| `generate_email_reply(original, instructions, ...)` | Email reply |
|
|
686
|
+
| `generate_social_post(prompt, platform, ...)` | Social media post |
|
|
687
|
+
| `generate_social_comment(post_text, platform, ...)` | Social comment |
|
|
688
|
+
| `generate_ad_copy(prompt, platform, ...)` | Ad copy |
|
|
689
|
+
| `generate_presentation(prompt, ...)` | Presentation |
|
|
690
|
+
| `summarize_youtube(url, ...)` | YouTube summary |
|
|
691
|
+
| `transcribe_youtube(url, ...)` | YouTube transcript |
|
|
692
|
+
| `translate_youtube(url, language, ...)` | YouTube translation |
|
|
693
|
+
| `translate_document(file_id, language, ...)` | Document translation |
|
|
694
|
+
|
|
695
|
+
#### Assets
|
|
696
|
+
|
|
697
|
+
| Method | Description |
|
|
698
|
+
|---|---|
|
|
699
|
+
| `upload_asset(file_path, ...)` | Upload local file |
|
|
700
|
+
| `upload_asset_from_url(url, ...)` | Register public URL |
|
|
701
|
+
|
|
702
|
+
#### Account
|
|
703
|
+
|
|
704
|
+
| Method | Description |
|
|
705
|
+
|---|---|
|
|
706
|
+
| `get_current_user()` | User and team info |
|
|
707
|
+
| `get_team_credits()` | Credit balance |
|
|
708
|
+
| `estimate_chat_cost(prompt, models, ...)` | Pre-flight cost estimate |
|
|
709
|
+
| `list_models(feature)` | Model catalog |
|
|
710
|
+
| `list_team_members()` | Team members |
|
|
711
|
+
| `get_feature_settings(feature)` | Feature settings |
|
|
712
|
+
| `update_feature_settings(models, feature)` | Update feature settings |
|
|
713
|
+
| `update_user_settings(**settings)` | Update user settings |
|
|
714
|
+
| `get_notebook()` | User notebook |
|
|
715
|
+
| `get_unread_notification_count()` | Unread notification count |
|
|
716
|
+
| `get_notification(notification_id)` | Fetch a notification |
|
|
717
|
+
| `get_explore_posts()` | Public explore feed |
|
|
718
|
+
| `list_tags()` | Conversation tags |
|
|
719
|
+
| `list_studios()` | Team studios |
|
|
720
|
+
| `oauth_login(token)` | Authenticate with Google OAuth |
|
|
721
|
+
|
|
722
|
+
---
|
|
723
|
+
|
|
724
|
+
### `ChatSession`
|
|
725
|
+
|
|
726
|
+
| Method / Property | Description |
|
|
727
|
+
|---|---|
|
|
728
|
+
| `send_message(prompt, ...)` | Send a message, await full reply |
|
|
729
|
+
| `send_message_stream(prompt, ...)` | Send a message, stream reply |
|
|
730
|
+
| `delete()` | Delete the server-side conversation |
|
|
731
|
+
| `.conversation_id` | Server UUID of this thread |
|
|
732
|
+
| `.model` | Model used by this session |
|
|
733
|
+
|
|
734
|
+
---
|
|
735
|
+
|
|
736
|
+
### Return types
|
|
737
|
+
|
|
738
|
+
| Type | Key fields |
|
|
739
|
+
|---|---|
|
|
740
|
+
| `ChatOutput` | `text`, `text_delta`, `model`, `conversation_id`, `record_id` |
|
|
741
|
+
| `ImageOutput` | `images: list[GeneratedImage]`, `image` (first), `model`, `record_id` |
|
|
742
|
+
| `GeneratedImage` | `url`, `model`; `.save(dir)` downloads to disk |
|
|
743
|
+
| `AudioOutput` | `audio_url`, `model`, `record_id`; `.save(dir)` |
|
|
744
|
+
| `MusicOutput` | `audio_url`, `model`, `record_id`; `.save(dir)` |
|
|
745
|
+
| `VideoOutput` | `video_url`, `model`, `record_id`; `.save(dir)` |
|
|
746
|
+
| `TranscriptionOutput` | `text`, `model`, `record_id` |
|
|
747
|
+
| `AssetRecord` | `asset_key`, `file_id`, `asset_type` |
|
|
748
|
+
| `UserRecord` | `user_id`, `email`, `team_id`, `team_name`, `credit`, `plan` |
|
|
749
|
+
| `ConversationRecord` | `conversation_id`, `title` |
|
|
750
|
+
| `MessageRecord` | `role`, `content`, `record_id`, `credit`, `execution_time` |
|
|
751
|
+
| `CreditEstimate` | `models`, `total_input_tokens`, `total_estimated_credit` |
|
|
752
|
+
|
|
753
|
+
---
|
|
754
|
+
|
|
755
|
+
## Development
|
|
756
|
+
|
|
757
|
+
```sh
|
|
758
|
+
git clone https://github.com/cyber-wojtek/1MinAI-API
|
|
759
|
+
cd 1MinAI-API
|
|
760
|
+
pip install -e ".[dev]"
|
|
761
|
+
|
|
762
|
+
export ONEMINAI_API_KEY="your-key"
|
|
763
|
+
python examples.py
|
|
764
|
+
```
|
|
765
|
+
|
|
766
|
+
---
|
|
767
|
+
|
|
768
|
+
## References
|
|
769
|
+
|
|
770
|
+
- [1min.AI](https://1min.ai)
|
|
771
|
+
- [1min.AI app](https://app.1min.ai)
|
|
772
|
+
- [claude-webapi](https://github.com/cyber-wojtek/Claude-API) — sister project for Claude.ai
|
|
773
|
+
- [gemini_webapi](https://github.com/HanaokaYuzu/Gemini-API) — inspiration for the interface design
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
1minai_webapi-1.0.0.dist-info/METADATA,sha256=ScmbSRtDniiZcojAfWakElmYLzY6NZWe6irjXClDs3Q,23428
|
|
2
|
+
1minai_webapi-1.0.0.dist-info/WHEEL,sha256=QccIxa26bgl1E6uMy58deGWi-0aeIkkangHcxk2kWfw,87
|
|
3
|
+
1minai_webapi-1.0.0.dist-info/licenses/LICENSE,sha256=kPW1j-q9NhteRizSkrlesUMHYX2kO9B9iGw3JK64Iy4,1065
|
|
4
|
+
1minai_webapi-1.0.0.dist-info/RECORD,,
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Wojciech
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|