Skip to main content
Glama
Archers007

Liquipedia MCP

by Archers007
README.md
# Liquipedia MCP

A [Model Context Protocol](https://modelcontextprotocol.io) server that exposes
the [Liquipedia](https://liquipedia.net) **v3 esports API** β€” matches, teams,
players, tournaments, placements, and standings β€” as MCP tools any AI client
(Claude Desktop, Cursor, pi, …) can call.

It talks to the Liquipedia v3 REST API (`https://api.liquipedia.net/api/v3`)
using the `Authorization: Apikey <key>` scheme, plus the MediaWiki action API
for raw page wikitext. Requests are serialized and rate-limited to respect
Liquipedia's [API terms of use](https://liquipedia.net/api-terms-of-use).

> **πŸ”‘ Bring your own API key.** This server ships with **no** credentials.
> Every user must supply their own Liquipedia v3 API key β€” request one via the
> [Liquipedia API terms page](https://liquipedia.net/api-terms-of-use).

## Tools

| Tool | What it does |
|------|--------------|
| `query` | Low-level access to any datapoint (`match`, `team`, `player`, `tournament`, `placement`, `standingsentry`, `transfer`, `teamtemplate`, `squadplayer`, `series`, `company`, `externalmedialink`). Full `conditions` / `order` / `query` control. |
| `list_matches` | Matches (schedules + results) for a wiki. Filter by `opponent`, `tournament`, `date`. |
| `list_teams` | Teams for a wiki. Filter by `name`, `region`, `location`. |
| `list_players` | Players for a wiki. Filter by `id` (handle), `team`, `nationality`. |
| `list_tournaments` | Tournaments for a wiki. Filter by `name`, `startdate`, `organizer`. |
| `list_placements` | Tournament placements/results. Filter by `opponentname`, `tournament`. |
| `list_standings` | Ranked standings / points table for a tournament (great for battle-royale like Apex/ALGS, PUBG, Fortnite). Returns teams **sorted by placement with points**, using the latest round snapshot. Pass the tournament page name. |
| `get_wikitext` | Raw wikitext of one or more pages via the MediaWiki API (no key needed). |

### Common parameters

- **`wiki`** β€” the Liquipedia wiki to query: `valorant`, `counterstrike`,
  `dota2`, `leagueoflegends`, `rocketleague`, `apexlegends`, `rainbowsix`,
  `halo`, `smash`, `fighters`, `starcraft2`, … Pipe-separate for multiple:
  `valorant|counterstrike`.
- **`conditions`** β€” raw Liquipedia condition syntax, `[[field::value]]` joined
  by `AND` / `OR`, e.g. `[[opponent::Sentinels]] AND [[date::>2024-01-01]]`.
  The convenience tools' typed filters are merged (AND) with this.
- **`query`** β€” comma-separated projection of fields to return, e.g.
  `pagename,date,tournament`.
- **`limit`**, **`offset`**, **`order`** (e.g. `date DESC`).

## Setup

```bash
pnpm install            # or: npm install
cp .env.example .env    # then set LIQUIPEDIA_API_KEY to YOUR key
```

You need your **own** Liquipedia v3 API key. Request one via the
[Liquipedia API terms page](https://liquipedia.net/api-terms-of-use), then put
it in `.env` (or pass it via the MCP client's `env`, see below). Also set
`LIQUIPEDIA_USER_AGENT` to identify your app + a contact, as the terms require.

| Variable | Default | Description |
|----------|---------|-------------|
| `LIQUIPEDIA_API_KEY` | β€” | v3 API key (required for structured tools; `get_wikitext` works without). |
| `LIQUIPEDIA_USER_AGENT` | `LiquipediaMCP/1.0 (…)` | Identifying UA sent on every request (required by ToS). |
| `LIQUIPEDIA_MIN_INTERVAL_MS` | `2000` | Minimum gap between requests (rate limiting). |
| `LIQUIPEDIA_TIMEOUT_MS` | `12000` | Per-request timeout. |
| `LIQUIPEDIA_RETRIES` | `1` | Retries on timeout / 429. |
| `LOG_LEVEL` | `info` | `silent`/`error`/`warn`/`info`/`debug` (logs go to **stderr**). |

## Run

The server speaks MCP over **stdio** β€” an MCP client launches it as a subprocess.

```bash
pnpm start          # node src/index.js
pnpm run inspect    # open the MCP Inspector UI
node scripts/smoke.mjs   # end-to-end check: lists tools + runs a real query
```

## Add to an MCP client

**Claude Desktop** / **Cursor** (`claude_desktop_config.json` or `.cursor/mcp.json`):

```json
{
  "mcpServers": {
    "liquipedia": {
      "command": "node",
      "args": ["/absolute/path/to/LiqMcp/src/index.js"],
      "env": {
        "LIQUIPEDIA_API_KEY": "your-own-key-here",
        "LIQUIPEDIA_USER_AGENT": "MyApp/1.0 (you@example.com)"
      }
    }
  }
}
```

Or run it straight from GitHub without cloning (Node β‰₯20):

```json
{
  "mcpServers": {
    "liquipedia": {
      "command": "npx",
      "args": ["-y", "github:Archers007/LiqMcp"],
      "env": { "LIQUIPEDIA_API_KEY": "your-own-key-here" }
    }
  }
}
```

If you leave `LIQUIPEDIA_API_KEY` out of `env`, the server reads it from a
`.env` in the working directory. **The key is always supplied by you** β€” none
is bundled with the server.

## Example prompts

- "Use liquipedia to list Shopify Rebellion Gold's upcoming valorant matches."
- "What tournaments are on the counterstrike wiki with the biggest prize pools?"
- "Get Sentinels' team info from the valorant wiki (name, region, logo)."
- "Fetch the wikitext infobox (section 0) for the 'TenZ' page on the valorant wiki."

## How it works

```
MCP client ──stdio──> src/index.js (McpServer, 7 tools)
                            β”‚
                            β–Ό
                     src/client.js  ── serialized + rate-limited ──> Liquipedia v3 API
                            β”‚                                          (Apikey auth)
                            └───────────────────────────────────────> MediaWiki action API
                                                                       (wikitext, no key)
```

- **`src/config.js`** β€” env-driven config (key, UA, timeouts, rate limit).
- **`src/client.js`** β€” `LiquipediaClient`: query builder, single-flight rate
  limiter, timeout + retry, 429 handling.
- **`src/index.js`** β€” MCP server: tool schemas (zod), condition builder,
  error mapping.

## Notes

- The Liquipedia API is unofficial/unstable and **rate-limited** β€” requests are
  serialized with a minimum interval; heavy use may still be throttled (429).
- Data is CC-BY-SA; **attribute Liquipedia** on anything you render from it.
- Not affiliated with or endorsed by Liquipedia / Team Liquid.

TDQS

A3.7/5.0

Scored across 8 tools

Disambiguation5/5

Each tool targets a distinct entity or operation (wikitext, matches, placements, players, standings, teams, tournaments, generic query), with clear descriptions that differentiate them. No obvious overlap.

Naming Consistency3/5

Most tools use 'list_' prefix for fetching lists, but 'get_wikitext' uses 'get_' and 'query' is a bare verb. This inconsistency in naming convention could cause confusion about the action being performed.

Tool Count4/5

8 tools is a reasonable number for an esports wiki server, covering major entities. Not too few or too many, but a few more specialized tools could be added without bloat.

Completeness5/5

The tool set covers the main entities (matches, players, teams, tournaments, standings, placements) plus raw wikitext retrieval and a generic query tool for any other datapoint, ensuring no obvious gaps.

Maintenance

ActivityInactive
ResponsivenessNo issues