DocumentationCompetitions
Volleyball fixtures and results by competition
GET/v1/competitions/{id}/matches
A competition's matches, every round and pool, filtered by status. Use it for a fixture list, a results page or a whole tournament at once.
Parameters
All optional. Days you can read depend on your plan: the free key reads today and yesterday, Live the last 30 days, Archive and Complete every season since 2001.
| Name | Type | What it does | Example |
|---|---|---|---|
id | path | The competition id, in the address. Required. | cp_5pd3gq9x |
status | enum | One of scheduled, live, finished, awarded, cancelled. | scheduled |
page | int | Page number, from 1. Adds totals to meta. | 2 |
per_page | int | Rows a page, 1 to 200. 50 when not sent. | 200 |
cursor | string | The next_cursor from the last answer. Send it alone. |
Request
Send your key in the Authorization header as a Bearer token, or in X-API-Key. A key in the address is refused, so it never ends up in a log.
# A competition's matches curl "https://api.volleyballapi.com/v1/competitions/cp_5pd3gq9x/matches?per_page=2" \ -H "Authorization: Bearer $VBA_KEY"
$q = http_build_query(['per_page' => '2']); $ch = curl_init('https://api.volleyballapi.com/v1/competitions/cp_5pd3gq9x/matches?' . $q); curl_setopt_array($ch, [ CURLOPT_HTTPHEADER => ['Authorization: Bearer ' . getenv('VBA_KEY')], CURLOPT_RETURNTRANSFER => true, ]); $res = json_decode(curl_exec($ch), true); print_r($res['data']);
import os, requests r = requests.get( "https://api.volleyballapi.com/v1/competitions/cp_5pd3gq9x/matches", params={"per_page": "2"}, headers={"Authorization": f"Bearer {os.environ['VBA_KEY']}"}, ) print(r.json()["data"])
const res = await fetch("https://api.volleyballapi.com/v1/competitions/cp_5pd3gq9x/matches?per_page=2", { headers: { "X-API-Key": process.env.VBA_KEY }, }); const { data, meta } = await res.json();
Response
Every answer is data plus meta. A first call with page adds totals to meta; a call with cursor carries only the next cursor, which is quicker over long ranges. This is a real answer to the request above, counted 2026-10-13, with long lists cut short.
{
"data": [
{
"id": "mt_92wefstq",
"discipline": "indoor",
"gender": "women",
"status": "finished",
"current_set": null,
"date": "2015-06-26",
"time_local": "13:00",
"start_utc": "2015-06-26T07:00:00Z",
"competition": {
"id": "cp_5pd3gq9x",
"name": "World Grand Prix 2015 - 3rd Group",
"season": 2015
},
"round": null,
"pool": "Pool N",
"team_a": { "id": "tm_cvvzr61h", "name": "Australia" },
"team_b": { "id": "tm_3b35zh93", "name": "Cuba" },
"score": { "a": 0, "b": 3 },
"winner": "b",
"sets": [
{ "set": 1, "a": 22, "b": 25, "duration_s": 1500 },
{ "set": 2, "a": 12, "b": 25, "duration_s": 1260 },
{ "set": 3, "a": 16, "b": 25, "duration_s": 1380 }
],
"sets_complete": true,
"duration_s": 4140,
"updated_utc": "2026-09-29T12:34:58Z"
},
{
"id": "mt_jqnc4jvp",
"discipline": "indoor",
"gender": "women",
"status": "finished",
"current_set": null,
"date": "2015-06-26",
"time_local": "16:00",
"start_utc": "2015-06-26T10:00:00Z",
"competition": {
"id": "cp_5pd3gq9x",
"name": "World Grand Prix 2015 - 3rd Group",
"season": 2015
},
"round": null,
"pool": "Pool N",
"team_a": { "id": "tm_ttx004b7", "name": "Kazakhstan" },
"team_b": { "id": "tm_pwe3x70a", "name": "Algeria" },
"score": { "a": 3, "b": 0 },
"winner": "a",
"sets": [
{ "set": 1, "a": 25, "b": 23, "duration_s": 1320 },
{ "set": 2, "a": 25, "b": 17, "duration_s": 1320 },
{ "set": 3, "a": 25, "b": 20, "duration_s": 1440 }
],
"sets_complete": true,
"duration_s": 4080,
"updated_utc": "2026-09-29T12:34:58Z"
}
],
"meta": {
"plan": "Complete",
"count": 2,
"next_cursor": "eyJvIjoyLCJwIjoyfQ",
"page": 1,
"per_page": 2,
"total": 28,
"total_pages": 14,
"next_page": 2,
"prev_page": null
}
}Fields
| Field | Type | What it holds |
|---|---|---|
id | string | Stable match id, mt_ |
discipline | enum | indoor or beach |
gender | enum | men, women or mixed |
status | enum | scheduled, live, finished, awarded or cancelled |
current_set | int | The set being played, while live; otherwise null |
date, time_local | date, time | The venue's calendar day and clock |
start_utc | datetime | Scheduled start in UTC, ISO 8601 |
competition | object | id, name and season |
round, pool | string | "Semifinals", "Pool B", or null |
team_a, team_b | object | id and name: a club, a national team or a beach pair |
score | object | Sets won by each side |
winner | enum | a or b, null until finished |
sets | array | Each set: number, points each side, duration in seconds |
sets_complete | bool | false when the source's set scores do not add up to its result, so some sets are missing |
duration_s | int | Match length in seconds |
updated_utc | datetime | When anything in the match last changed |
Errors
Errors come back as {"error": {"code", "message", "docs"}}, with plan and pricing added when a plan would answer. Every error.
| HTTP | Code | When |
|---|---|---|
| 400 | bad_request | A value of the wrong shape, or per_page outside 1 to 200 |
| 401 | unauthorized | No key, or a key that is not known or was revoked |
| 404 | not_found | An id that does not exist |
| 422 | unknown_parameter | A parameter this endpoint does not take; the answer lists the ones it does |
| 429 | rate_limited | Too many calls this minute; Retry-After says when to try again |
| 429 | quota_exceeded | The day's or month's allowance is used; the answer says when it resets |
Try it
Fill in what you need; the request is built as you type. Paste your key to run it here, straight against the API.