From 5ca9558d0d8dfbd7c45bee6f45b64baf7438d5a1 Mon Sep 17 00:00:00 2001 From: Kraina CI/CD <150701114+kraina-cicd@users.noreply.github.com> Date: Tue, 24 Sep 2024 23:05:29 +0200 Subject: [PATCH] chore(CI/CD): bump version 0.10.0 -> 0.11.0 (#159) * chore(CI/CD): bump version 0.10.0 -> 0.11.0 * docs: update CHANGELOG.md * chore: change geometry reading to be compatible with multiple duckdb versions * fix: keep support for old geopandas api --------- Co-authored-by: Kamil Raczycki --- CHANGELOG.md | 6 +++++- pyproject.toml | 4 ++-- quackosm/__init__.py | 2 +- quackosm/_geopandas_api_version.py | 4 ++++ quackosm/cli.py | 24 +++++++++++++++++++----- quackosm/osm_extracts/__init__.py | 9 +++++++-- quackosm/pbf_file_reader.py | 17 ++++++++++------- tests/base/test_geocoding.py | 6 +++++- 8 files changed, 53 insertions(+), 19 deletions(-) create mode 100644 quackosm/_geopandas_api_version.py diff --git a/CHANGELOG.md b/CHANGELOG.md index da74939..7df1f6c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.11.0] - 2024-09-24 + ### Changed - Bumped minimal DuckDB version to `1.1.0` @@ -381,7 +383,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - Created QuackOSM repository - Implemented PbfFileReader -[Unreleased]: https://github.com/kraina-ai/quackosm/compare/0.10.0...HEAD +[Unreleased]: https://github.com/kraina-ai/quackosm/compare/0.11.0...HEAD + +[0.11.0]: https://github.com/kraina-ai/quackosm/compare/0.10.0...0.11.0 [0.10.0]: https://github.com/kraina-ai/quackosm/compare/0.9.4...0.10.0 diff --git a/pyproject.toml b/pyproject.toml index f256d55..d1ac211 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [project] name = "QuackOSM" -version = "0.10.0" +version = "0.11.0" description = "An open-source tool for reading OpenStreetMap PBF files using DuckDB" authors = [{ name = "Kamil Raczycki", email = "kraczycki@kraina.ai" }] dependencies = [ @@ -173,7 +173,7 @@ close-quotes-on-newline = true wrap-one-line = true [tool.bumpver] -current_version = "0.10.0" +current_version = "0.11.0" version_pattern = "MAJOR.MINOR.PATCH[PYTAGNUM]" commit_message = "chore(CI/CD): bump version {old_version} -> {new_version}" commit = true diff --git a/quackosm/__init__.py b/quackosm/__init__.py index 9ee6437..1223c7f 100644 --- a/quackosm/__init__.py +++ b/quackosm/__init__.py @@ -18,7 +18,7 @@ from quackosm.pbf_file_reader import PbfFileReader __app_name__ = "QuackOSM" -__version__ = "0.10.0" +__version__ = "0.11.0" __all__ = [ "PbfFileReader", diff --git a/quackosm/_geopandas_api_version.py b/quackosm/_geopandas_api_version.py new file mode 100644 index 0000000..6ed3faf --- /dev/null +++ b/quackosm/_geopandas_api_version.py @@ -0,0 +1,4 @@ +import geopandas as gpd +from packaging import version + +GEOPANDAS_NEW_API = version.parse(gpd.__version__) >= version.parse("1.0.0") diff --git a/quackosm/cli.py b/quackosm/cli.py index e9d09ea..14c1397 100644 --- a/quackosm/cli.py +++ b/quackosm/cli.py @@ -8,6 +8,7 @@ import click import typer +from quackosm._geopandas_api_version import GEOPANDAS_NEW_API from quackosm._osm_tags_filters import GroupedOsmTagsFilter, OsmTagsFilter from quackosm.osm_extracts.extract import OsmExtractSource from quackosm.pbf_file_reader import _is_url_path @@ -96,7 +97,10 @@ def convert(self, value, param=None, ctx=None): # type: ignore import geopandas as gpd gdf = gpd.read_file(value) - return gdf.union_all() + if GEOPANDAS_NEW_API: + return gdf.union_all() + else: + return gdf.unary_union except Exception: raise typer.BadParameter("Cannot parse provided geo file") from None @@ -140,9 +144,13 @@ def convert(self, value, param=None, ctx=None): # type: ignore geometries.append( box(minx=bounds["w"], miny=bounds["s"], maxx=bounds["e"], maxy=bounds["n"]) ) - return gpd.GeoSeries(geometries).union_all() + if GEOPANDAS_NEW_API: + return gpd.GeoSeries(geometries).union_all() + else: + return gpd.GeoSeries(geometries).unary_union except Exception: - raise typer.BadParameter(f"Cannot parse provided Geohash value: {geohash}") from None + raise + # raise typer.BadParameter(f"Cannot parse provided Geohash value: {geohash}") from None class H3GeometryParser(click.ParamType): # type: ignore @@ -165,7 +173,10 @@ def convert(self, value, param=None, ctx=None): # type: ignore geometries.append( Polygon([coords[::-1] for coords in h3.cell_to_boundary(h3_cell.strip())]) ) - return gpd.GeoSeries(geometries).union_all() + if GEOPANDAS_NEW_API: + return gpd.GeoSeries(geometries).union_all() + else: + return gpd.GeoSeries(geometries).unary_union except Exception as ex: raise typer.BadParameter(f"Cannot parse provided H3 values: {value}") from ex @@ -190,7 +201,10 @@ def convert(self, value, param=None, ctx=None): # type: ignore geometries.append( Polygon(s2.s2_to_geo_boundary(s2_index.strip(), geo_json_conformant=True)) ) - return gpd.GeoSeries(geometries).union_all() + if GEOPANDAS_NEW_API: + return gpd.GeoSeries(geometries).union_all() + else: + return gpd.GeoSeries(geometries).unary_union except Exception: raise typer.BadParameter(f"Cannot parse provided S2 value: {s2_index}") from None diff --git a/quackosm/osm_extracts/__init__.py b/quackosm/osm_extracts/__init__.py index 3c082da..dcaaa14 100644 --- a/quackosm/osm_extracts/__init__.py +++ b/quackosm/osm_extracts/__init__.py @@ -30,6 +30,7 @@ OsmExtractMultipleMatchesError, OsmExtractZeroMatchesError, ) +from quackosm._geopandas_api_version import GEOPANDAS_NEW_API from quackosm.osm_extracts.bbbike import _get_bbbike_index from quackosm.osm_extracts.extract import OpenStreetMapExtract, OsmExtractSource from quackosm.osm_extracts.extracts_tree import get_available_extracts_as_rich_tree @@ -817,9 +818,13 @@ def _simplify_selected_extracts( ) with warnings.catch_warnings(): warnings.simplefilter("ignore", category=FutureWarning) - other_geometries = matching_extracts.loc[ + other_geometries_gdf = matching_extracts.loc[ sorted_extracts_gdf["id"] != extract_id - ].union_all() + ] + if GEOPANDAS_NEW_API: + other_geometries = other_geometries_gdf.union_all() + else: + other_geometries = other_geometries_gdf.unary_union if extract_geometry.covered_by(other_geometries): extract_to_remove = extract_id simplify_again = True diff --git a/quackosm/pbf_file_reader.py b/quackosm/pbf_file_reader.py index ebe6e7b..a92c78c 100644 --- a/quackosm/pbf_file_reader.py +++ b/quackosm/pbf_file_reader.py @@ -2275,14 +2275,17 @@ def _save_parquet_file_with_geometry( is_empty = not any(file_path.iterdir()) if is_empty: relation.to_parquet(str(file_path / "empty.parquet")) - return self.connection.sql( - f""" - SELECT * REPLACE (ST_GeomFromWKB(geometry) AS geometry) - FROM read_parquet('{file_path}/**') - """ - ) - return self.connection.sql(f"SELECT * FROM read_parquet('{file_path}/**')") + return self.connection.sql( + f""" + SELECT * EXCLUDE(geometry), + CASE WHEN typeof(geometry) = 'GEOMETRY' + THEN geometry::GEOMETRY + ELSE ST_GeomFromWKB(geometry::BLOB) + END AS geometry + FROM read_parquet('{file_path}/**') + """ + ) def _concatenate_results_to_geoparquet( self, diff --git a/tests/base/test_geocoding.py b/tests/base/test_geocoding.py index 76ab1b7..ad4678b 100644 --- a/tests/base/test_geocoding.py +++ b/tests/base/test_geocoding.py @@ -7,6 +7,7 @@ from quackosm import geocode_to_geometry from quackosm._exceptions import QueryNotGeocodedError +from quackosm._geopandas_api_version import GEOPANDAS_NEW_API @pytest.mark.parametrize( # type: ignore @@ -21,7 +22,10 @@ ) def test_geocoding(query: Union[str, list[str]]) -> None: """Test if geocoding works the same as osmnx.""" - assert geocode_to_gdf(query).union_all().equals(geocode_to_geometry(query)) + if GEOPANDAS_NEW_API: + assert geocode_to_gdf(query).union_all().equals(geocode_to_geometry(query)) + else: + assert geocode_to_gdf(query).unary_union.equals(geocode_to_geometry(query)) @pytest.mark.parametrize( # type: ignore