Skip to content

Commit 9865174

Browse files
committed
Fix MultiPolygons not maintaining properties.
1 parent 5d0ac08 commit 9865174

File tree

6 files changed

+84
-5
lines changed

6 files changed

+84
-5
lines changed

geojson_aoi/_async/parser.py

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -195,9 +195,23 @@ async def parse_aoi_async(
195195

196196
elif geojson_parsed.get("type") == "FeatureCollection":
197197
for feature in geojson_parsed.get("features"):
198-
if feature["geometry"]["type"] in valid_geoms:
198+
199+
# Append a copy of the properties list for each coordinate set
200+
# in the MultiPolygon. This ensures the split Polygons maintain
201+
# these properties.
202+
if feature["geometry"]["type"] == "MultiPolygon":
203+
for coordinate in feature["geometry"]["coordinates"]:
204+
properties.append(feature["properties"])
205+
206+
elif feature["geometry"]["type"] in valid_geoms:
199207
properties.append(feature["properties"])
200208

209+
# The same MultiPolygon handling as before. But applied to top-level MultiPolyons
210+
elif geojson_parsed.get("type") == "MultiPolygon":
211+
if feature["geometry"]["type"] == "MultiPolygon":
212+
for coordinate in feature.get("coordinates"):
213+
properties.append(feature["properties"])
214+
201215
# Extract from FeatureCollection
202216
geoms = strip_featcol(geojson_parsed)
203217

geojson_aoi/_sync/parser.py

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -195,9 +195,23 @@ def parse_aoi(
195195

196196
elif geojson_parsed.get("type") == "FeatureCollection":
197197
for feature in geojson_parsed.get("features"):
198-
if feature["geometry"]["type"] in valid_geoms:
198+
199+
# Append a copy of the properties list for each coordinate set
200+
# in the MultiPolygon. This ensures the split Polygons maintain
201+
# these properties.
202+
if feature["geometry"]["type"] == "MultiPolygon":
203+
for coordinate in feature["geometry"]["coordinates"]:
204+
properties.append(feature["properties"])
205+
206+
elif feature["geometry"]["type"] in valid_geoms:
199207
properties.append(feature["properties"])
200208

209+
# The same MultiPolygon handling as before. But applied to top-level MultiPolyons
210+
elif geojson_parsed.get("type") == "MultiPolygon":
211+
if feature["geometry"]["type"] == "MultiPolygon":
212+
for coordinate in feature.get("coordinates"):
213+
properties.append(feature["properties"])
214+
201215
# Extract from FeatureCollection
202216
geoms = strip_featcol(geojson_parsed)
203217

@@ -208,6 +222,9 @@ def parse_aoi(
208222
# Remove any properties that PostGIS might have assigned.
209223
for feature in result.featcol["features"]:
210224
feature.pop("properties", None)
225+
226+
# TODO: Parser breaks when properties and result.featcol['features'] arent't equal
227+
# print(f"Properties: {len(properties)}\n Results: {len(result.featcol['features'])}")
211228

212229
# Restore saved properties.
213230
if properties:

geojson_aoi/_sync/postgis.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,9 @@ class PostGis:
3434
Can reuse an existing upstream connection.
3535
"""
3636

37-
def __init__(self, db: str | Connection, geoms: list[GeoJSON], merge: bool = False):
37+
def __init__(
38+
self, db: str | Connection, geoms: list[GeoJSON], merge: bool = False
39+
):
3840
"""Initialise variables and compose classes."""
3941
self.table_id = uuid4().hex
4042
self.geoms = geoms

tests/_async/test_parser.py

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -320,7 +320,11 @@ async def test_featurecollection_mixed_geoms(db, featurecollection_mixed_geoms):
320320
}
321321

322322

323-
# TODO: Add test case for FeatureCollection with a mix of features with properties
323+
async def test_featurecollection_multi_props(db, featurecollection_multipolygon_properties):
324+
"""Test a FeatureCollection that contatins a MultiPolygon Feature with properties."""
325+
result = await parse_aoi_async(db, featurecollection_multipolygon_properties)
326+
327+
assert result["features"]["properties"] == {"id": 1}
324328

325329

326330
async def test_invalid_input(db):

tests/_sync/test_parser.py

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -320,6 +320,13 @@ def test_featurecollection_mixed_geoms(db, featurecollection_mixed_geoms):
320320
}
321321

322322

323+
def test_featurecollection_multi_props(db, featurecollection_multipolygon_properties):
324+
"""Test a FeatureCollection that contatins a MultiPolygon Feature with properties."""
325+
result = parse_aoi(db, featurecollection_multipolygon_properties)
326+
327+
assert result["features"]["properties"] == {"id": 1}
328+
329+
323330
def test_invalid_input(db):
324331
"""Invalud input for parse_aoi function."""
325332
with pytest.raises(
@@ -422,7 +429,10 @@ def test_warnings_raised_invalid_coords(db):
422429
"properties": {},
423430
}
424431
],
425-
"crs": {"type": "name", "properties": {"name": "urn:ogc:def:crs:EPSG::4326"}},
432+
"crs": {
433+
"type": "name",
434+
"properties": {"name": "urn:ogc:def:crs:EPSG::4326"},
435+
},
426436
}
427437
with pytest.warns(UserWarning):
428438
parse_aoi(db, geojson_data)

tests/conftest.py

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -298,3 +298,35 @@ def featurecollection_mixed_geoms():
298298
},
299299
],
300300
}
301+
302+
@pytest_asyncio.fixture
303+
def featurecollection_multipolygon_properties():
304+
"""FeatureCollection containing a MultiPolygon with properties."""
305+
return {
306+
"type" : "FeatureCollection",
307+
"features": [
308+
{
309+
"type": "Feature",
310+
"properties": {
311+
"id": 1,
312+
},
313+
"geometry": {
314+
"type": "MultiPolygon",
315+
"coordinates": [
316+
[[[40.0, 40.0], [20.0, 45.0], [45.0, 30.0], [40.0, 40.0]]],
317+
[
318+
[
319+
[20.0, 35.0],
320+
[10.0, 30.0],
321+
[10.0, 10.0],
322+
[30.0, 5.0],
323+
[45.0, 20.0],
324+
[20.0, 35.0],
325+
],
326+
[[30.0, 20.0], [20.0, 15.0], [20.0, 25.0], [30.0, 20.0]],
327+
],
328+
],
329+
}
330+
}
331+
]
332+
}

0 commit comments

Comments
 (0)