Metadata-Version: 2.4
Name: catentio-saas
Version: 0.3.0
Summary: Official Python SDK for Catentio. `PublicClient` speaks the public API (https://catent.io/v1 — API-key auth: agents, templates, runs, projects, webhooks). `CatentioClient` speaks the internal control plane (session-cookie auth via the Huudis device flow).
Project-URL: Homepage, https://catentio.com
Project-URL: Documentation, https://catentio.com/docs
Project-URL: Source, https://github.com/hachimi-cat/saas-catentio/tree/main/sdk/python
Project-URL: Issues, https://github.com/hachimi-cat/saas-catentio/issues
Author-email: Forjio <hello@catentio.com>
License: MIT
Keywords: agent-platform,catentio,forjio,huudis,operator
Classifier: Development Status :: 4 - Beta
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3 :: Only
Classifier: Topic :: Internet :: WWW/HTTP
Classifier: Typing :: Typed
Requires-Python: >=3.9
Requires-Dist: httpx>=0.27.0
Requires-Dist: pyjwt[crypto]>=2.9.0
Provides-Extra: dev
Requires-Dist: pytest>=8.0; extra == 'dev'
Requires-Dist: respx>=0.21; extra == 'dev'
Description-Content-Type: text/markdown

# catentio-saas (Python)

Official Python SDK for the [catentio-saas](https://catentio.com) control
plane. Python parity with [`@forjio/catentio-saas-node`](../node) —
same 25 resource namespaces, same Bearer auth via Huudis OIDC, same API
envelope.

## Install

```bash
pip install catentio-saas
```

(Python import: `catentio_saas` — PEP 8 underscore-naming.)

## Quickstart

### Static API key (server-to-server)

```python
from catentio_saas import CatentioClient

with CatentioClient(api_key="cat_pk_...") as catentio:
    workspaces = catentio.workspaces.list()
    print(workspaces)

    run = catentio.agents.invoke("cimi", {"message": "hello"})
    print(run["id"])
```

### Bearer session (CLI / device-flow)

```python
from catentio_saas import CatentioClient, Session

# An access_token from your Huudis device-flow login.
session = Session(
    access_token="...",
    refresh_token="...",
    expires_at=1_800_000_000,
    issuer="https://huudis.com",
    client_id="catentio-cli",
)

with CatentioClient(session=session) as catentio:
    projects = catentio.projects.list()
```

For automatic refresh, wire a `refresh_fn` into the `Session`. The SDK
keeps the refresh callable pluggable so it can use the `huudis` Python
SDK's `refresh_access_token` (or your own) without taking a hard
dependency on it.

## Resource namespaces

| Namespace | Routes |
|---|---|
| `catentio.workspaces` | `list`, `show`, `create`, `destroy`, `set_state` |
| `catentio.agents` | `list`, `get`, `invoke` |
| `catentio.runs` | `list`, `get`, `cancel` |
| `catentio.projects` | `list`, `get`, `create`, `list_attachments`, `add_attachment`, `list_tasks`, `get_task`, `list_subtasks`, `get_subtask`, `list_attempts`, `list_artifacts`, `list_events`, `cost`, `pause`, `resume`, `abandon`, `run_step`, `retry_subtask` |
| `catentio.templates` | `list` |
| `catentio.tools` | `list`, `get`, `create`, `update`, `delete` |
| `catentio.skills` | `list`, `get` |
| `catentio.memory` | `stats`, `list_entries`, `get_entry`, `create_entry`, `update_entry` |
| `catentio.api_keys` | `list`, `create`, `delete` |
| `catentio.billing` | `catalog`, `summary`, `subscribe` |
| `catentio.cost` | `summary` |
| `catentio.integrations` | `list`, `configure`, `delete` |
| `catentio.webhooks` | `list`, `create`, `delete` |
| `catentio.scheduled_jobs` | `list`, `create`, `update`, `delete` |
| `catentio.feature_flags` | `list`, `set` |
| `catentio.files` | `list`, `upload`, `delete` |
| `catentio.output_destinations` | `list`, `get`, `create`, `update`, `delete` |
| `catentio.discord` | `status`, `send_message` |
| `catentio.gojo` | `sessions` |
| `catentio.heartbeats` | `list`, `config`, `update_config` |
| `catentio.system` | `info`, `health` (unauth) |
| `catentio.chat` | `send`, `history` |
| `catentio.events` | `list` |
| `catentio.inbound_webhooks` | `list` |

Every method takes an optional `token=` last-arg to override the
client-level Bearer for a single call (e.g. acting on behalf of another
workspace).

## Errors

```python
from catentio_saas import CatentioError, NetworkError

try:
    catentio.workspaces.show("ws_404")
except CatentioError as e:
    print(e.code, e.message, e.status, e.request_id)
except NetworkError as e:
    print("transport failure:", e.message)
```

## Source

<https://github.com/hachimi-cat/saas-catentio/tree/main/sdk/python>

## License

MIT
