message.comDevelopers

Python SDK Planned

Idiomatic Python wrapper for the message.com REST API. Pythonic naming (snake_case), typed dataclasses, sync and async clients, retries with exponential backoff. Targets Python 3.10+ and is type-checked with mypy strict.

Scheduled for Q2 2026. The underlying REST endpoints are already live and stable, so backend integrations can be built today against raw HTTP. See the REST API conventions for the manual approach.

Installation

The package supports CPython 3.10 through 3.13 plus PyPy 3.10. We avoid native dependencies so wheels are platform-agnostic.

Terminal
pip install message-com
# or, if you use uv
uv pip install message-com
# poetry
poetry add message-com

Initialise the client

Construct a single client per process. The client is thread-safe and connection-pooled. For high-throughput backends, share one instance across workers.

app.py
import os
from message_com import Message

msg = Message(api_key=os.environ["MESSAGE_API_KEY"])

Sync visitors

The most common backend task is mirroring your customer table into the workspace visitor list. The SDK exposes an idempotent visitors.upsert that keys on external_id first, then falls back to email.

signals.py
# Upsert a visitor on a Django signal
msg.visitors.upsert(
    email="[email protected]",
    external_id="crm-4567",
    name="Alice Johnson",
    attributes={"plan": "pro", "mrr": 99},
)

Create tickets

Tickets are conversations where channel = "ticket". The helper hides that detail. A reply on the resulting ticket sends as email through your configured outbound domain.

tasks.py
# Open a ticket from a Celery task
msg.tickets.create(
    visitor_email="[email protected]",
    subject="Auto-detected failed payment",
    body="Stripe charge ch_xyz failed. Reach out within 4h.",
    tags=["billing", "auto-created"],
)

Async client

The async variant exposes the same surface using httpx under the hood. Use it from FastAPI, Starlette, or any asyncio runtime.

stream.py
import asyncio
from message_com import AsyncMessage

async def main():
    async with AsyncMessage(api_key="msg_live_...") as msg:
        async for conv in msg.conversations.stream(status="open"):
            print(conv.id, conv.subject)

asyncio.run(main())

Framework integrations

The Python SDK ships first-party adapters for the major frameworks. These thin wrappers handle settings discovery, lifecycle hooks, and error propagation.

  • Django. Add to INSTALLED_APPS, run python manage.py message_sync to backfill, then point your post_save signals at the helper.
  • Flask. MessageFlask(app) binds the client to app.extensions and reads config from app.config.
  • FastAPI. Use the dependency-injection helper to get a per-request handle.

Retries and timeouts

The client retries on 429 and 5xx responses with jittered exponential backoff, capped at five attempts. You can override the retry policy per call or globally on the constructor.

Common pitfalls

  • Do not call from request handlers without timeouts. The default network timeout is 30s. Set timeout=5 on hot paths.
  • Use external_id for stable identity. Visitors change emails; primary keys do not.
  • Keep one client per process, not per request. The HTTP connection pool is the expensive part.