Metadata-Version: 2.4
Name: craft-suite-api
Version: 0.8.0
Summary: Craft suite API connector and MCP server; current ArtCraft backend subset
Author-email: Repository Maintainers <maintainers@knuckles.team>
License: MIT
Classifier: Development Status :: 4 - Beta
Classifier: License :: OSI Approved :: MIT License
Classifier: Environment :: Console
Classifier: Operating System :: POSIX :: Linux
Classifier: Programming Language :: Python :: 3
Requires-Python: <3.15,>=3.12
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: rfc3986-validator<0.2,>=0.1.1
Requires-Dist: rfc3339-validator<0.2,>=0.1.4
Requires-Dist: jsonschema<5,>=4.26.0
Requires-Dist: regex>=2026.9.29
Requires-Dist: scion-sdk[mcp]<0.9,>=0.8.2
Provides-Extra: mcp
Requires-Dist: scion-sdk[mcp,storage-s3]<0.9,>=0.8.2; extra == "mcp"
Provides-Extra: all
Requires-Dist: scion-sdk[mcp,storage-s3]<0.9,>=0.8.2; extra == "all"
Provides-Extra: test
Requires-Dist: pytest-xdist>=3.8.0; extra == "test"
Requires-Dist: pytest; extra == "test"
Requires-Dist: pytest-asyncio; extra == "test"
Requires-Dist: pytest-cov; extra == "test"
Requires-Dist: rdflib<8,>=7.0.0; extra == "test"
Dynamic: license-file

# Craft Suite API connector

The MCP connector for the ArtCraft suite. It serves **every operation of the
ArtCraft backend API as one typed tool** (268 today), generated from the
backend's published API description, and the suite's desktop apps as lazily
loaded MCP upstreams (see [the apps spec](specs/craft-suite-apps/spec.md)).

## Backend tools

Each backend operation is the tool `craft_suite_<operationId>`, for example
`craft_suite_list_tags_handler`, `craft_suite_omni_gen_image_models_handler`,
`craft_suite_omni_api_image_generate_handler` or
`craft_suite_omni_upload_image_media_file_handler`. Inputs and outputs are typed
from the description. Reads (GET) are annotated read-only.

| Class | Operations | Policy |
| --- | --- | --- |
| read | 92 | Runs directly |
| generation | 62 | Write: operator switch plus confirmation |
| upload | 24 | Write; the file part is base64 text, sent as a binary multipart part |
| account | 21 | Write (sessions, keys, credentials, profile) |
| moderation | 10 | Write |
| write | 59 | Write (folders, tags, bookmarks, ratings and other changes) |

Every refusal is a typed result `{cancelled, operation, reason, write_class}`:
`BACKEND_NOT_CONFIGURED` with no base URL, `WRITES_DISABLED` without the operator
switch, or the SDK confirmation refusal. Every write decision is logged to the
`craft_suite_api.audit` logger.

## Package identity

The connector is `craft-suite-api`, imported as `craft_suite_api`, with the
`craft-suite-mcp` command and `CRAFT_SUITE_API_` configuration prefix.

## Usage

| Setting | Meaning |
| --- | --- |
| `CRAFT_SUITE_API_BASE_URL` | The backend HTTPS origin, without a path. Unset: every backend call refuses. |
| `CRAFT_SUITE_API_TOKEN_REF` | An SDK credential reference (for example `env://CRAFT_SUITE_SESSION`) sent as the `session` header. |
| `CRAFT_SUITE_API_ALLOW_WRITES` | Default false. Enables writes; each one still needs confirmation (elicited, or `confirm=true`). |
| `CRAFT_SUITE_API_ALLOW_PLAINTEXT` | Default false. Allows a credential over plain HTTP. |

TLS verification stays on. Redirects are not followed, each request is tried
once with a 30 s timeout, and responses are capped at 16 MiB. Graph ingestion is
unavailable.

```json
{"name":"craft_suite_omni_gen_image_models_handler","arguments":{}}
```

## Provenance

`craft_suite_api/api_spec/backend.openapi.json` is the backend's published API
description, kept byte for byte and pinned by sha256 in
`craft_suite_api/api_spec/backend.source.json`. Both ship in the package. When
the server first builds the backend tools, `craft_suite_api/backend_spec.py`
checks the pin and repairs the document's known defects in memory (missing
references, untyped parameters, multipart upload bodies, the session scheme).
Nothing generated is committed and there is no regenerate step. The backend
source is under its own source-available licence: only the interface
description is used. To take a new description, replace the pinned file,
update the sha256 and run `python -m pytest tests -q`.

## Validation boundary

Tests use the real SDK HTTP, auth and MCP components with a fake transport at
the backend boundary. Writes are proven there; live writes need the operator
switch and a backend credential.
