Skip to main content

meterspw-sdk

Python client for Meter-SPW — deterministic LLM routing with metered savings.

You bring your own provider keys. Meter-SPW routes each prompt to the cheapest model that can answer it, caches what repeats, and meters what it saved.

pip install meterspw-sdk

Zero runtime dependencies — the default transport is urllib from the standard library.

Use

from meterspw import MeterSpwClient

with MeterSpwClient() as spw:            # key from ROUTER_API_KEY
    out = spw.relay(
        "Summarise this contract in three bullets.",
        model="claude-sonnet-5",
        max_tokens=2000,
    )
    print(out.content)
    print(out.model_used)                # what ACTUALLY answered
    print(out.savings.usd)               # what that saved you

model is what you want; model_used is what answered. The difference is the product.

Attachments

out = spw.relay_multipart(
    "Summarise the attached report.",
    model="claude-sonnet-5",
    max_tokens=2000,
    files=["report.pdf"],
)

Know where you stand

b = spw.balance()
print(b.usd, b.accrued_micro_usd, b.remaining_usd)
if b.passthrough:
    print("credit exhausted — calls still work, but nothing is being routed")

Check passthrough. At zero credit the router degrades to a transparent proxy: your calls keep succeeding, with no routing, no cache and no savings. Nothing fails, which is exactly why it is easy to miss.

Three numbers, because two books. usd is the ledger. accrued is this period's fees, which have not been taken yet — they settle at the monthly close. remaining is what you should plan against.

Your receipts

rows = spw.verdicts(window="7d", q="haiku")      # the last 7 days, searched

window is one of 30m 1h 6h 12h 24h 7d 4w 12m (a period ending now); q matches the decision, the requested model and the served model. The router applies both, so the same two values count and export exactly these rows:

curl -H "Authorization: Bearer $ROUTER_API_KEY" \
  "https://spw.scitechsolutions.ai/v1/verdicts/count?window=7d&q=haiku"
curl -H "Authorization: Bearer $ROUTER_API_KEY" -o verdicts-7d.csv \
  "https://spw.scitechsolutions.ai/v1/verdicts.csv?window=7d&q=haiku"

The export is refused, with the count, when more than 200 000 rows match — narrow the window or the search.

Long requests

A proxy between you and the router closes a connection that stays silent for about 100 seconds, and the router is silent until the verified answer exists. So relay() asks for keep-alive delivery: the router answers within a second, keeps the line warm every 15 seconds while the model works, and delivers the whole answer at the end — the same result, nothing to change on your side.

timeout bounds silence on the line, not the whole call. A long answer is bounded by the router's own request limit (the operator's ROUTER_REQUEST_TIMEOUT_SECS), not by this number.

Over raw HTTP, send the header yourself and read the last data: line:

curl -N -X POST https://spw.scitechsolutions.ai/v1/relay \
  -H "Authorization: Bearer $ROUTER_API_KEY" \
  -H "Accept: text/event-stream" \
  -H "Content-Type: application/json" \
  -d '{"prompt": "Summarise this contract in three bullets.", "model": "claude-sonnet-5", "max_tokens": 2000}'
# -N is optional: curl prints each line as it arrives instead of all at the end.
: keep-alive          ← every 15 s while the model works
event: result
data: {"decision": "relayed", "model_used": "…", "content": "…", "verdict_id": "…", "latency_ms": 1840, …}

An event: error line with {"status": 502, "error": "…"} takes the place of result if the router fails late. /v1/relay-multipart takes the same header. Without it the reply is one JSON body — and a call longer than about 100 seconds dies at the proxy.

Errors

Exception When Retry?
AuthError 401/403 — key wrong or revoked no
RateLimited 429 yes, honours Retry-After
UploadCapacityFull 503 — upload slots full yes, honours Retry-After
Exhausted 502 — the router spent every lever no
TransportError never reached the server yes

Exhausted is not retryable on purpose. The router already climbed the model ladder, repaired and re-called before answering — each of those attempts billed your provider key. Asking again spends the same levers for the same failure. The message names what it tried.

Retries use exponential backoff with deterministic jitter and a wall-clock budget, and never extend past your own deadline. Configure with RetryPolicy.

Configuration

ROUTER_API_KEY your Meter-SPW key (or pass api_key=)
ROUTER_BASE_URL defaults to https://spw.scitechsolutions.ai

The SDK never sees a provider key. Those are stored once in the dashboard and used by the router on your behalf — the only credential here spends credit, not inference.

Support

support@scitechsolutions.ai — quote RelayResult.verdict_id or the request_id from an error and we can find the exact call.


© S&T Integrated Solutions, LLC — MIT licensed.

Download files

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

Source Distribution

meterspw_sdk-0.2.0.tar.gz (28.0 kB view details)

Uploaded Source

Built Distribution

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

meterspw_sdk-0.2.0-py3-none-any.whl (25.2 kB view details)

Uploaded Python 3

File details

Details for the file meterspw_sdk-0.2.0.tar.gz.

File metadata

  • Download URL: meterspw_sdk-0.2.0.tar.gz
  • Upload date:
  • Size: 28.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for meterspw_sdk-0.2.0.tar.gz
Algorithm Hash digest
SHA256 896a85e12b361ea0e00bbbd685a2a9a5fb62ef4d7911b49cfa327da1c8951cf7
MD5 d205ba580300fd9643d3cdd3a82b4190
BLAKE2b-256 f92c7863d5d7496a2389cb9d8f9f7c2b11564b32032c4198c4eafb936a8d761f

See more details on using hashes here.

Provenance

The following attestation bundles were made for meterspw_sdk-0.2.0.tar.gz:

Publisher: sdk-python-publish.yml on johndo0277/llm-router

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

File details

Details for the file meterspw_sdk-0.2.0-py3-none-any.whl.

File metadata

  • Download URL: meterspw_sdk-0.2.0-py3-none-any.whl
  • Upload date:
  • Size: 25.2 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for meterspw_sdk-0.2.0-py3-none-any.whl
Algorithm Hash digest
SHA256 9dfed3f8590ae302f88cf61fe096dd355069472756966889cd10421be6df717d
MD5 0a45de02f6c5cb3d746b57bb9dce13a1
BLAKE2b-256 c2854c81f4a73eb59b64f083506c433eea7667f642a50328bd491ec11166c2f0

See more details on using hashes here.

Provenance

The following attestation bundles were made for meterspw_sdk-0.2.0-py3-none-any.whl:

Publisher: sdk-python-publish.yml on johndo0277/llm-router

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

Release history Release notifications | RSS feed

This release

0.2.0 This release

2 files

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