Skip to content

Build a surface fuel grid from LANDFIRE

You are viewing in-progress documentation for v2 (Beta). Switch to the stable version for the current production release.

A physics-based fire model needs surface fuel loads — how much fuel sits in each size class, per unit area. FastFuels builds them from LANDFIRE in two steps:

  1. Fetch the FBFM40 fuel-model grid — a categorical grid of Scott & Burgan 40 fire-behavior fuel-model codes (fbfm), pulled from LANDFIRE.
  2. Look up fuel parameters — translate each fuel-model code into continuous loads (1hr/10hr/100hr, live herbaceous/woody) and fuel depth.

The split is deliberate: the FBFM grid is a reusable categorical input, and the lookup turns it into the continuous bands a model consumes. You can run the lookup again with a different band selection without re-fetching LANDFIRE.

  1. An API key. Set it once — it propagates to every code block: my-api-key.

  2. A domain within CONUS. LANDFIRE covers the conterminous United States. Plug your domain id in once: your-domain-id. See Create a domain.

The whole flow in one script:

Build a surface fuel grid (both steps + polling)
import time
import requests
API_KEY = "my-api-key"
DOMAIN_ID = "your-domain-id"
BASE = "https://api-v2-prod-nyvjyh5ywa-uw.a.run.app"
HEADERS = {"api-key": API_KEY}
def poll(grid_id: str) -> dict:
while True:
grid = requests.get(
f"{BASE}/domains/{DOMAIN_ID}/grids/{grid_id}", headers=HEADERS
).json()
if grid["status"] in ("completed", "failed"):
return grid
time.sleep(5)
# Step 1: FBFM40 fuel-model grid from LANDFIRE (categorical `fbfm` band).
fbfm = requests.post(
f"{BASE}/domains/{DOMAIN_ID}/grids/fbfm40/landfire",
headers=HEADERS,
json={"name": "FBFM40 fuel model (LANDFIRE 2024)", "version": "2024"},
).json()
fbfm = poll(fbfm["id"])
assert fbfm["status"] == "completed", fbfm
# Step 2: look up surface fuel loads + depth from the FBFM codes.
loads = requests.post(
f"{BASE}/domains/{DOMAIN_ID}/grids/lookup/fbfm40",
headers=HEADERS,
json={
"name": "Surface fuel loads (FBFM40 lookup)",
"source_grid_id": fbfm["id"],
"source_band": "fbfm",
"bands": [
"fuel_load.1hr",
"fuel_load.10hr",
"fuel_load.100hr",
"fuel_load.live_herb",
"fuel_load.live_woody",
"fuel_depth",
],
},
).json()
loads = poll(loads["id"])
print(loads["id"], loads["status"]) # -> <grid id> completed

The rest of this page walks the two calls individually.

Step 1 — Fetch the FBFM40 fuel-model grid

Section titled “Step 1 — Fetch the FBFM40 fuel-model grid”
POST fbfm40/landfire
curl -X 'POST' \
'https://api-v2-prod-nyvjyh5ywa-uw.a.run.app/domains/your-domain-id/grids/fbfm40/landfire' \
-H 'accept: application/json' \
-H 'api-key: my-api-key' \
-H 'Content-Type: application/json' \
-d '{
"name": "FBFM40 fuel model (LANDFIRE 2024)",
"version": "2024"
}'

version selects the LANDFIRE release (2019, 2020, 2022, 2023, 2024; default 2024). The grid carries a single categorical band, fbfm. Record its id — you’ll pass it to the lookup: your-fbfm40-grid-id.

Poll until completed:

GET grid status
curl -X 'GET' \
'https://api-v2-prod-nyvjyh5ywa-uw.a.run.app/domains/your-domain-id/grids/your-grid-id' \
-H 'accept: application/json' \
-H 'api-key: my-api-key'

Point the lookup at the completed FBFM grid. source_band is the band holding the codes (fbfm), and bands is the list of parameters to compute.

POST lookup/fbfm40
curl -X 'POST' \
'https://api-v2-prod-nyvjyh5ywa-uw.a.run.app/domains/your-domain-id/grids/lookup/fbfm40' \
-H 'accept: application/json' \
-H 'api-key: my-api-key' \
-H 'Content-Type: application/json' \
-d '{
"name": "Surface fuel loads (FBFM40 lookup)",
"source_grid_id": "your-fbfm40-grid-id",
"source_band": "fbfm",
"bands": [
"fuel_load.1hr",
"fuel_load.10hr",
"fuel_load.100hr",
"fuel_load.live_herb",
"fuel_load.live_woody",
"fuel_depth"
]
}'

Poll this grid the same way. When complete, it carries the six continuous bands you asked for, with units resolved from the lookup table:

{
"id": "your-grid-id",
"domain_id": "your-domain-id",
"name": "Surface fuel loads (FBFM40 lookup)",
"description": "",
"status": "completed",
"progress": {
"percent": 100,
"message": "Complete"
},
"created_on": "2026-05-25T18:44:51.210747Z",
"modified_on": "2026-05-25T18:44:54.656088Z",
"source": {
"name": "lookup",
"source_band": "fbfm",
"source_grid_id": "your-fbfm40-grid-id",
"table": "fbfm40"
},
"modifications": [],
"bands": [
{
"key": "fuel_load.1hr",
"type": "continuous",
"unit": "kg/m**2",
"index": 0
},
{
"key": "fuel_load.10hr",
"type": "continuous",
"unit": "kg/m**2",
"index": 1
},
{
"key": "fuel_load.100hr",
"type": "continuous",
"unit": "kg/m**2",
"index": 2
},
{
"key": "fuel_load.live_herb",
"type": "continuous",
"unit": "kg/m**2",
"index": 3
},
{
"key": "fuel_load.live_woody",
"type": "continuous",
"unit": "kg/m**2",
"index": 4
},
{
"key": "fuel_depth",
"type": "continuous",
"unit": "m",
"index": 5
}
],
"georeference": {
"crs": "EPSG:32611",
"transform": [
29.438767164252283, 0.0, 720227.9398802927, 0.0, -29.438767164262632,
5190646.487014395
],
"shape": [30, 45]
},
"error": null,
"chunks": {
"shape": [512, 512],
"count": 1,
"count_by_axis": {
"x": 1,
"y": 1
}
},
"tags": []
}

This is a finished surface fuel grid: every cell’s FBFM code is mapped to its loads. On the Blue Mountain domain the codes present (grass, shrub, and timber-litter models, plus non-burnable 91) map fuel_load.1hr across 0.0 (non-burnable) up to 1.3 kg/m**2 — distinct values per fuel model, exactly as the lookup table prescribes.

The fuel-load grid is ready to use:

  • Domain outside CONUS. LANDFIRE is conterminous-US only; a domain elsewhere has no coverage and the FBFM fetch fails. Check that your AOI is within the lower 48.
  • Running the lookup before the FBFM grid is completed. The lookup reads the source grid’s data — it needs source_grid_id to point at a finished grid. Poll step 1 to completed first.
  • Wrong source_band. source_band must name the categorical FBFM band on the source grid (fbfm). Pointing it at a non-existent band fails the lookup.
  • Empty bands. At least one band is required. Pick from the fuel-load, SAVR, depth, and combustion parameters listed above.