# MLB & NHL Sports Stats API (Official Data) (`teamkamkod/sport-stats-intel`) Actor

Teams, schedules, standings and rosters for MLB and NHL straight from the official league APIs - no API key, no login, no proxy. Deterministic flat rows for analytics, fantasy and AI agents.

- **URL**: https://apify.com/teamkamkod/sport-stats-intel.md
- **Developed by:** [Team Kamkod](https://apify.com/teamkamkod) (community)
- **Categories:**
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.40 / 1,000 stat-rows

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?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
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.
Actors are written with capital "A".

## 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.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## Sports Stats API — MLB & NHL (Official Data)

**Six datasets, two leagues, one actor.** Teams, schedules, standings, rosters
(with player bios), full season player stats and league leaders for **MLB** and
**NHL**, straight from the official league APIs (`statsapi.mlb.com`,
`api-web.nhle.com`, `api.nhle.com`) — **no API key, no login, no browser, no
proxy**. Deterministic flat rows that read cleanly as JSON or CSV — built for
fantasy models, betting analytics, dashboards, and AI agents.

#### Why this actor?

- **Two leagues, not one** — the only multi-sport official-API stats actor:
  MLB *and* NHL (teams, standings, skaters/goalies) under a single input.
- **One flat event** — every row (any dataset, any league) charges the same
  `stat-row`, no per-mode surprises, no run-start fee on top.
- **Full season player stats** — ~1 600 MLB hitting/pitching lines, ~1 000 NHL
  skater/goalie lines, canonical field names across both leagues.
- **Player bios included** — MLB roster rows carry birth date, city, height,
  weight, bats/throws and MLB debut date, not just a name and a jersey number.
- **Official source, updated live** — no scraping of third-party pages, no
  selector to break when a site redesigns.
- **Honest by design** — runs that return nothing cost nothing; NHL team
  identity documented (abbreviation, no numeric id on the official API).

### Datasets (per league, selectable)

| Dataset | Content |
|---|---|
| `teams` | Teams with id, name, city, division/conference (MLB 30 / NHL 32) |
| `schedule` | Games for one date (default today) with status + scores when played |
| `standings` | Division/conference standings: GP, W, L (+ OT, points for NHL), win %, streaks |
| `rosters` | All 30/32 teams — player id, name, position, jersey + **MLB player bios** |
| `player-stats` | Full season player stats: MLB hitting + pitching, NHL skaters + goalies |
| `leaders` | Top-N per stat (default 25, configurable 1-100): HR/AVG/RBI/SB/OBP/OPS, W/ERA/K/SV (MLB) — points/goals/assists/±/GWG, W/GAA/SHO (NHL). Categories selectable |
| `boxscores` | MLB only — per team-in-game: runs, hits, errors, RBI, LOB (one date) |

Rows are flat and carry `league`, `dataset`, plus season/id fields:

```json
{ "league": "MLB", "dataset": "standings", "season": "2026", "teamId": 119,
  "teamName": "Los Angeles Dodgers", "division": "NL West",
  "gamesPlayed": 138, "wins": 96, "losses": 42, "winPct": 0.696 }
```

```json
{ "league": "NHL", "dataset": "player-stats", "season": "20252026",
  "group": "skater", "playerId": 8478406, "playerName": "Connor McDavid",
  "abbreviation": "EDM", "points": 138, "goals": 42, "assists": 96 }
```

### Input

- `leagues` — MLB and/or NHL (default both)
- `datasets` — teams / schedule / standings / rosters / player-stats / leaders / boxscores
- `seasonsMlb` / `seasonsNhl` — **multi-season per run** (e.g. `["2024","2025","2026"]`, MLB back to 1876); NHL: rosters/player-stats/leaders per season, standings current only
- `mlbGameType` — R (default), S spring, E exhibition, A all-star, F wild card, D division series, L league championship, W world series, P postseason (standings/schedule)
- `mlbLeaderCategories` / `nhlLeaderCategories` — optional subsets (default all)
- `date` — schedule/boxscores date, YYYY-MM-DD (default today UTC)
- `leadersLimit` — players per stat for `leaders` (1-100, default 25)
- `maxItems` — hard cap on rows pushed and charged (default 20 000; excess dropped with a warning)

### Pricing

`stat-row` — **$0.003 / row pushed** — below single-sport equivalents on the
store for the same official-API data, with NHL and full season stats included
at no extra. No run-start fee, no minimum. Runs returning nothing cost nothing.
Infrastructure (HTTP-only, official endpoints) is near-zero, so the price holds
margin at any volume.

### Honest notes

- Official APIs are keyless but unofficial — endpoints can change; monitoring in place.
- NHL has no numeric team id on these endpoints: **team identity = abbreviation** (TOR, COL…).
- Off-season schedule dates legitimately return 0 rows for NHL.
- NBA is NOT in v1: its CDN blocks datacenter IPs (403 Akamai) — would need
  proxies, excluded by design.

### Roadmap

- v1.1 ✅: leaders + season player stats (MLB hitting/pitching, NHL skaters/goalies)
- v1.2 ✅: multi-seasons per run, MLB gameType, boxscores, selectable leader categories, maxItems cap, MLB roster player bios
- v1.3: NHL boxscores, NHL playoffs bracket, date-range player splits, more leagues whose official APIs stay keyless (gated 09/2026: NBA = 403 Akamai, WNBA = 403, AHL refused, EuroLeague DNS)

# Actor input Schema

## `leagues` (type: `array`):

Leagues to include (default: both).

## `datasets` (type: `array`):

Which datasets to pull per league and season. rosters = one API call per team; schedule/boxscores = one date (default today); boxscores is MLB-only in v1.

## `date` (type: `string`):

Schedule and boxscores use this date (default: today UTC).

## `seasonsMlb` (type: `array`):

One or more MLB seasons, e.g. \["2026"] or \["2024","2025","2026"] (historical data back to 1876).

## `seasonsNhl` (type: `array`):

One or more NHL season ids, e.g. \["20252026"]. Applies to rosters/player-stats/leaders; NHL standings are current season only.

## `mlbGameType` (type: `string`):

R = regular season (default), S = spring training, E = exhibition, A = all-star, F = wild card, D = division series, L = league championship, W = world series, P = postseason.

## `leadersLimit` (type: `integer`):

How many players per stat for the leaders dataset (1-100, default 25).

## `mlbLeaderCategories` (type: `array`):

Optional subset; default = all 10.

## `nhlLeaderCategories` (type: `array`):

Optional subset; default = all 8.

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

Hard cap on rows pushed (and therefore charged). Excess rows are dropped with a warning.

## Actor input object example

```json
{
  "leagues": [
    "MLB",
    "NHL"
  ],
  "datasets": [
    "teams",
    "schedule",
    "standings"
  ],
  "seasonsMlb": [
    "2026"
  ],
  "seasonsNhl": [
    "20262027"
  ],
  "mlbGameType": "R",
  "leadersLimit": 25,
  "maxItems": 20000
}
```

# Actor output Schema

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

One dataset item per row: teams, schedule, standings, rosters, player season stats, leaders or boxscores, tagged by league and season.

## `input` (type: `string`):

The input used for this run.

# 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("teamkamkod/sport-stats-intel").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("teamkamkod/sport-stats-intel").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 teamkamkod/sport-stats-intel --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,teamkamkod/sport-stats-intel"
        }
    }
}

```

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/1PyOLoKACxcO1Lrcd/builds/4mX27fZnxoWyuci7e/openapi.json
