Sofascore Rankings Scraper
Pricing
from $1.50 / 1,000 ranking rows
Sofascore Rankings Scraper
Scrape every global ranking Sofascore publishes: FIFA world rankings, UEFA club and league coefficients, ATP and WTA singles and live, UTR, World Rugby, rugby league, Premier Padel and all twelve UFC divisions. Plus name-to-ID search. No API key, no login.
Pricing
from $1.50 / 1,000 ranking rows
Rating
0.0
(0)
Developer
Elena Vance
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
2 days ago
Last modified
Categories
Share
Every global ranking Sofascore publishes, in one run — and a name-to-ID search for the rest of its data.
25 ranking tables across five sports: FIFA world rankings, UEFA club and league coefficients, ATP and WTA singles and live, UTR, World Rugby, rugby league, Premier Padel, and all twelve UFC divisions.
No API key, no login, no browser. Calls Sofascore's own JSON API directly and only reaches for a proxy if a request is actually blocked.
The point of this Actor
Sofascore's ranking endpoint returns rows and nothing that names them. Ask it for type 11 and you get sixteen fighters with no indication that this is the UFC flyweight division; ask for type 1 expecting the FIFA table and you get UEFA's league coefficients instead. There is no index, no documentation, and the numbering has gaps.
So the catalogue below is the product. It was built by sweeping every type from 1 to 110 against the live API and identifying each table from its contents — 25 live, the rest 404.
| Football | Tennis | Combat & other |
|---|---|---|
| FIFA Men's World Ranking (211 nations) | ATP singles (500) | UFC — all 12 divisions |
| UEFA club coefficients (411 clubs) | WTA singles (500) | World Rugby (113 nations) |
| UEFA league coefficients (55 leagues) | ATP live, WTA live | Rugby league world (35) |
| UTR men, UTR women | Premier Padel men & women |
What you get
Two row types in one dataset, told apart by recordType.
ranking — one row per ranked entity: rank, points, previous rank, places
moved, the entity's Sofascore ID and a URL you can open. Tennis rows add career
best and tournaments played; MMA rows add the fight record; UEFA coefficient
rows add the year.
searchResult — one row per hit when you search a name: the entity type,
its Sofascore ID, its sport and club, and how many users follow it (which is
how you tell the Erling Haaland you want from the four others).
What makes this different
- The catalogue is the product. Sofascore's ranking endpoint returns rows with nothing that names them, no index, and gaps in the numbering. This Actor's 25-table catalogue was built by sweeping every type from 1 to 110 against the live API and identifying each table from its contents — see The point of this Actor.
- Five sports in one Actor. Sellers elsewhere carry a single slice each: tennis only, or football only. This one covers football, tennis, rugby, MMA and padel.
- Name-to-ID search feeds the whole suite.
searchQueriesresolves a name into the team, player and tournament IDs that the other five Actors take as input, and tells duplicates apart by follower count. - UEFA coefficient history no bulk table exposes — ask for a club by ID and get its coefficient and position for every year from 2018 to 2027.
- UFC rank 0 is the champion, carried with an explicit
isChampionflag so code that treats 0 as a null does not misplace the title-holder.
Input
| Field | Type | Default | What it does |
|---|---|---|---|
rankings | array | — | Table names from the catalogue (atp-singles, fifa-world-ranking, ufc-heavyweight…), raw Sofascore type numbers, or ["all"] for every table. |
topN | integer | whole table | Keep only the top N of each. The tennis and padel tables are 500 rows; the UFC divisions are 16. |
entities | array | — | Team IDs or Sofascore URLs. Returns every ranking that entity is in. |
searchQueries | array | — | Names to resolve to Sofascore IDs. 2–100 characters each. |
searchType | string | all | Narrow to teams, players, competitions, managers or referees. |
maxSearchPages | integer | 1 | 20 results per page; paging stops early on a short page. |
maxItems | integer | 10000 | Stop after this many rows. |
proxyConfiguration | object | off | Only needed if your IP is blocked. |
A run needs at least one of rankings, entities or searchQueries.
{ "rankings": ["fifa-world-ranking", "atp-singles"], "topN": 50 }
Three things worth knowing
In the UFC tables, rank 0 is the champion. Not a missing value. Every
division runs 0–15, and code that treats 0 as null puts the title-holder in the
wrong place — so every row also carries an explicit isChampion flag.
Sofascore models individual athletes as teams. A tennis player, an MMA
fighter, a padel player and a motorsport driver all arrive as team entities;
only team-sport athletes are player. That is why entities takes team IDs,
and why the URL for a "team" depends on the sport — /tennis/player/…,
/mma/fighter/…, /football/team/…. The Actor emits the right one.
A club look-up returns history the bulk table cannot. /rankings for the
UEFA club coefficients carries only the current year. Ask for Manchester City
by ID and you get its coefficient and position for every year from 2018 to
2027 — ten rows, one per season. This is the only route to that series.
The flip side: footballers cannot be looked up at all. Sofascore only ranks
entities it models as teams, so a player ID returns nothing, and the run says
so rather than failing.
Notes
- The whole catalogue is 25 requests, roughly 5,700 rows. A complete sweep is a cheap run.
- There is no way to ask for a historical snapshot of a ranking — every dated variant of the endpoint 404s. The UEFA club coefficient series above is the only history Sofascore exposes.
- A type number outside the catalogue is still fetched. It comes back labelled
Ranking type Nrather than rejected, so a table Sofascore adds tomorrow works today. - Bad input is recorded as an unbilled
INVALID_INPUTrow rather than crashing the run.
The Sofascore Actor suite
Six Actors from the same publisher, built on one shared HTTP layer and one ID space — so the output of one is the input of the next.
| Actor | What it returns |
|---|---|
| Live Scores & Fixtures | Fixtures and live results by date across 19 sports. Emits eventId. |
| Match Stats, xG & Lineups | Per-match shotmaps with pitch coordinates, lineups, ratings, momentum. Takes eventId. |
| League Standings & Tables | League tables, group stages, conferences and divisions. Takes uniqueTournamentId. |
| Team & Player Data | Squads, bios, market values, transfers, match logs. Takes team and player IDs. |
| Season Stats | Season leaderboards and complete team statistics. Takes uniqueTournamentId. |
| Rankings & Search | This Actor. |
How they chain. Live Scores emits the eventId that Match Stats takes.
Rankings' search turns a name into the team, player and tournament IDs the
other five accept. Standings and Season Stats share uniqueTournamentId, and
Team & Player emits that same ID as primaryTournamentId.
All six need no API key, no login and no headless browser; none requires a residential-proxy add-on, and all run on the Apify free plan.
Development
pip install -r requirements-dev.txtpytest # 161 tests, no networknpx apify-cli@1 validate-schemaapify run # needs storage/key_value_stores/default/INPUT.json
docs/architecture.md covers the catalogue and how the pieces fit together;
docs/ci-cd.md the GitHub Actions pipeline; docs/publishing.md the Apify
Store listing and pricing.