Python SDK (bessai)
The official Python SDK is the easiest way to build agents, place and analyze calls, run the same agents as text chat, launch outbound campaigns, and manage your account. This section documents every method on the client — one page per resource.
1. Install & get an API key
pip install bessai
Get your API key from the BESS AI dashboard → Settings → API Keys. The key looks like bess_sk_live_xxxxxxxx… and is shown only once at creation — store it securely.
Set it as an environment variable (the SDK reads it automatically):
export BESSAI_API_KEY="bess_sk_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
2. Quickstart
from bessai import BessAI
client = BessAI() # reads BESSAI_API_KEY from the environment
## 3. Client setup
```python
from bessai import BessAI, AsyncBessAI
client = BessAI(
api_key=None, # falls back to env BESSAI_API_KEY
base_url="https://api.bess-ai.com", # or env BESSAI_BASE_URL
timeout=30.0, # seconds
max_retries=3,
headers=None, # extra headers, optional
)
| Option | Default | Notes |
|---|---|---|
api_key | BESSAI_API_KEY env | Required. Raises ValueError if neither is set. |
base_url | https://api.bess-ai.com | Override with BESSAI_BASE_URL. |
timeout | 30.0 | Per-request timeout in seconds. |
max_retries | 3 | Auto-retries on 429/500/502/503/504 and connection errors, with exponential backoff that honors Retry-After. |
- Every request sends
Authorization: Bearer <api_key>. - Namespaces:
agent,call,chat,phone_number,batch_call,workflow,analytic,billing,config,knowledge_bases,api_keys. Plural aliases also exist (agents,calls,phone_numbers,batch_calls,workflows,analytics). - Context manager:
with BessAI() as client: ...closes the HTTP session automatically (or callclient.close()). - Async: use
AsyncBessAI(...)— every method is identical withawait(see Async usage).
4. Errors & exceptions
All SDK exceptions inherit from bessai.BessAIError and carry message, status_code, and body.
from bessai import BessAI, AuthenticationError, RateLimitError, NotFoundError, BessAIError
client = BessAI()
try:
agent = client.agent.retrieve("does-not-exist")
except NotFoundError:
print("No such agent")
except RateLimitError as e:
print(f"Slow down — retry after {e.retry_after}s")
except AuthenticationError:
print("Bad or missing API key")
except BessAIError as e:
print(f"API error {e.status_code}: {e.message}")
| Exception | HTTP | Meaning |
|---|---|---|
AuthenticationError | 401 | Missing, invalid, or expired API key. |
PermissionDeniedError | 403 | The key's scopes don't allow this operation. |
NotFoundError | 404 | Resource doesn't exist. |
ValidationError | 422 | Invalid input. Has .errors (a list of field errors). |
RateLimitError | 429 | Rate limit hit. Has .retry_after (seconds). |
InternalServerError | 5xx | Server-side error. |
ConnectionError | — | Could not reach the server. |
TimeoutError | — | The request timed out. |
BessAIError | — | Base class for all of the above. |
Rate limits are per API key, per minute and per day, by tier (free / starter / professional / enterprise). Successful responses include
X-RateLimit-*headers.
5. Pagination
List methods take simple offset/limit-style arguments and return a plain Python list:
- Most resources:
skip+limit. client.workflow.list(...):page+per_page.client.billing.*:limit+offset.
agents = client.agent.list(skip=0, limit=50)
more = client.agent.list(skip=50, limit=50)
There is no automatic paginator — loop with increasing skip/page until you get fewer than limit items.
7. Async usage
Every method exists on AsyncBessAI with the same signature — just await it:
import asyncio
from bessai import AsyncBessAI
async def main():
async with AsyncBessAI() as client:
agents = await client.agent.list()
for a in agents:
print(a.agent_id, a.agent_name)
asyncio.run(main())
Questions or issues? contact@bess-ai.com.