# Tennis Live Scores - ATP, WTA, Challenger & ITF (`crawlplant/tennis-live-scores`) Actor

Every tennis match in play right now: set and game score, who serves, status, ATP and WTA rank and Elo, with optional in-play odds from your country's bookmakers. Or any day's matches: today's scores, results and fixtures. ATP, WTA, Challenger and ITF. Works as an MCP tool for AI agents.

- **URL**: https://apify.com/crawlplant/tennis-live-scores.md
- **Developed by:** [CrawlPlant](https://apify.com/crawlplant) (community)
- **Categories:** Sports, AI
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $0.70 / 1,000 matches

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## Tennis Live Scores - ATP, WTA, Challenger & ITF

*Independent tool, not affiliated with, endorsed by or connected to Flashscore, Livesport, the ATP, the WTA, the ITF or any
bookmaker. It reads the public match data that flashscore.com shows to every visitor.*

**Every tennis match in play right now, one row per match.** ATP, WTA, Challenger and ITF singles and doubles with the
**set-by-set score, the live game score and who is serving**, the status ("Set 2", "Set 3 - Tiebreak"), both players'
**ranking and Elo rating**, and optional **in-play odds from the bookmakers of your country**. The default run lists **today's
matches**, with the live score of every match in play; **live** mode keeps only the matches in play, and any other day
gives its results or fixtures.

### Related runnable examples

Explore the same tennis research workflows in our example repository. These recipes currently call the broader Flashscore Tennis Scraper or Match Dataset Actor; they are companion examples, not direct calls to this specialized Actor.

- [Capture the current live scoreboard](https://github.com/CrawlPlant/examples/blob/main/docs/recipes/tennis-live-scoreboard.md)
- [Export yesterday’s completed tennis matches](https://github.com/CrawlPlant/examples/blob/main/docs/recipes/tennis-daily-matches.md)
- [Fetch the scheduled match list](https://github.com/CrawlPlant/examples/blob/main/docs/recipes/tennis-upcoming.md)

Follow the [Python setup and `.env` guide](https://github.com/CrawlPlant/examples/blob/main/docs/LIVE-QUICKSTART.md) with your own `APIFY_TOKEN`, or browse the [complete catalog](https://github.com/CrawlPlant/examples/blob/main/docs/CATALOG.md) and [AI assistant instructions](https://github.com/CrawlPlant/examples/blob/main/docs/AI-AGENTS.md). Actor runs follow Apify pricing; the quickstart explains per-run spending limits.

### Why this one

- **Live in seconds.** A live run returns every match in play with its current set score, game score and server: schedule
  it every few minutes for a scoreboard, an alert or a dataset of match flow.
- **Scores for any day too.** Today, yesterday, tomorrow or a past date; the whole day in one run.
- **All tours.** ATP, WTA, Challenger, WTA 125, ITF men and women, Davis Cup and Billie Jean King Cup ties.
- **Context on every row.** ATP / WTA rank and points, Elo rating and Elo win probability, and serve and return
  statistics once a match is under way.
- **Odds when you want them.** Switch on **Bookmaker odds** for in-play and pre-match prices, the best price per player
  with the bookmaker offering it, and the win probability without the margin. Off by default, so a plain run is cheapest.
- **Filters.** By tour, singles or doubles, player name or tournament name.
- **Safe to schedule.** Today's matches by default, finished and upcoming included, so a run always has something to show;
  in `live` mode a moment with no match in play returns 0 rows and a note in the log, never a failed run.
- **See it live.** Today's matches with each favourite by Elo and the Elo leaders of both tours, from the same database
  your runs read: [crawlplant.com/tennis-live-scores](https://crawlplant.com/tennis-live-scores/).

### What can you use it for?

- **Live score widgets and alerts**: current set and game score, who serves, a notification when a match goes to a tiebreak.
- **Betting and trading tools**: in-play odds next to the score, from the bookmakers of one country.
- **Fantasy and media sites**: today's results and tomorrow's order of play without maintaining your own scraper.
- **AI agents**: ask "who is playing right now?" and get JSON.

### Quick start

1. Click **Try for free** with the default input (today's matches with live scores for those in play, up to 50).
2. Narrow it with **Tours**, **Player name contains** or **Tournament name contains**, or switch **Mode** to live now for
   only the matches in play.
3. Download the table as CSV, Excel or JSON, or save the input as a **task** and schedule it every few minutes.

#### Copy to your AI assistant

Paste this into ChatGPT, Claude or any agent so it knows how to use the Actor:

```
crawlplant/tennis-live-scores on Apify: live tennis scores (ATP, WTA, Challenger, ITF). Input: mode (matches = a day's
matches, the default | live = matches in play now), dateFrom / dateTo (matches mode: today, yesterday, tomorrow, 2026-09-28, -3),
tours (atp, wta, challenger-men, challenger-women, itf-men, itf-women, teams, other), matchType (singles | doubles | all),
status (all | scheduled | live | finished), players / tournaments (name contains), includeStatistics, includeRankings,
includeOdds (default false) with oddsCountry (GB, DE, PL, US...), sortBy (tour | time), maxItems (default 50).
Row: matchId, url, date, startTime, tour, tournament, round, surface, status, statusText, isLive, player1Name, player2Name,
player1Rank, player2Rank, player1Elo, player2Elo, player1EloWinProbability, score, sets, currentGame {player1, player2,
serving}, winnerName, statistics, odds {player1Best, player2Best, player1Average, player2Average, ...}.
Price: $1.00 per 1,000 matches on the Free plan, plus $1.50 per 1,000 matches that carry odds.
```

### Ready-to-use examples

**1. Live tennis scores right now (up to 50 matches, $0.05)**

```json
{ "mode": "live" }
```

**2. Today's ATP and WTA singles scores (up to 300 matches, $0.30)**

```json
{ "mode": "matches", "tours": ["atp", "wta"], "maxItems": 300 }
```

**3. One tournament's matches of the last three days (up to 200 matches, $0.20)**

```json
{ "mode": "matches", "dateFrom": "-3", "dateTo": "today", "tournaments": ["Paris Masters"], "maxItems": 200 }
```

**4. Live ATP and WTA matches with in-play odds from UK bookmakers (up to 50 matches, $0.13)**

```json
{ "mode": "live", "tours": ["atp", "wta"], "includeOdds": true, "oddsCountry": "GB" }
```

**5. Live matches of one player, ordered by start time (a few matches, under $0.01)**

```json
{ "mode": "live", "players": ["Sinner"], "sortBy": "time" }
```

### How to…

#### Get live tennis scores

`mode: "live"` (example 1) returns every match in play: `score` (sets), `currentGame` (points and who serves),
`statusText` and `isLive`. Schedule the task every few minutes to keep a scoreboard or a dataset current. The default
`mode: "matches"` returns all of today's matches, with the same live fields on those in play.

#### Get today's tennis results

`mode: "matches"` returns the matches of the days you pick. Add `"status": "finished"` for results only or
`"status": "scheduled"` for the order of play (example 2).

#### Follow one tournament or one player

`tournaments` keeps matches whose tournament name contains any of the words (example 3); `players` keeps matches of a
player by name (example 5).

### Input options

| Option | Default | Description |
|---|---|---|
| `mode` | `matches` | `matches` (a day's matches) or `live` (in play now) |
| `dateFrom`, `dateTo` | today | Scores by day: first and last day (UTC), e.g. `yesterday`, `2026-09-28`, `-3` |
| `tours` | all | `atp`, `wta`, `challenger-men`, `challenger-women`, `itf-men`, `itf-women`, `teams`, `other` |
| `matchType` | `singles` | `singles`, `doubles`, `all` |
| `status` | `all` | `all`, `scheduled`, `live`, `finished` (scores by day) |
| `players` | `[]` | Player name contains, e.g. `Sinner` |
| `tournaments` | `[]` | Tournament name contains, e.g. `US Open`, `Challenger` |
| `includeStatistics` | `true` | Serve and return statistics (included in the price) |
| `includeRankings` | `true` | ATP / WTA rank and points of each player (included in the price) |
| `includeOdds` | `false` | Bookmaker odds, charged per match that has them |
| `oddsCountry` | `GB` | Bookmakers licensed in this country |
| `sortBy` | `tour` | `tour` (ATP first, then WTA...) or `time` |
| `maxItems` | `50` | Maximum matches in total |

### Output fields

| Field | Description |
|---|---|
| `matchId`, `url` | Flashscore's match id and page |
| `date`, `startTime` | Day (UTC) and start time (ISO) |
| `tour`, `tournament`, `round`, `surface` | `atp`, `wta`, `challenger-men`...; "Final", "Semi-finals", "Q1"; hard / clay / grass / carpet |
| `status`, `statusText`, `isLive` | scheduled, live, finished, retired, walkover...; "Set 2", "Set 3 - Tiebreak" |
| `player1Name`, `player2Name`, `player1Rank`, `player2Rank` | Both sides and their ATP / WTA singles rank |
| `score`, `sets`, `currentGame` | Set-by-set score, each set with tiebreak points, the game in progress and who serves |
| `player1Elo`, `player2Elo`, `player1EloWinProbability` | Elo before the match and the win probability it gives |
| `statistics` | Serve and return statistics of the match so far |
| `odds` | With Bookmaker odds: best and average prices, the bookmaker offering each, win probability without the margin |
| `scrapedAt`, `source` | When the run read it; `live` = read from Flashscore in the run |

### How much does tennis live score data cost?

Pay per result: platform usage is included. One price per match, statistics and rankings included; odds are charged only
on matches that have them, and only when you switch them on.

| Event | No discount (Free plan) | Bronze (Starter) | Silver (Scale) | Gold (Business) |
|---|---|---|---|---|
| Match (per 1,000) | $1.00 | $0.90 | $0.80 | $0.70 |
| Bookmaker odds (per 1,000) | $1.50 | $1.35 | $1.20 | $1.05 |
| Actor start (per run) | $0.00005 | $0.00005 | $0.00005 | $0.00005 |

| Example on the Free plan | Rows | Cost |
|---|---|---|
| Default run: today's matches | up to 50 | ~$0.05 |
| Live ATP and WTA with odds | up to 50 + 50 with odds | up to ~$0.13 |
| A busy day, every tour | 300-450 | ~$0.30-0.45 |

Set a **maximum cost per run** in the run options to stop a large run at your budget.

### Run it through the API

JavaScript:

```js
import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: 'YOUR_TOKEN' });
const run = await client.actor('crawlplant/tennis-live-scores').call({ mode: 'live', tours: ['atp', 'wta'] });
const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items.length, items[0]);
```

Python:

```python
from apify_client import ApifyClient
client = ApifyClient("YOUR_TOKEN")
run = client.actor("crawlplant/tennis-live-scores").call(run_input={"mode": "matches", "tours": ["wta"], "status": "finished"})
for row in client.dataset(run["defaultDatasetId"]).iterate_items():
    print(row["tournament"], row["player1Name"], row["player2Name"], row["score"])
```

### Use with AI agents

The Actor works as a tool in the [Apify MCP server](https://mcp.apify.com) for Claude, ChatGPT, Cursor and others:

```
https://mcp.apify.com?tools=crawlplant/tennis-live-scores
```

Try *"who is playing on Centre Court right now, and what is the score?"*.

**Use it when** you need the scores of matches in play or of one day.

**Not for** a player's career or a long range of past results (use [Tennis Match History](https://apify.com/crawlplant/tennis-match-history)).

### More tennis data

- [Flashscore Tennis Scraper](https://apify.com/crawlplant/flashscore-tennis): every match of any day with odds from about
  20 bookmakers, head-to-head, form, rankings, player statistics and Elo lists.
- [Tennis Match History](https://apify.com/crawlplant/tennis-match-history): a player's whole career, match by match, with Elo and serve statistics.
- [ATP & WTA Tennis Rankings](https://apify.com/crawlplant/tennis-rankings): the current lists, every weekly list back to 1973 (ATP) and 2001 (WTA), and the player lists.
- [Tennis Odds Dataset](https://apify.com/crawlplant/tennis-odds-dataset): closing odds with results and Elo, in tennis-data.co.uk's columns.
- [ATP & WTA Tennis Match Dataset](https://apify.com/crawlplant/tennis-match-dataset): whole seasons in Jeff Sackmann's CSV columns.

### FAQ

#### How fresh is a live run?

It reads the live feed when it starts: the scores are as current as a Flashscore page opened at that second.

#### What if nothing is in play?

A live run gives 0 rows and a note in the log; the run still succeeds, so a schedule keeps going.

#### Does it include doubles?

Yes, `matchType: "doubles"` or `"all"`; both players of each pair are in the row.

#### Is it legal?

The data is public sporting results read without logging in, at a polite pace. How you use and publish them is your
responsibility, so check the source's terms for your use case.

Questions, a missing field or a source you need? Open an issue on this Actor: we reply within a day. If it saved you time, a short review helps others find it.

### Privacy

The data is about professional players' public sporting results. Each run sends the developer anonymous feature-usage
statistics (the options used, never the players you asked for); your Apify account id is replaced by a one-way hash.

# Actor input Schema

## `mode` (type: `string`):

live = every match in play right now: set and game score, who serves, in-play odds (a moment with nothing in play returns 0 rows and a note, never an error); matches = every match of the days you pick (today by default, any past day): results, fixtures and scores, with Elo, rankings and statistics.

## `dateFrom` (type: `string`):

Scores by day: the first day, in UTC. today, yesterday, tomorrow, a date like 2026-09-28, or an offset like -3 (three days ago) or +1. Ignored in live mode.

## `dateTo` (type: `string`):

Scores by day: the last day, inclusive, same formats as From day. Empty = only the From day. Example: From -7 and To today = the last 8 days. Ignored in live mode.

## `tours` (type: `array`):

Keep only these tours. Empty = all. challenger-women is the WTA 125 level; teams = Davis Cup, Billie Jean King Cup, Laver Cup ties; other = exhibitions, juniors and the rest.

## `matchType` (type: `string`):

singles (default), doubles (includes mixed doubles), or all (also team ties).

## `status` (type: `string`):

Scores by day: all, scheduled (not started, delayed, postponed), live (in play), finished (including retired, walkover and awarded). Live mode always returns matches in play.

## `players` (type: `array`):

Keep matches with a player whose name contains any of these, case-insensitive (Flashscore writes names as "Sinner J."): Sinner, Swiatek. A player id also works.

## `tournaments` (type: `array`):

Keep matches whose tournament name or category contains any of these, case-insensitive, e.g. Beijing, US Open, W100, Challenger.

## `includeStatistics` (type: `boolean`):

Serve and return statistics for matches that started: aces, double faults, 1st serve %, points won on 1st / 2nd serve, break points saved and converted, service and return games won, for the match and each set. Included in the base price.

## `includeRankings` (type: `boolean`):

Current ATP / WTA singles rank and points of each player (singles matches). Two small requests per list per run.

## `includeOdds` (type: `boolean`):

Match-winner odds of each bookmaker (in-play for live matches), best and average price, win probability without the bookmaker margin, and a link to each bookmaker. Charged per match that has odds (see Pricing); off by default.

## `oddsCountry` (type: `string`):

Used with Bookmaker odds. Bookmakers differ by country (licences). Two-letter code: GB (about 20 bookmakers), DE, PL, IT, ES, FR, US, AU, NG and others.

## `sortBy` (type: `string`):

tour = ATP first, then WTA, Challenger, ITF, each by start time; time = by start time only. Players mode is always newest first.

## `maxItems` (type: `integer`):

Maximum matches to return, counted after the filters. A busy moment has 100-200 matches in play; a busy day 300-450 singles matches across all tours.

## Actor input object example

```json
{
  "mode": "matches",
  "dateFrom": "today",
  "tours": [],
  "matchType": "singles",
  "status": "all",
  "players": [],
  "tournaments": [],
  "includeStatistics": true,
  "includeRankings": true,
  "includeOdds": false,
  "oddsCountry": "GB",
  "sortBy": "tour",
  "maxItems": 50
}
```

# Actor output Schema

## `results` (type: `string`):

No description

## `summary` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {};

// Run the Actor and wait for it to finish
const run = await client.actor("crawlplant/tennis-live-scores").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {}

# Run the Actor and wait for it to finish
run = client.actor("crawlplant/tennis-live-scores").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{}' |
apify call crawlplant/tennis-live-scores --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,crawlplant/tennis-live-scores"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/QazyDIAmMbQ3rlbp6/builds/IyCladPrsDNwdDslO/openapi.json
