In this tutorial, we'll take you step-by-step through all the fixtures data for a league and this including events, lineups, teams and players statistics.
Using the England Premier League as an example. This competition includes 20 teams, giving a total of 380 matches spread over 38 rounds. The league id and season used are 39
and 2024
. If you want to do the same for another competition you have all whole list of league ID and seasons available in the dashboard or by calling the endpoint leagues
.
Let's take a look at the most efficient way of retrieving all this data, rather than doing it match by match.
Requirements
- A valid API-KEY for our dashboard
Step 1 : Get the list of fixtures ids
First of all, we need all the match ids in the league. Of course, we're looking to retrieve data for matches that have already been played, as this data is only available for completed or ongoing matches, so we'll need to exclude upcoming matches from our queries so as not to call the API for nothing.
To do this, we'll use the endpoint fixtures with the league
, season
and status
parameters
For status
, we'll use the documentation to select only matches with a “completed” status.
Our query will therefore look like this:
v3.football.api-sports.io/fixtures?league=39&season=2024&status=FT-AET-PEN
If we want to add matches in progress, we need to add all these statuses 1H-HT-2H-ET-BT-P
let's test it in Postman
So we have 149 fixtures which are either completed or in progress and for which we will get the data.
What will interest us in this API response are only the fixture id fields
"fixture": {
"id": 1208021,
At this point it would be advisable to create an empty array in your code and fill it with ids.
In javascript it would look like this
// API header configuration
const myHeaders = new Headers();
myHeaders.append("x-rapidapi-key", "xXxXxXxXxXxXxX"); // Replace with your API key
myHeaders.append("x-rapidapi-host", "v3.football.api-sports.io");
// Query options
const requestOptions = {
method: 'GET',
headers: myHeaders,
redirect: 'follow'
};
// Main function for retrieving fixtures and managing queries
async function fetchFixtures() {
try {
// Main call to retrieve fixtures
const response = await fetch("https://v3.football.api-sports.io/fixtures?league=39&season=2024&status=FT-AET-PEN-1H-HT-2H-ET-BT-P", requestOptions);
const data = await response.json();
// IDs extraction
const fixtures_id = [];
if (data.response && Array.isArray(data.response)) {
data.response.forEach(item => {
if (item.fixture && item.fixture.id) {
fixtures_id.push(item.fixture.id);
}
});
}
} catch (error) {
console.log("Data recovery error :", error);
}
}
// Executing the main function
fetchFixtures();
Step 2 : Transform the ids array to use it as a parameter API
Now that we have our array containing all the ids from which we want to retrieve data, we're going to transform it to coincide with the API requirements.
The endpoint we'll use will be fixtures?ids=
and, as indicated in the documentation, it's limited to a maximum of 20 ids, whereas we have 149.
We'll therefore have to split our array into a multi-dimensional array, with each key containing a maximum of 20 ids.
In Javascript we could do it like this
function chunkArray(array, chunkSize) {
const chunks = [];
for (let i = 0; i < array.length; i += chunkSize) {
chunks.push(array.slice(i, i + chunkSize));
}
return chunks;
}
const chunked_fixtures_id = chunkArray(fixtures_id, 20);
If we print (console.log) the new array it should look like this :
We therefore have 8 keys, each containing a maximum of 20 fixture ids. Now we have what we need to call the API and retrieve the data
Step 3 : Get the data
Now that everything's ready, all we need to do is browse each key in the chunked_fixtures_id
array and make an API call using the ids fixtures.
If we test the 1st query in Postman, we get 20 results including events, lineups, statistics and players statistics for each fixture.
v3.football.api-sports.io/fixtures?ids=1208021-1208022-1208023-1208024-1208025-1208026-1208027-1208028-1208029-1208030-1208033-1208035-1208038-1208039-1208037-1208034-1208032-1208031-1208040-1208036
The complete code would look like this.
// API header configuration
const myHeaders = new Headers();
myHeaders.append("x-rapidapi-key", "xXxXxXxXxXxXxX"); // Replace with your API key
// Query options
const requestOptions = {
method: 'GET',
headers: myHeaders,
redirect: 'follow'
};
// Function for dividing an array into sub-arrays of maximum size
function chunkArray(array, chunkSize) {
const chunks = [];
for (let i = 0; i < array.length; i += chunkSize) {
chunks.push(array.slice(i, i + chunkSize));
}
return chunks;
}
// Utility function to add a delay
const delay = (ms) => new Promise(resolve => setTimeout(resolve, ms));
// Main function for retrieving fixtures and managing queries
async function fetchFixtures() {
try {
// Main call to retrieve fixtures
const response = await fetch("https://v3.football.api-sports.io/fixtures?league=39&season=2024&status=FT-AET-PEN-1H-HT-2H-ET-BT-P", requestOptions);
const data = await response.json();
// IDs extraction
const fixtures_id = [];
if (data.response && Array.isArray(data.response)) {
data.response.forEach(item => {
if (item.fixture && item.fixture.id) {
fixtures_id.push(item.fixture.id);
}
});
}
// Divide IDs into sub-tables of up to 20 each
const chunked_fixtures_id = chunkArray(fixtures_id, 20);
// Browse each group of IDs with a time delay
for (const idsGroup of chunked_fixtures_id) {
// Building the parameter chain for the API
const idsParam = idsGroup.join("-");
const url = `https://v3.football.api-sports.io/fixtures?ids=${idsParam}`;
// Making an API call
const groupResponse = await fetch(url, requestOptions);
const groupResult = await groupResponse.json();
console.log("Result for IDs group :", groupResult);
// Enter a delay before the next request (ie 1000 ms)
await delay(1000);
}
} catch (error) {
console.log("Data recovery error :", error);
}
}
// Executing the main function
fetchFixtures();
Note that we've added a limiter to take account of the API Ratelimit. If we don't add few requests will return an error depending on the plan subscribed to.
If you run the code you should have this in your console
All that's left to do is to exploit the content of each answer and, of course, adapt it to your needs. For example, this code could be useful for retrieving information only from live matches or from the previous day's matches.
This way, in just 9 API calls, we've retrieved all available fixture data for a given league.
Don't forget to check the competition's coverage before calling up this information, as not all competitions have the same coverage and the same information available.