Skip to main content

Single match stream

Subscribe to push updates for one specific match.

URL

wss://api.scorelytics.pro/v1/ws/match/{id}?api_key=sk_live_...

{id} is the match identifier returned by listMatches.

Messages emitted

score_update

Sent whenever any of these change: home_score, away_score, period, minute, game_clock_secs.

{
"type": "score_update",
"match_id": "abc123",
"data": {
"home": 2,
"away": 1,
"minute": 67
}
}

For basketball matches, data carries game_clock_secs instead of minute:

{
"type": "score_update",
"match_id": "xyz789",
"data": {
"home": 84,
"away": 81,
"period": 25,
"game_clock_secs": 180
}
}

status_change

Sent when status_code transitions. Both old and new are included so a client can choose to react only to specific transitions (e.g. 2 → 3 for final whistle).

{
"type": "status_change",
"match_id": "abc123",
"data": { "from": 2, "to": 3 }
}

Suggested flow

const apiKey = process.env.SCORELYTICS_KEY;
const matchId = 'abc123';

async function start() {
const snap = await fetch(
`https://api.scorelytics.pro/v1/football/matches/${matchId}`,
{ headers: { 'X-API-Key': apiKey } }
).then(r => r.json());

render(snap);

const ws = new WebSocket(
`wss://api.scorelytics.pro/v1/ws/match/${matchId}?api_key=${apiKey}`
);
ws.onmessage = (e) => {
const msg = JSON.parse(e.data);
if (msg.type === 'score_update') {
Object.assign(snap, {
home_score: msg.data.home,
away_score: msg.data.away,
minute: msg.data.minute ?? snap.minute,
});
} else if (msg.type === 'status_change') {
snap.status_code = msg.data.to;
}
render(snap);
};

ws.onclose = () => setTimeout(start, 3_000);
}
start();

When the match ends

After a status_change to 3 (Finished), no further messages will arrive. Close the connection cleanly:

if (msg.type === 'status_change' && msg.data.to === 3) {
ws.close(1000, 'match finished');
}

Errors

StatusMeaning
401API key missing or invalid (sent before the WebSocket upgrade).
404Match ID does not exist.
426Request did not include WebSocket upgrade headers.