Metadata-Version: 2.5
Name: cocka
Version: 0.1.0
Summary: Official Python SDK for the Čočka receipt-to-ISDOC API
Project-URL: Homepage, https://github.com/qubusp/cocka-py
Project-URL: Repository, https://github.com/qubusp/cocka-py
Project-URL: API reference, https://api.cocka.cloud/api-docs
Author: Čočka
License-Expression: MIT
License-File: LICENSE
Keywords: ares,cocka,czech,invoicing,isdoc,receipts
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.8
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Requires-Python: >=3.8
Requires-Dist: requests>=2.25
Provides-Extra: dev
Requires-Dist: mypy; extra == 'dev'
Requires-Dist: pytest>=7; extra == 'dev'
Requires-Dist: responses>=0.23; extra == 'dev'
Description-Content-Type: text/markdown

# cocka

Official Python SDK for the [Čočka](https://cocka.cloud) receipt-to-ISDOC
API — photograph a receipt, get back OCR-extracted, ARES-verified,
ISDOC 6.0.1 invoice data.

Full API reference: [api.cocka.cloud/api-docs](https://api.cocka.cloud/api-docs)
(Swagger UI) or the raw spec at
[api.cocka.cloud/openapi.yaml](https://api.cocka.cloud/openapi.yaml).

## Install

```bash
pip install cocka
```

## Quickstart

```python
from cocka import Cocka

client = Cocka()
client.login("user@example.com", "password")

# Enqueue a receipt photo for OCR + extraction + ARES verification
job = client.ingest("receipt.jpg")
print(job)  # {"status": "queued", "job_id": "...", "filename": "receipt.jpg"}

# List your tenant's receipts
for receipt in client.list_receipts():
    print(receipt.id, receipt.supplier_name, receipt.total_incl_vat)

# Mark one as verified (generates the ISDOC file server-side)
client.update_receipt(receipt.id, verified=True)
```

Already have a long-lived API token (issued via `client.issue_my_token()`,
the web UI's "generate token" button, or an admin)? Skip `login()`:

```python
client = Cocka(token="...")
```

## Uploading and polling

`ingest()` is fire-and-forget — there's no per-job status endpoint for it,
poll `list_receipts()`/`get_receipt()` instead. `upload()` is the
JSON-API counterpart that *does* support polling:

```python
job = client.upload("receipt.jpg")
status = client.get_upload_status(job["job_id"])
```

## Looking up a company in the Czech ARES registry

No authentication required:

```python
company = client.lookup_ares("27074358")
if company is None:
    print("no company found for this IČO")
else:
    print(company.name, company.address)
```

## Errors

Every non-2xx response raises a subclass of `CockaAPIError` (itself a
`CockaError`), carrying `.status_code`, `.reason`, and the raw `.payload`:

```python
from cocka import CockaAuthError, CockaNotFoundError, CockaTrialExhaustedError

try:
    client.ingest("receipt.jpg")
except CockaTrialExhaustedError:
    print("free trial used up")
except CockaAuthError:
    print("token expired or invalid, log in again")
```

| Exception                    | HTTP status |
|-------------------------------|-------------|
| `CockaAuthError`              | 401         |
| `CockaTrialExhaustedError`    | 402         |
| `CockaForbiddenError`         | 403         |
| `CockaNotFoundError`          | 404         |
| `CockaRateLimitedError`       | 429         |
| `CockaAPIError` (base)        | any other non-2xx |

`lookup_ares()` is the one exception to this: a 404 there just means "no
company for this IČO," a normal outcome, so it returns `None` instead of
raising.

## Models

Response objects (`Receipt`, `Company`, `Principal`, `Tenant`) are thin,
forward-compatible wrappers over the JSON the API returned — known fields
are available as attributes (`receipt.supplier_name`), and any field not
yet wrapped by name is still reachable via `receipt["some_field"]` or
`receipt.raw`.

## Full method reference

Auth: `login`, `logout`, `request_password_reset`, `confirm_password_reset`,
`change_password`, `admin_request_password_reset`, `get_my_token`,
`issue_my_token`, `revoke_my_token`, `register_device`.

Receipts: `ingest`, `upload`, `get_upload_status`, `list_receipts`,
`get_receipt`, `update_receipt`, `verify_receipt`, `reextract_receipt`.

ARES: `lookup_ares`.

Admin/back-office (require a `platform_admin` token, or in some cases a
tenant's own `role=admin` user): `list_tenants`, `create_tenant`,
`get_tenant`, `update_tenant`, `grant_tenant_transformations`,
`get_billing`, `set_billing_price`, `list_leads`, `list_tenant_users`,
`create_tenant_user`, `issue_tenant_user_token`,
`revoke_tenant_user_token`.

## Development

```bash
pip install -e ".[dev]"
pytest
```

## License

MIT
