🏈 CFL SDK
A modern Python SDK for the Canadian Football League API using httpx.
Features · Installation · Quick Start · API Reference · Built with CFL SDK · Contributing
Features
- Full type hints using modern Python typing
- Comprehensive API coverage (most endpoints supported)
- Error handling and logging
Installation
pip install cfl-sdk
With Poetry
poetry add cfl-sdk
Quick Start
from cfl import CFLClient
client = CFLClient()
# Get all teams
teams = client.get_teams()
for team in teams:
print(f"{team['name']} ({team['abbreviation']})")
# Get fixtures for a season
fixtures = client.get_fixtures(season_id=75) # 2026 season
# Get players filtered by position
qbs = client.get_players(position="QB", limit=20)
API Reference
Teams · Venues · Players · Seasons · Fixtures · Rosters · Roster Players · Colleges · Ledger · Team Stats · Player Stats · Standings · Leaderboard
Teams
# Get all teams
teams = client.get_teams()
# Get a specific team
team = client.get_team(team_id=1)
# Get a team's full current roster
roster = client.get_team_roster(team_id=1)
Venues
# Get all venues
venues = client.get_venues()
# Get specific venue
venue = client.get_venue(venue_id=1)
Players
# Get players (filterable)
players = client.get_players(limit=50)
players = client.get_players(position="QB")
players = client.get_players(college_id=295)
players = client.get_players(sort_by="lastname", sort_order="asc", page=2, limit=25)
# Get a specific player
player = client.get_player(player_id=183186)
# Embed college details in the response
player = client.get_player(player_id=183186, with_college=True)
# player["relations"]["college"] -> college object
# Search players by name pattern
results = client.search_players("mitchell") # returns [{ID, name}, ...]
# Get all position definitions
positions = client.get_player_positions()
Seasons
# Get all seasons (with optional pagination)
seasons = client.get_seasons(page=1, limit=50)
# Get specific season
season = client.get_season(season_id=75) # 2026 season
Fixtures (Games)
# Get fixtures (with optional filters and pagination)
fixtures = client.get_fixtures(limit=50)
fixtures = client.get_fixtures(season_id=75) # 2026 season
fixtures = client.get_fixtures(home_team_id=1)
fixtures = client.get_fixtures(away_team_id=1)
fixtures = client.get_fixtures(venue_id=1)
# Get a specific fixture
fixture = client.get_fixture(fixture_id=6555)
# Embed related objects
fixture = client.get_fixture(fixture_id=6555, with_venue=True)
fixture = client.get_fixture(fixture_id=6555, with_season=True)
# fixture["relations"]["venue"] -> venue object
Rosters
# Get all rosters
rosters = client.get_rosters()
# Get specific roster
roster = client.get_roster(roster_id=1)
# Get per-team roster state and nationality counts
summary = client.get_rosters_summary()
Roster Players
# Get all roster player entries
roster_players = client.get_roster_players(limit=50)
# Filter to a specific player's entry
entries = client.get_roster_players(player_id=183186)
# Embed full player object
entries = client.get_roster_players(with_player=True, limit=25)
# entries[0]["relations"]["player"] -> full player object
# Get a specific roster player entry
rp = client.get_roster_player(rosterplayer_id=26733)
rp = client.get_roster_player(rosterplayer_id=26733, with_player=True)
# Get all valid roster states
states = client.get_roster_player_states()
Colleges
# Get all colleges
colleges = client.get_colleges(limit=50)
# Filter by name
colleges = client.get_colleges(name="laval")
# Sort and paginate
colleges = client.get_colleges(sort_by="name", sort_order="asc", page=1, limit=25)
# Get a specific college
college = client.get_college(college_id=295)
Ledger (Transactions)
# Get transactions for a year
transactions = client.get_ledger(year=2026)
Team Stats
# Get team stats
team_stats = client.get_team_stats()
# Get team stats for a season
team_stats = client.get_team_stats(season_id=75) # 2026 season
# Get specific team stats
team_stat = client.get_team_stat(team_stats_id=122345)
Player Stats
# Get player stats (with optional pagination and season filter)
player_stats = client.get_player_stats(season_id=75, page=1, limit=50)
# Get specific player stats
player_stat = client.get_player_stat(player_stats_id=1629968)
# Get player stats with photo URL
player_stat = client.get_player_pims(player_id=168507)
Standings
# Get standings for a year (2016-2026 supported)
standings = client.get_standings(year=2026)
standings["week"] # week the standings reflect
standings["east"] # list of team rows for the East division
standings["west"] # list of team rows for the West division
standings["unified"] # combined table (available from 2020 on)
row = standings["west"][0]
row["place"], row["abbreviation"], row["wins"], row["losses"], row["ties"]
Leaderboard
# Get league leaders for every stat category (2016-2026 supported)
leaders = client.get_leaderboards(season=2026)
# Return more players per category (1-25, default 3)
leaders = client.get_leaderboards(season=2026, count=10)
leaders["offence"] # [{"category": "passing", "leaders": [...]}, ...]
leaders["defence"] # [{"category": "tackles", "leaders": [...]}, ...]
leaders["special_teams"] # [{"category": "fieldGoalsSucceeded", "leaders": [...]}, ...]
top_passer = leaders["offence"][0]["leaders"][0]
top_passer["firstname"], top_passer["lastname"], top_passer["statValue"]
Error Handling
The SDK provides specific error types:
CFLAPIConnectionError: For connection issuesCFLAPITimeoutError: For request timeoutsCFLAPINotFoundError: For 404 responsesCFLAPIAuthenticationError: For auth issuesCFLAPIValidationError: For invalid requestsCFLAPIServerError: For server errors
from cfl import CFLClient, CFLAPINotFoundError
client = CFLClient()
try:
team = client.get_team(team_id=999999)
except CFLAPINotFoundError:
print("Team not found")
Using with Context Manager
with CFLClient() as client:
teams = client.get_teams()
# Client will be closed automatically
Acknowledgements & Disclaimer
Thank you to the Canadian Football League (CFL) for providing a public API.
This is an unofficial SDK and is not affiliated with, endorsed, or sponsored by the Canadian Football League (CFL).
Built with CFL SDK
Using this SDK in a project? Open a PR to add it here!
| Project | Description |
|---|---|
| Your project here | Open a PR to add yours |
Contributing
Contributions are welcome! Please feel free to submit a pull request or open an issue for any bugs or feature requests.
License
This project is licensed under the MIT License. See the LICENSE file for more details.
Metadata
Release files for cfl-sdk 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| cfl_sdk-0.1.0.tar.gz | 16.0 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| cfl_sdk-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 34.6 kB
Release files / cfl_sdk-0.1.0.tar.gz
| Download URL | cfl_sdk-0.1.0.tar.gz |
|---|---|
| Size | 16.0 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
61bd0f8e049a8daf2e028ad4b10cb960627f566a4e840facb6de819dc788c210
|
|
BLAKE2b-256 checksum How to use checksums |
fb93ed3c9973256179f54a00a8524ea1594585aaa5c88c508902538a8ff67a4c
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 3, 2026.
Transparency logRelease files / cfl_sdk-0.1.0-py3-none-any.whl
| Download URL | cfl_sdk-0.1.0-py3-none-any.whl |
|---|---|
| Size | 18.6 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
82a51ec20425203d0076880a91983c4d45f17ef683710ddb7e855b7c228c208d
|
|
BLAKE2b-256 checksum How to use checksums |
14a182d12333f6b94b1c5c70fab2e2fe26c769bf50fa38fda4f6848390d8295d
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 3, 2026.
Transparency log