Skip to content

Custom rosters ​

You do not have to start a league from the built-in teams. You can start from a roster file. A roster file sets your own teams, divisions, colors and players, so you can build a fictional universe of your own. This page shows how to load a file someone made, and how to build your own.

Load a roster file ​

If someone has shared a roster file with you, you are about 30 seconds from kickoff.

  1. Open My Leagues. Select Start a league, or New league if you already have one.
  2. Give your league a name.
  3. Paste the public https:// link to the JSON file into Community roster URL (optional).
  4. Click anywhere outside the box. The game checks the file at once. A green message shows the team count and the name of the file, for example "32 teams". A red list shows what is wrong.
  5. Pick your sim schedule and select Create league.

Two things to know:

  • Equal budgets: a league made from a roster file gives every team the same cap, $224.8M, with no market tiers. The league stays balanced no matter which team you run.
  • The file is locked at creation: you cannot swap the roster file after the league exists. Check that you have the right one first.

Build your own file ​

A roster file is plain JSON. There is no spreadsheet uploader. You, or a script, write the JSON and host it at a public link. A full league has 32 teams, so most people use a script.

In the v2 format, each team sets its own name, abbreviation, conference, division and colors. The basic shape is below.

json
{
  "format": "ftfl-rosters-v2",
  "season_label": "My Universe 2026",
  "teams": [
    {
      "name": "Harbor Gulls",
      "abbrev": "HBG",
      "conference": "Eastern",
      "division": "North",
      "colors": { "primary": "#1c3f94", "secondary": "#c8102e" },
      "active":         [ /* exactly 40 players */ ],
      "practice_squad": [ /* exactly 12 players */ ]
    }
    /* ...one block per team, all 32... */
  ],
  "free_agents": [ /* optional list of players */ ]
}

Rules the file must follow ​

If a file does not validate, check this list.

  • format must be exactly ftfl-rosters-v2.
  • The file needs exactly 32 teams.
  • The conference and division labels must form exactly 2 conferences. Each conference has 4 divisions. Each division has exactly 4 teams. The labels are free text, but this 2 x 4 x 4 shape is required, so the schedule and playoffs work.
  • Every team needs a unique abbrev. The game uses it on crests and tables.
  • Every team needs exactly 40 active players and exactly 12 practice_squad players in the file. During the season, the game allows up to 16 on a practice squad.
  • Each active roster needs at least 1 QB, 1 K and 1 P. Without them the sim cannot field special teams.
  • colors is optional. Use 6-digit hex values: { "primary": "#rrggbb", "secondary": "#rrggbb" }. The secondary color is optional. If you skip colors, the game makes a color from the team name. Your colors drive the team's crest.
  • free_agents is optional. If you skip it, free agency starts thin.

Team names are yours. Pick what fits your universe.

Define a player ​

You can put a player on a roster in two ways.

Reference a player in the database. Give the player's Pro-Football-Reference id and, if you want, an age.

json
{ "pfr_id": "MahoPa00", "age": 28 }

The sim reads that player's real career to set the player's ratings. Leave out age and the sim uses the player's real age.

To find the id, open the player's page on Pro-Football-Reference. The id is in the address. For example, the page pro-football-reference.com/players/M/MahoPa00.htm gives the id MahoPa00. Use the id, not the name. More than one player can share a name.

The game takes the position of a referenced player from its database, not from your file. You may write "position" next to the id to keep the file readable. The game ignores it. If a referenced player appears in the wrong position group, that is a database problem, and your file cannot fix it. To set a position yourself, define the player inline.

Define a player inline. Use this for rookies, prospects and fictional players.

json
{
  "name": "Sam Rivera",
  "position": "QB",
  "birth_year": 2001,
  "debut_year": 2024,
  "draft_round": 1,
  "draft_pick": 1
}

Inline players need name, position, birth_year and debut_year. draft_round and draft_pick are optional. The sim uses draft position and years of experience to shape the player's ability, so a first overall pick comes out stronger than an undrafted player.

position must be one of 14 values: QB, RB, FB, WR, TE, OL, EDGE, DT, LB, CB, S, K, P, LS. Put guards, tackles and centers under OL. Put edge rushers under EDGE. Put safeties under S.

How ability works ​

The file has no overall rating to type. For a referenced player, the sim builds ratings from the player's real career. For an inline player, it builds ratings from position, age and draft position. Every player lands on the same scale as a player in a normal league.

Use the built-in teams with the v1 format ​

If you do not want to name your own teams, use the v1 format. It fills rosters onto the built-in teams. Set "format" to ftfl-rosters-v1. Name each team with franchise, not with the v2 team fields. Player blocks are the same.

json
{ "franchise": "Harbor Gulls", "active": [ /* 40 */ ], "practice_squad": [ /* 12 */ ] }

The 32 built-in teams, for v1 only:

  • Coastal East: Harbor Gulls, Empire Statesmen, Granite Wardens, Bayshore Captains
  • Coastal North: Northport Steamers, Foundry Anvils, Cinder Forge, Iron Lake Miners
  • Coastal South: Coral Coast Sharks, Delta Catfish, Bayou Herons, Sunbelt Armadillos
  • Coastal West: Summit Pioneers, Pacifica Surge, Mesa Coyotes, Canyon Vipers
  • Heartland East: Capital Sentinels, Metro Knights, Keystone Quarriers, Crown Monarchs
  • Heartland North: Prairie Cyclones, Heartland Reapers, Lakefront Tradesmen, Timberline Lumberjacks
  • Heartland South: Crescent Brass, Gulfport Tarpons, Lowcountry Gators, Magnolia Mockingbirds
  • Heartland West: Goldfield Prospectors, Verde Cacti, Cascade Loggers, Bay City Fog

Host and test your file ​

  • Host the file at a publicly readable https:// link. Plain HTTP is rejected, and the host cannot ask for a login.
  • Keep the file under 5 MB. The host must answer within 10 seconds.
  • A GitHub Gist raw link or any static JSON host works.
  • The checker lists all errors at once. Paste your draft link, read the red errors, fix the file, host it again, and click out of the box until you see the green message.