Official Python client for the Live Tennis API — real-time tennis scores, players, market prices and model win-probability over REST and WebSocket.
Project description
livetennisapi
Official Python client for the Live Tennis API.
Real-time tennis scores, players, rankings, match-winner market prices and model win-probability — for ATP, WTA, Challenger and ITF, over REST and WebSocket.
Install
pip install livetennisapi # REST client + CLI
pip install "livetennisapi[all]" # + WebSocket feed and rich CLI tables
Use
from livetennisapi import LiveTennisAPI
with LiveTennisAPI(api_key="twjp_…") as client: # or set LIVETENNISAPI_KEY
for match in client.list_matches(status="live"):
print(match.tournament, match.p1.name, "vs", match.p2.name, match.score.sets)
Async is the same API, awaited:
from livetennisapi import AsyncLiveTennisAPI
async with AsyncLiveTennisAPI() as client:
match = await client.get_match(18953)
Command line
The package ships a livetennis command:
$ livetennis live
Live matches (3)
ID Tournament Rd Players Score
18953 ATP Wimbledon R16 *Alcaraz / Sinner 6-4 3-6 2-1 (40-30)
$ livetennis match 18953
$ livetennis players djokovic
$ livetennis watch --match 18953 # live WebSocket stream
Live score feed (ULTRA)
from livetennisapi import LiveScoreStream
with LiveScoreStream() as stream:
for update in stream:
print(update.match_id, update.score.sets)
Reconnects automatically with backoff and re-subscribes. Heartbeats are consumed internally, so you only see real score changes. It deliberately does not reconnect on a bad key or an insufficient tier — those raise immediately rather than retry forever.
Tiers
| BASIC | PRO | ULTRA | |
|---|---|---|---|
list_matches get_match get_match_score |
✅ | ✅ | ✅ |
search_players get_player list_fixtures list_completed_matches |
✅ | ✅ | ✅ |
list_match_events list_markets get_market_prices |
— | ✅ | ✅ |
get_match_analysis, win_probability_p1 / danger, WebSocket |
— | — | ✅ |
Calling above your tier raises UpgradeRequired, which tells you which tier you need:
from livetennisapi import UpgradeRequired
try:
client.get_match_analysis(18953)
except UpgradeRequired as exc:
print(exc.required_tier) # 'ULTRA'
Errors
| Exception | When |
|---|---|
Unauthorized |
401 — key missing, unknown, or disabled |
UpgradeRequired |
403 — valid key, tier too low (carries .required_tier) |
NotFound |
404 — no such resource, or no data yet |
RateLimited |
429 — carries .retry_after in seconds |
ServerError / ServiceUnavailable |
5xx |
APIConnectionError / APITimeoutError |
never reached the API |
All inherit from LiveTennisAPIError.
Requests retry automatically on 429 and 5xx only, honouring Retry-After
with exponential backoff and jitter. Other 4xx are never retried — a bad key or
an unentitled tier cannot start working, and retrying only burns rate limit.
Pagination
limit defaults to 50; the API rejects anything above 200. To walk everything —
paginate() clamps the page size for you:
for player in client.paginate("search_players", search="nadal"):
print(player.name)
Forward compatibility
The API ships additive changes within v1, so this client never rejects a
field it doesn't recognise. Unknown fields stay reachable:
match = client.get_match(18953)
match.raw["some_new_field"] # present if the server sent it
match.some_new_field # also works
That means a new server-side field is usable without upgrading this package.
The score shape (read this one)
games is player-major, not set-major:
score.games # [[6, 3, 2], [4, 6, 1]] -> 6-4, 3-6, 2-1
# ^p1 per set ^p2 per set
score.sets # [1, 1] -> one set each
score.server # 1 or 2
Indexing it the other way is the most common mistake made against this API, so there's a helper:
score.games_for_set(0) # (6, 4)
Configuration
LiveTennisAPI(
api_key="twjp_…", # or $LIVETENNISAPI_KEY
base_url=None, # or $LIVETENNISAPI_BASE_URL
timeout=30.0,
max_retries=2,
auth_header="bearer", # or "x-api-key"
)
Contributing
Issues and pull requests welcome at livetennisapi/livetennisapi-python.
pip install -e ".[dev]"
pytest -m "not contract" # unit tests, offline
LIVETENNISAPI_KEY=twjp_… pytest -m contract # verify against the live API
The contract tests assert that the live API's real responses match these models. If the API and the spec disagree, that's a bug worth reporting.
Licence
MIT — see LICENSE. Use of the API service is governed by the Terms of Service.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file livetennisapi-1.0.1.tar.gz.
File metadata
- Download URL: livetennisapi-1.0.1.tar.gz
- Upload date:
- Size: 27.2 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a05d04f52752a8a5e3631f8c488203eb3b3aa1886411e14977599d5c86530603
|
|
| MD5 |
1d82877ce7646554a78abe2cd2305421
|
|
| BLAKE2b-256 |
7a390c55313e78174d056c50c4f98164958ea953d0bc9033461c6c04a6aab302
|
Provenance
The following attestation bundles were made for livetennisapi-1.0.1.tar.gz:
Publisher:
publish.yml on livetennisapi/livetennisapi-python
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
livetennisapi-1.0.1.tar.gz -
Subject digest:
a05d04f52752a8a5e3631f8c488203eb3b3aa1886411e14977599d5c86530603 - Sigstore transparency entry: 2195514574
- Sigstore integration time:
-
Permalink:
livetennisapi/livetennisapi-python@b4fbcad04df85cf2225283a8526ed089b1b6a3e0 -
Branch / Tag:
refs/tags/v1.0.1 - Owner: https://github.com/livetennisapi
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@b4fbcad04df85cf2225283a8526ed089b1b6a3e0 -
Trigger Event:
release
-
Statement type:
File details
Details for the file livetennisapi-1.0.1-py3-none-any.whl.
File metadata
- Download URL: livetennisapi-1.0.1-py3-none-any.whl
- Upload date:
- Size: 24.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1915c64a92d3967ab1b3a0d47579623f72d612f00d14da0c5f676c0f49ac7e40
|
|
| MD5 |
05d3a2b91e4721e4dc0644e21f2b86a7
|
|
| BLAKE2b-256 |
6c40052bdd18ad88999509edb6e84ba4531f057b1acfcb96dde64258b1d54805
|
Provenance
The following attestation bundles were made for livetennisapi-1.0.1-py3-none-any.whl:
Publisher:
publish.yml on livetennisapi/livetennisapi-python
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
livetennisapi-1.0.1-py3-none-any.whl -
Subject digest:
1915c64a92d3967ab1b3a0d47579623f72d612f00d14da0c5f676c0f49ac7e40 - Sigstore transparency entry: 2195514579
- Sigstore integration time:
-
Permalink:
livetennisapi/livetennisapi-python@b4fbcad04df85cf2225283a8526ed089b1b6a3e0 -
Branch / Tag:
refs/tags/v1.0.1 - Owner: https://github.com/livetennisapi
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@b4fbcad04df85cf2225283a8526ed089b1b6a3e0 -
Trigger Event:
release
-
Statement type: