Skip to main content

By Your Side Python SDK

Zero-dependency Python client for the By Your Side Agent Outbound-Call API. Place objective-driven AI calls, poll for results, and verify webhooks using only the Python standard library.

Requires Python 3.8+. No third-party packages needed.


Quick start

Place a call and wait for the result

from byourside import Client

client = Client(api_key="bys_ak_YOUR_KEY")

# Place an outbound call with an objective
call = client.place_call(
    to="+14155550123",
    objective="Confirm the appointment for tomorrow at 2pm and ask if they need to reschedule.",
    fields=[
        {"name": "confirmed", "type": "boolean"},
        {"name": "new_time", "type": "string"},
    ],
)
print("Placed:", call["callId"], "status:", call["status"])

# Poll until the call reaches a terminal status (default timeout: 180s)
result = client.wait_for_call(call["callId"], timeout=180, interval=5)
print("Final status:", result["status"])
print("Extracted fields:", result.get("extracted"))

List recent calls

calls = client.list_calls(limit=10)
for c in calls:
    print(c["callId"], c["status"])

Get a specific call

call = client.get_call("call_abc123")
print(call)

Call statuses

Status Meaning
queued Call accepted, waiting to be placed
in_progress Call is active
completed Call finished normally (terminal)
no_answer Recipient did not pick up (terminal)
voicemail Reached voicemail (terminal)
declined Recipient declined the call (terminal)
failed Call could not complete (terminal)

wait_for_call returns once the status is one of the five terminal states.


Webhook verification

By Your Side sends a X-BYS-Signature header with each webhook delivery. Verify it before processing the payload.

Flask example

from flask import Flask, request, abort
from byourside import verify_webhook

app = Flask(__name__)
WEBHOOK_SECRET = "whsec_YOUR_SECRET"

@app.route("/webhook/bys", methods=["POST"])
def bys_webhook():
    sig = request.headers.get("X-BYS-Signature", "")
    raw_body = request.get_data(as_text=True)
    if not verify_webhook(sig, raw_body, WEBHOOK_SECRET):
        abort(400, "Invalid signature")
    payload = request.get_json()
    print("Call update:", payload["callId"], payload["status"])
    return "", 200

The signature format is t=<unix_seconds>,v1=<hex> where hex = HMAC-SHA256(secret, f"{t}.{raw_body}").

verify_webhook never raises. It returns False for invalid or expired signatures (default tolerance: 300 seconds).


Error handling

All API errors raise ByoursideError:

from byourside import Client, ByoursideError

client = Client(api_key="bys_ak_YOUR_KEY")
try:
    client.place_call(to="+19001234567", objective="Sell something")
except ByoursideError as e:
    print(e.code)    # e.g. "destination_blocked"
    print(e.status)  # HTTP status, or 0 for network/timeout errors
    print(str(e))    # Human-readable message

Common error codes:

Code Meaning
destination_blocked Destination not allowed (premium, IRSF, or unsupported country)
invalid_number Number must be E.164, e.g. +14155550123
to_required Missing destination number
objective_required Missing call objective
caller_id_not_owned Caller ID not on your account
rate_limited Rate limit reached, retry shortly
over_minute_cap Outbound usage limit reached
unauthorized Invalid or missing API key
not_found Call ID not found
placement_failed Carrier or trunk issue, retry shortly
store_error Temporary service error, retry shortly
network_error Could not reach the API
timeout wait_for_call deadline exceeded

Development

Clone the repo. No install step needed for local use: run tests from the sdks/python/ directory so that byourside/ is on the path automatically.

cd sdks/python
python3 -m unittest discover -s tests

Expected output: all tests pass (11 tests across errors, client, wait, and webhooks).

If your environment does not add CWD to the path automatically, use:

cd sdks/python
PYTHONPATH=. python3 -m unittest discover -s tests

Syntax check all source files:

python3 -m py_compile byourside/errors.py byourside/client.py byourside/webhooks.py byourside/__init__.py

Publishing to PyPI is deferred. Do not publish without explicit owner approval.

Metadata

Release files for byourside 0.1.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for byourside 0.1.0
File Size Uploaded Provenance Actions
byourside-0.1.0.tar.gz 7.8 kB Without provenance Details for byourside-0.1.0.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for byourside 0.1.0
File Interpreter ABI Platform Actions
byourside-0.1.0-py3-none-any.whl Python 3 none any Details for byourside-0.1.0-py3-none-any.whl

Total release size: 15.3 kB

Release files / byourside-0.1.0.tar.gz

Download URL byourside-0.1.0.tar.gz
Size 7.8 kB
Tags Source
SHA-256 checksum
How to use checksums
e08d2d3b6723277a899a2888a28be9d3f5ab0f25e7e5b0e1d93744e3c859f868
BLAKE2b-256 checksum
How to use checksums
dae7986000c393e16cdd584da19a7e249113cea4ea53722d22114000a712a436
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.14.5

Release files / byourside-0.1.0-py3-none-any.whl

Download URL byourside-0.1.0-py3-none-any.whl
Size 7.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
1339c511709cbec07c9835fbb0045b365c608d7ffea5cdf693597bc7250d19b7
BLAKE2b-256 checksum
How to use checksums
80b0f8b1f8791abae4d6b456a564719afe7bbfada7c3bd8d43e72984745c0153
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.14.5

Security for byourside 0.1.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.1.0 This release

2 release files No provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page