fluxchat/sdk

SDK · Stable

Python SDK

v0.3.0 · Stable

Official FluxChat SDK for Python. Works with Django, FastAPI, Flask, and plain scripts. Typed dataclasses, httpx under the hood.

SourceContributed by @benjaminmugangu — Python SDK

Installation

terminal
pip install fluxchat

Create a client

The base URL defaults to https://api.fluxchat-corp.com/api/v2 — production. Pass it explicitly to target dev.

client.py
import os
from fluxchat import FluxChat

client = FluxChat(api_key=os.environ["FLUXCHAT_API_KEY"])

ask()

Send a message and get the assistant's reply. Pass context to inject real-time data the bot treats as a priority source of truth, above the knowledge base. A sessionId keeps multi-turn history without persisting a conversation.

ask.py
response = client.ask(
    "Quels sont vos horaires ?",
    context="Utilisateur : Alice, Plan : Pro",
    session_id=my_session_id,
)
print(response.reply)
print(response.conversation_id)

Human handoff (support thread)

When the bot can't help, hand the visitor to a human. This creates a real support ticket in the organization's dashboard — and unlike a contact form, the conversation stays open in the same thread: the visitor polls it, the agent answers into it.

handoff.py
# 1. Hand off. With the same session_id you pass to ask(), everything the
#    bot already said is copied into the ticket — the agent picks up mid-flow.
ticket = client.support.escalate(
    name="Jordan Mbeki",
    email="jordan@example.com",
    message="Mon virement est bloqué depuis hier.",
    session_id=my_session_id,
)

# 2. Follow the thread. Keep (ticket_id, email): the e-mail is what proves
#    the ticket is theirs — no account, no token.
thread = client.support.thread(ticket.ticket_id, "jordan@example.com")
for m in thread.messages:
    print(m.role, m.content)          # bot | visitor | agent
if thread.agent_connected:
    print(f"{thread.agent_name} is answering")

# 3. Let them reply into it.
client.support.reply(ticket.ticket_id, "jordan@example.com", "La référence est 4821.")
  • Ownership is the e-mail. A wrong e-mail and a non-existent ticket both return 404, deliberately — a guessed ticket id reveals nothing. The lookup is also scoped to the organization behind your API key.
  • Polled, not pushed. There is no socket on the public surface. 5s is the cadence the official widget uses and what the route's limits are sized for: 60 reads/min, 30 replies/min, 5 escalations/min.
  • Statuses: open → in_progress → resolved → closed. A reply to a resolved ticket reopens it; a closed one refuses the write (403) rather than swallowing a message nobody will read.
  • Requires the organization's plan to include supportTickets (403 otherwise).

Knowledge base

Create, update and delete articles. Write operations need a key with the bot:write scope, or an admin JWT.

knowledge.py
kb = client.knowledge

article = kb.create(
    title="Délais de livraison",
    content="Livraison sous 48 h en RDC.",
    keywords=["livraison", "délai"],
)
kb.update(article.id, content="Livraison sous 24 h à Kinshasa.")
kb.delete(article.id)

Errors

Every failure is typed: an API error carries the HTTP status and the server's message, a network error wraps the transport failure, and a config error is raised before any request leaves.

errors.py
from fluxchat import FluxChatApiError, FluxChatNetworkError, FluxChatConfigError

try:
    client.support.thread(ticket_id, "someone@else.com")
except FluxChatApiError as err:
    # 404 both when the ticket does not exist and when the e-mail does not
    # own it — deliberately indistinguishable.
    print(err.status_code, err)
except FluxChatNetworkError as err:
    print("transport failure:", err)
except FluxChatConfigError as err:
    print("bad client configuration:", err)