fio-l2-cairo-mixedgeom-split
Map (reference ← swipe → agent)
0:00
Heritage analyst here. I've put together `heritage_sites.geojson` from my own field work, and every site in it is several features sharing a `site_id`. I need to load the data into our desktop tool, which only ingests typed GPKG layers, no mixed-geometry files, and every feature has to be single-part. Can you give me back `heritage.gpkg` with three layers named `points`, `lines`, and `polygons`, keeping the `site_id` on every feature so I don't lose the cross-layer link? Use Egypt's national grid.
0:00
System info
{
"adapter": "openrouter",
"model": "google/gemma-4-26b-a4b-it",
"base_url": "https://openrouter.ai/api/v1"
}
0:01
Bash
ls -F
heritage_sites.geojson
0:06
Write
/work/inspect_data.py
content · 13 lines · py
import geopandas as gpd
# Load the data
gdf = gpd.read_file('heritage_sites.geojson')
# Inspect the data
print("Initial data head:")
print(gdf.head())
print("\nGeometry types present:")
print(gdf.geometry.type.unique())
print("\nCRS:")
print(gdf.crs)
Wrote /work/inspect_data.py (253 chars).
0:07
Bash
python /work/inspect_data.py
Initial data head:
site_id ... geometry
0 EG-CAI-001 ... POLYGON ((31.256 30.0316, 31.2572 30.0316, 31....
1 EG-CAI-001 ... LINESTRING (31.2556 30.0321, 31.2566 30.0322, ...
2 EG-CAI-001 ... LINESTRING (31.2567 30.0312, 31.2566 30.0322, ...
3 EG-CAI-001 ... POINT (31.2566 30.0326)
4 EG-CAI-001 ... POINT (31.257 30.0322)
[5 rows x 5 columns]
Geometry types present:
<ArrowStringArray>
['Polygon', 'LineString', 'Point', 'MultiPolygon']
Length: 4, dtype: str
CRS:
EPSG:4326
0:45
Write
/work/solve.py
content · 57 lines · py
import geopandas as gpd
from shapely.geometry import MultiPoint, MultiLineString, MultiPolygon
def explode_to_single_part(gdf):
"""Explodes Multi-geometries into individual single-part geometries."""
# Explode is available in modern geopandas to turn Multi-parts into individual rows
# We use explode() which returns a GeoDataFrame with a MultiIndex.
# We then reset the index to maintain a clean structure.
exploded = gdf.explode(index_parts=True).reset_index(drop=True)
return exploded
def process_heritage_data(input_file, output_file, target_crs):
# Load the data
gdf = gpd.read_file(input_file)
# Transform to Egypt's National Grid (EPSG:22992 is often used for Egypt,
# but let's check common ones or if user meant something specific.
# WGS 84 / Egypt Red Belt is EPSG:22992.
# Actually, let's use EPSG:22992 if available or just stick to the standard for Egypt.
# Let's use EPSG:22992 (Egypt Red Belt)
gdf = gdf.to_crs(target_crs)
# Explode Multi-geometries to single-part
gdf = explode_to_single_part(gdf)
# Separate by geometry type
# We need to filter carefully because 'geometry.type' returns 'Point', 'LineString', 'Polygon'
# Note: Multi-parts are already gone after explode.
points = gdf[gdf.geometry.type == 'Point']
lines = gdf[gdf.geometry.type == 'LineString']
polygons = gdf[gdf.geometry.type == 'Polygon']
# Save to GPKG
# We write each layer to the same file
with gpd.GeoDataFrame(columns=gdf.columns, geometry='geometry', crs=target_crs) as driver:
# Use the engine for writing
# To avoid conflict, we'll write them sequentially
pass
# Using a more robust way to write layers to GPKG
points.to_file(output_file, layer='points', driver='GPKG')
lines.to_file(output_file, layer='lines', driver='GPKG')
polygons.to_file(output_file, layer='polygons', driver='GPKG')
print(f"Successfully created {output_file}")
print(f"Points count: {len(points)}")
print(f"Lines count: {len(lines)}")
print(f"Polygons count: {len(polygons)}")
if __name__ == "__main__":
# Egypt National Grid: EPSG:22992 is standard for many parts,
# but let's verify if there's a more generic one or if EPSG:22992 is acceptable.
# EPSG:22992 is Egypt Red Belt.
# Let's use EPSG:22992.
process_heritage_data('heritage_sites.geojson', 'heritage.gpkg', 'EPSG:22992')
Wrote /work/solve.py (2466 chars).
0:48
Bash
python /work/solve.py
Traceback (most recent call last):
File "/work/solve.py", line 56, in <module>
process_heritage_data('heritage_sites.geojson', 'heritage.gpkg', 'EPSG:22992')
~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/work/solve.py", line 36, in process_heritage_data
with gpd.GeoDataFrame(columns=gdf.columns, geometry='geometry', crs=target_crs) as driver:
~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
TypeError: 'geopandas.geodataframe.GeoDataFrame' object does not support the context manager protocol (missed __exit__ method)
0:54
Write
/work/solve.py
content · 39 lines · py
import geopandas as gpd
def explode_to_single_part(gdf):
"""Explodes Multi-geometries into individual single-part geometries."""
# Explode is available in modern geopandas to turn Multi-parts into individual rows
# We use explode(index_parts=False) to ensure we get a clean GeoDataFrame
exploded = gdf.explode(index_parts=False).reset_index(drop=True)
return exploded
def process_heritage_data(input_file, output_file, target_crs):
# Load the data
gdf = gpd.read_file(input_file)
# Transform to Egypt's National Grid (EPSG:22992 is common)
gdf = gdf.to_crs(target_crs)
# Explode Multi-geometries to single-part
gdf = explode_to_single_part(gdf)
# Separate by geometry type
points = gdf[gdf.geometry.type == 'Point'].copy()
lines = gdf[gdf.geometry.type == 'LineString'].copy()
polygons = gdf[gdf.geometry.type == 'Polygon'].copy()
# Save to GPKG
# We write each layer to the same file
points.to_file(output_file, layer='points', driver='GPKG')
lines.to_file(output_file, layer='lines', driver='GPKG')
polygons.to_file(output_file, layer='polygons', driver='GPKG')
print(f"Successfully created {output_file}")
print(f"Points count: {len(points)}")
print(f"Lines count: {len(lines)}")
print(f"Polygons count: {len(polygons)}")
if __name__ == "__main__":
# Egypt Red Belt (EPSG:22992)
process_heritage_data('heritage_sites.geojson', 'heritage.gpkg', 'EPSG:22992')
Wrote /work/solve.py (1493 chars).
0:56
Bash
python /work/solve.py
Successfully created heritage.gpkg Points count: 25 Lines count: 15 Polygons count: 15
1:00
Bash
ogrinfo heritage.gpkg
INFO: Open of `heritage.gpkg'
using driver `GPKG' successful.
1: points (Point)
2: lines (Line String)
3: polygons (Polygon)
1:04
Bash
# No changes needed, the script worked.
# No changes needed, the script worked. # Just confirming the output exists. ls -l heritage.gpkg
-rw-r--r-- 1 agent agent 139264 Jun 18 08:30 heritage.gpkg
1:14