Skip to main content

Official Python SDK for CloudFactory AI Platform - download and manage project assets and results

Project description

CloudFactory AI Platform Python Client

PyPI version Python Support License: MIT

Official Python SDK for the CloudFactory AI Platform. Download COCO format annotations from your projects with flexible filtering (batches, work items, timestamps), concurrent workers, automatic retries, and progress tracking.

Prerequisites

Before you start, you will need:

  • Python 3.10 or later
  • A CloudFactory API Key
  • Your Project ID
  • Your Space ID

Installation

uv add cf-ai-platform-client

Or with pip:

pip install cf-ai-platform-client

Quick Start

Option A: Synchronous (simpler, no async required)

If you are writing a script, running in a Jupyter notebook, or are not familiar with Python async/await syntax, use SyncCFUserClient:

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("YOUR_API_KEY") as client:
    summary = client.download_project(
        project_id="YOUR_PROJECT_ID",
        space_id="YOUR_SPACE_ID",
        destination="./downloads"
    )

print(f"Downloaded {summary.successful} of {summary.total_items} items")
if summary.failed > 0:
    print(f"  {summary.failed} items failed")

Option B: Async script or entry point

If you are writing an async application or prefer async/await syntax, use CFUserClient:

import asyncio
from cf_ai_platform_client import CFUserClient

async def main():
    async with CFUserClient.create_with_api_key("YOUR_API_KEY") as client:
        summary = await client.download_project(
            project_id="YOUR_PROJECT_ID",
            space_id="YOUR_SPACE_ID",
            destination="./downloads"
        )

    print(f"Downloaded {summary.successful} of {summary.total_items} items")

asyncio.run(main())

Usage Examples

The examples below use SyncCFUserClient for simplicity. Async equivalents use CFUserClient with await and async with.

Basic Download

Download all COCO annotations from a project:

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads"
    )

    if summary.failed > 0:
        print("Some downloads failed:")
        for result in summary.results:
            if not result.success:
                print(f"  - Item {result.item_id}: {result.error}")

Filter by Batch IDs

Download only specific batches (up to 100 batch IDs):

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads",
        batch_ids=[1, 2, 3]
    )

Filter by Work Item IDs

Download specific work items by their UUIDs (up to 100):

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads",
        work_item_ids=[
            "550e8400-e29b-41d4-a716-446655440000",
            "6ba7b810-9dad-11d1-80b4-00c04fd430c8"
        ]
    )

Filter by Date (ISO 8601)

Filter by creation date:

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads",
        created_at_from="2026-01-01T00:00:00Z",
        created_at_to="2026-01-31T23:59:59Z"
    )

Filter by last updated date:

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads",
        updated_at_from="2026-02-11T00:00:00Z",
        updated_at_to="2026-02-18T23:59:59Z"
    )

Note: these filters apply to work items — when they were created and last updated.

Combine Multiple Filters

All filters can be combined freely:

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads",
        batch_ids=[1, 2],
        created_at_from="2026-01-01T00:00:00Z",
        created_at_to="2026-01-31T23:59:59Z",
        max_workers=15
    )

Configure Concurrency

By default the SDK downloads 10 work items concurrently. Increase this for faster downloads or decrease it to reduce load:

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads",
        max_workers=20  # default: 10
    )

Inspect Download Results

Access detailed information about each downloaded item:

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads"
    )

    for result in summary.results:
        if result.success:
            print(f"✅ {result.item_id} -> {result.file_path}")
        else:
            print(f"❌ {result.item_id}: {result.error}")

Custom Base URL

Use a custom API endpoint (e.g., for staging):

from cf_ai_platform_client import SyncCFUserClient

with SyncCFUserClient.create_with_api_key(
    api_key="MY_API_KEY",
    base_url="https://api.staging.ai.cloudfactory.app/api/v1"
) as client:
    summary = client.download_project(
        project_id="proj_abc123",
        space_id="space_456",
        destination="./my_downloads"
    )

File Organization

Downloaded COCO annotation files are organized by batch name:

destination/
├── Default/
│   ├── <work_item_id>.json
│   └── <work_item_id>.json
└── Training_Batch_001/
    └── <work_item_id>.json
  • Files are grouped by batch name (fetched from batch metadata)
  • If no batches have been defined, all items will be under the Default batch
  • File naming: {work_item_id}.{extension}
  • Extension is auto-detected from URL (defaults to .json)
  • Each .json file is a COCO-format annotation with an asset_url field injected into the info block so you can trace it back to the original asset
  • Only COMPLETED work items are downloaded by default

API Reference

SyncCFUserClient (synchronous)

Synchronous wrapper around CFUserClient. Runs a background event loop in a daemon thread — all methods block until complete. Use with for context management.

Methods

create_with_api_key(api_key: str, base_url: Optional[str] = None) -> SyncCFUserClient

Create a client instance with API key authentication.

Parameters:

  • api_key (str): Your CloudFactory API key
  • base_url (Optional[str]): Custom API base URL (default: production)

Returns: Configured SyncCFUserClient instance


download_project(project_id, space_id, destination, ...) -> DownloadSummary

Download all COCO annotations from a project with flexible filtering options. Blocks until complete.

All parameters are identical to CFUserClient.download_project.


close() -> None

Close HTTP clients and stop the background event loop. Called automatically when using with.


CFUserClient (async)

Async client for the CloudFactory AI Platform. All methods must be awaited; use async with for context management.

Architecture

The download process follows these steps:

  1. Fetch Batches: Retrieve batch metadata (ID → name mapping) from the Platform API
  2. Fetch Manifest: Query work items with optional filters (status defaults to "COMPLETED")
  3. Parallel Downloads: Use asyncio with semaphore to download annotations concurrently
  4. For Each Item:
    • Fetch annotation metadata from Platform API
    • Extract COCO results URL from annotation metadata
    • Generate signed download URL from Space API
    • Download file content with retry logic
    • Save to disk organized by batch name
  5. Return Summary: Aggregate statistics and per-item results

Methods

create_with_api_key(api_key: str, base_url: Optional[str] = None) -> CFUserClient

Create a client instance with API key authentication.

Parameters:

  • api_key (str): Your CloudFactory API key
  • base_url (Optional[str]): Custom API base URL (default: production)

Returns: Configured CFUserClient instance


async download_project(project_id, space_id, destination, ...) -> DownloadSummary

Download all COCO annotations from a project with flexible filtering options. Must be awaited.

Parameters:

  • project_id (str): The project ID to download
  • space_id (str): The space ID (required for generating signed URLs)
  • destination (str): Local directory path to save files
  • batch_ids (Optional[list[int]]): Filter by specific batch IDs (max 100). Downloads all if None
  • work_item_ids (Optional[list[str]]): Filter by specific work item IDs (UUID format). Downloads all if None
  • created_at_from (Optional[str]): Filter items created on or after this timestamp (ISO 8601 format, e.g., "2026-01-15T10:30:00Z")
  • created_at_to (Optional[str]): Filter items created on or before this timestamp (ISO 8601 format)
  • updated_at_from (Optional[str]): Filter items updated on or after this timestamp (ISO 8601 format)
  • updated_at_to (Optional[str]): Filter items updated on or before this timestamp (ISO 8601 format)
  • max_workers (int): Maximum concurrent downloads (default: 10)
  • limit (Optional[int]): Items per page when fetching the manifest (1–100, default: API default of 20)

Returns: DownloadSummary with statistics and detailed results

Raises:

  • httpx.HTTPStatusError: If API requests fail
  • OSError: If file system operations fail

async close() -> None

Close HTTP clients and cleanup resources. Must be awaited. Called automatically when using async with.


Models

DownloadSummary

Summary statistics for a download operation.

Field Type Description
total_items int Total number of work items processed
successful int Number of files successfully downloaded
failed int Number of files that could not be downloaded
results list[DownloadResult] Per-item details

DownloadResult

Result of a single work item download.

Field Type Description
item_id str ID of the work item
batch_id Optional[int] Batch ID the item belongs to
success bool Whether the download succeeded
file_path Optional[str] Path where file was saved (if successful)
error Optional[str] Error message (if failed)

Error Handling

The SDK includes comprehensive error handling:

Error Likely Cause
ValueError API key cannot be empty
HTTP 401 API key is invalid or expired
HTTP 404 Project ID or Space ID does not exist
OSError Destination directory permissions issue

Automatic Retries

Downloads automatically retry up to 3 times with exponential backoff (2-10 seconds) for:

  • Network errors and timeouts (httpx.HTTPError, httpx.TimeoutException)
  • All HTTP errors (including 4xx and 5xx status codes)

Retries apply only to the download phase (fetching files from signed URLs). API calls to fetch manifests, batches, and annotations do not have automatic retries.

Graceful Failures

If a download fails after retries:

  • Error is logged
  • Item is marked as failed in results
  • Download continues for remaining items
  • Summary includes failure details

Example Error Handling

import logging
from cf_ai_platform_client import SyncCFUserClient

logging.basicConfig(level=logging.INFO)

with SyncCFUserClient.create_with_api_key("MY_API_KEY") as client:
    try:
        summary = client.download_project(
            project_id="proj_abc123",
            space_id="space_456",
            destination="./downloads"
        )

        if summary.failed > 0:
            print(f"\n⚠️  {summary.failed} items failed to download:")
            for result in summary.results:
                if not result.success:
                    print(f"  - {result.item_id}: {result.error}")

    except Exception as e:
        print(f"❌ Download failed: {e}")
        raise

Requirements

  • Python 3.10 to 3.14 (actively supported versions)
  • Dependencies:
    • httpx >= 0.27.0 - HTTP client
    • pydantic >= 2.6.0 - Data validation
    • tqdm >= 4.66.0 - Progress bars
    • tenacity >= 8.2.0 - Retry logic

Development

Setup

This project uses uv for fast dependency management. The setup script installs uv with checksum verification for security:

# Clone the repository
git clone https://github.com/cloudfactory/cf-ai-platform-client-python.git
cd cf-ai-platform-client-python

# Run setup (installs uv with checksum verification)
./setup.sh --dev

Alternative uv installation methods:

If you prefer to install uv yourself:

# macOS (recommended)
brew install uv

# Using pipx
pipx install uv

# Using pip
pip install uv

# Then install dependencies
uv sync --all-extras

Security note: The setup script downloads a pinned uv release (v0.10.4) with SHA256 checksum verification to prevent supply-chain attacks. CI/CD workflows use the official astral-sh/setup-uv@v4 GitHub Action.

Running Tests

# Run all tests with coverage
uv run pytest

# Run with verbose output
uv run pytest -v

# Run specific test file
uv run pytest tests/test_client.py

# Generate HTML coverage report
uv run pytest --cov=src --cov-report=html

Code Quality

# Format code
uv run ruff format src tests

# Lint code
uv run ruff check src tests

# Type checking
uv run mypy src

# Run all checks
uv run ruff format src tests && uv run ruff check --fix src tests && uv run mypy src

Building and Publishing

# Build distribution packages
uv build

# Publish to TestPyPI (for testing)
uv publish --publish-url https://test.pypi.org/legacy/

# Publish to PyPI (production)
uv publish

Note: Publishing is automated via GitHub Actions. Push to main triggers the production release workflow.

License

MIT License - see LICENSE file for details.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

cf_ai_platform_client-0.1.2.tar.gz (79.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

cf_ai_platform_client-0.1.2-py3-none-any.whl (17.9 kB view details)

Uploaded Python 3

File details

Details for the file cf_ai_platform_client-0.1.2.tar.gz.

File metadata

  • Download URL: cf_ai_platform_client-0.1.2.tar.gz
  • Upload date:
  • Size: 79.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for cf_ai_platform_client-0.1.2.tar.gz
Algorithm Hash digest
SHA256 f352eb572475eb3bbaa2d4fca89d987ff245efa77267ee7ad9b8e9d8a6549985
MD5 e1eb8c4b7e20e94a674366e54a91bc22
BLAKE2b-256 8a644e745267a4804b59159af2963258064131c10a320389323e730482fe2f55

See more details on using hashes here.

Provenance

The following attestation bundles were made for cf_ai_platform_client-0.1.2.tar.gz:

Publisher: prod-release.yml on cloudfactory/cf-ai-platform-client-python

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file cf_ai_platform_client-0.1.2-py3-none-any.whl.

File metadata

File hashes

Hashes for cf_ai_platform_client-0.1.2-py3-none-any.whl
Algorithm Hash digest
SHA256 b395a1797e3f1ed08ec465b8a96710c815a3d313c705ea4cc775c708d820578f
MD5 e2c4230317dd60421511ebc568738ae7
BLAKE2b-256 7a9fbe2612922ba619e111d48827c8a1e3e85ffdc3922f86e5924e0f7e320fbc

See more details on using hashes here.

Provenance

The following attestation bundles were made for cf_ai_platform_client-0.1.2-py3-none-any.whl:

Publisher: prod-release.yml on cloudfactory/cf-ai-platform-client-python

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page