a-b-street/abstreet · error
study area geojson has
Error message
study area geojson has {} polygons What it means
load_study_area parses the study area GeoJSON and requires exactly one polygon, since the scenario operates on a single contiguous study area. If the parsed list has any count other than 1, it bails reporting how many polygons were found.
Solutions
- Verify the study area geojson contains exactly one polygon fully inside the map's GPS bounds.
- Dissolve multiple polygons into one (union in QGIS/GeoPandas) or restrict the study area.
- Check the require_in_bounds setting and the map's bounds if features are being silently dropped.
Example fix
// before (two disjoint polygons) features: [polyA, polyB] // after (dissolved) features: [union(polyA, polyB)]
Defensive patterns
Strategy: validation
Validate before calling
let polys = Polygon::from_geojson_bytes(&bytes, gps_bounds, require_in_bounds)?;
if polys.len() != 1 {
bail!("study area must resolve to exactly 1 in-bounds polygon, got {}", polys.len());
} Try / catch
match load_study_area(map) {
Ok(area) => area,
Err(e) if e.to_string().contains("study area geojson has") => {
eprintln!("Fix the study area file (empty or multi-polygon): {e}");
return Err(e);
}
Err(e) => return Err(e),
} Prevention
- Ensure the study area polygon lies fully within the map's GPS bounds
- Union multiple study-area polygons into one before export
- Visually check the study area against the map boundary in QGIS first
When it happens
Trigger: generate_scenario for a UK map whose study area geojson yields 0 polygons (empty file / out-of-bounds features dropped when require_in_bounds is set) or multiple polygons (disjoint study area).
Common situations: Study area drawn partly outside the map's GPS bounds so in-bounds filtering drops all polygons; exporting a multi-polygon study area instead of dissolving it into one; pointing at a truncated or wrong file.
Understand the failure class
Background: EmptyResultError / "no results found": when an API or scraper succeeds but returns zero rows — this error's family across 9 libraries.
Related errors
- Unexpected geojson
- Expected exactly 1 feature
- Input is missing geo_code
- Started on a road we shouldn't trace
- doesn't have a column called Longitude, Latitude, or…
AI-assisted analysis of a-b-street/abstreet@0964f29315 (2026-09-13).
Data as JSON: /api/errors/94867a3ff3c50d84.
Report an issue: GitHub.
Appendix: source
Thrown at importer/src/uk.rs:218
} else {
bail!("Input is missing geo_code: {:?}", tags);
}
}
Ok(zones)
}
fn load_study_area(map: &Map) -> Result<Polygon> {
let require_in_bounds = true;
let mut list = Polygon::from_geojson_bytes(
&abstio::slurp_file(abstio::path(format!(
"system/study_areas/{}.geojson",
map.get_name().city.city.replace("_", "-")
)))?,
map.get_gps_bounds(),
require_in_bounds,
)?;
if list.len() != 1 {
bail!("study area geojson has {} polygons", list.len());
}
Ok(list.pop().unwrap().0)
}
fn check_sensor_data(map: &Map, scenario: &Scenario, sensor_path: &str, timer: &mut Timer) {
use map_model::PathRequest;
let requests = scenario
.all_trips()
.filter_map(|trip| {
if trip.mode == TripMode::Drive {
TripEndpoint::path_req(trip.origin, trip.destination, trip.mode, map)
} else {
None
}
})
.collect();
let deduped = PathRequest::deduplicate(map, requests);View on GitHub (pinned to 0964f29315)