Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package python-Shapely for openSUSE:Factory 
checked in at 2024-05-06 17:53:15
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-Shapely (Old)
 and      /work/SRC/openSUSE:Factory/.python-Shapely.new.1880 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "python-Shapely"

Mon May  6 17:53:15 2024 rev:26 rq:1171977 version:2.0.4

Changes:
--------
--- /work/SRC/openSUSE:Factory/python-Shapely/python-Shapely.changes    
2023-12-17 21:36:15.910174424 +0100
+++ /work/SRC/openSUSE:Factory/.python-Shapely.new.1880/python-Shapely.changes  
2024-05-06 17:53:33.127739374 +0200
@@ -1,0 +2,17 @@
+Sun May  5 11:01:36 UTC 2024 - Ben Greiner <c...@bnavigator.de>
+
+- Update to 2.0.4
+  * Fix bug in ``to_wkt`` with multiple empty Z geometries (#2012).
+  * Fix bug in ``to_ragged_array`` for an array of Points with
+    missing values (#2034).
+  * Compatibility with numpy 2
+- Release 2.0.3
+  * Fix regression in the ``oriented_envelope`` ufunc to accept
+    array-like input in case of GEOS<3.12 (#1929).
+  * The binary wheels are not yet compatible with a future NumPy
+    2.0 release, therefore a ``numpy<2`` upper pin was added to the
+    requirements (#1972).
+  * Upgraded the GEOS version in the binary wheel distributions to
+    3.11.3.
+
+-------------------------------------------------------------------

Old:
----
  shapely-2.0.2.tar.gz

New:
----
  shapely-2.0.4.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ python-Shapely.spec ++++++
--- /var/tmp/diff_new_pack.lsE63s/_old  2024-05-06 17:53:33.727761257 +0200
+++ /var/tmp/diff_new_pack.lsE63s/_new  2024-05-06 17:53:33.731761403 +0200
@@ -1,7 +1,7 @@
 #
 # spec file for package python-Shapely
 #
-# Copyright (c) 2023 SUSE LLC
+# Copyright (c) 2024 SUSE LLC
 #
 # All modifications and additions to the file contributed by third parties
 # remain the property of their copyright owners, unless otherwise agreed
@@ -18,7 +18,7 @@
 
 %{?sle15_python_module_pythons}
 Name:           python-Shapely
-Version:        2.0.2
+Version:        2.0.4
 Release:        0
 Summary:        Geospatial geometries, predicates, and operations
 License:        BSD-3-Clause
@@ -26,7 +26,7 @@
 Source:         
https://files.pythonhosted.org/packages/source/s/shapely/shapely-%{version}.tar.gz
 BuildRequires:  %{python_module Cython >= 0.29 with %python-Cython < 3}
 BuildRequires:  %{python_module devel >= 3.8}
-BuildRequires:  %{python_module numpy-devel >= 1.16}
+BuildRequires:  %{python_module numpy-devel >= 1.25}
 BuildRequires:  %{python_module pip}
 BuildRequires:  %{python_module setuptools}
 BuildRequires:  %{python_module wheel}
@@ -45,7 +45,7 @@
 # (libgeos_c1 is detected due to some Cython optimized lib, but libgeos3 is 
not)
 # use requires_eq in order to be detectable by the python_subpackages rewriter
 %requires_eq    %(rpm -q --requires geos-devel | grep libgeos)
-Requires:       python-numpy >= 1.16
+Requires:       (python-numpy >= 1.14 with python-numpy < 3)
 Provides:       python-shapely = %{version}-%{release}
 Obsoletes:      python-shapely < %{version}-%{release}
 %python_subpackages

++++++ shapely-2.0.2.tar.gz -> shapely-2.0.4.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/CHANGES.txt 
new/shapely-2.0.4/CHANGES.txt
--- old/shapely-2.0.2/CHANGES.txt       2023-10-12 22:06:28.000000000 +0200
+++ new/shapely-2.0.4/CHANGES.txt       2024-04-17 00:00:57.000000000 +0200
@@ -1,6 +1,26 @@
 Changes
 =======
 
+2.0.4 (2024-04-16)
+------------------
+
+Wheels for Python versions >= 3.9 will be compatible with the upcoming NumPy 
2.0
+release (as well as with supported NumPy 1.x versions).
+
+Bug fixes:
+
+- Fix bug in ``to_wkt`` with multiple empty Z geometries (#2012).
+- Fix bug in ``to_ragged_array`` for an array of Points with missing values 
(#2034).
+
+2.0.3 (2024-02-16)
+------------------
+
+- Fix regression in the ``oriented_envelope`` ufunc to accept array-like input
+  in case of GEOS<3.12 (#1929).
+- The binary wheels are not yet compatible with a future NumPy 2.0 release,
+  therefore a ``numpy<2`` upper pin was added to the requirements (#1972).
+- Upgraded the GEOS version in the binary wheel distributions to 3.11.3.
+
 2.0.2 (2023-10-12)
 ------------------
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/CITATION.cff 
new/shapely-2.0.4/CITATION.cff
--- old/shapely-2.0.2/CITATION.cff      2023-10-12 22:06:28.000000000 +0200
+++ new/shapely-2.0.4/CITATION.cff      2024-04-17 00:00:57.000000000 +0200
@@ -2,8 +2,8 @@
 message: "Please cite this software using these metadata."
 type: software
 title: Shapely
-version: "2.0.2"
-date-released: "2023-10-12"
+version: "2.0.4"
+date-released: "2024-04-16"
 doi: 10.5281/zenodo.5597138
 abstract: "Manipulation and analysis of geometric objects in the Cartesian 
plane."
 repository-artifact: https://pypi.org/project/Shapely
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/PKG-INFO new/shapely-2.0.4/PKG-INFO
--- old/shapely-2.0.2/PKG-INFO  2023-10-12 22:06:51.502693000 +0200
+++ new/shapely-2.0.4/PKG-INFO  2024-04-17 00:01:12.009678400 +0200
@@ -1,6 +1,6 @@
 Metadata-Version: 2.1
 Name: shapely
-Version: 2.0.2
+Version: 2.0.4
 Summary: Manipulation and analysis of geometric objects
 Author: Sean Gillies
 Maintainer: Shapely contributors
@@ -26,7 +26,7 @@
 Requires-Python: >=3.7
 Description-Content-Type: text/x-rst
 License-File: LICENSE.txt
-Requires-Dist: numpy>=1.14
+Requires-Dist: numpy<3,>=1.14
 Provides-Extra: test
 Requires-Dist: pytest; extra == "test"
 Requires-Dist: pytest-cov; extra == "test"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/pyproject.toml 
new/shapely-2.0.4/pyproject.toml
--- old/shapely-2.0.2/pyproject.toml    2023-10-12 22:06:28.000000000 +0200
+++ new/shapely-2.0.4/pyproject.toml    2024-04-17 00:00:57.000000000 +0200
@@ -1,7 +1,12 @@
 [build-system]
 requires = [
     "Cython",
-    "oldest-supported-numpy",
+    # Starting with NumPy 1.25, NumPy is (by default) as far back compatible
+    # as oldest-support-numpy was (customizable with a NPY_TARGET_VERSION
+    # define).  For older Python versions (where NumPy 1.25 is not yet 
avaiable)
+    # continue using oldest-support-numpy.
+    "oldest-supported-numpy; python_version<'3.9'",
+    "numpy>=1.25; python_version>='3.9'",
     "setuptools>=61.0.0",
 ]
 build-backend = "setuptools.build_meta"
@@ -38,7 +43,7 @@
 ]
 requires-python = ">=3.7"
 dependencies = [
-    "numpy>=1.14",
+    "numpy>=1.14,<3",
 ]
 
 [project.optional-dependencies]
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/_ragged_array.py 
new/shapely-2.0.4/shapely/_ragged_array.py
--- old/shapely-2.0.2/shapely/_ragged_array.py  2023-10-12 22:06:28.000000000 
+0200
+++ new/shapely-2.0.4/shapely/_ragged_array.py  2024-04-17 00:00:57.000000000 
+0200
@@ -37,7 +37,7 @@
     get_type_id,
 )
 from shapely.coordinates import get_coordinates
-from shapely.predicates import is_empty
+from shapely.predicates import is_empty, is_missing
 
 __all__ = ["to_ragged_array", "from_ragged_array"]
 
@@ -50,7 +50,8 @@
     coords = get_coordinates(arr, include_z=include_z)
 
     # empty points are represented by NaNs
-    empties = is_empty(arr)
+    # + missing geometries should also be present with some value
+    empties = is_empty(arr) | is_missing(arr)
     if empties.any():
         indices = np.nonzero(empties)[0]
         indices = indices - np.arange(len(indices))
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/_version.py 
new/shapely-2.0.4/shapely/_version.py
--- old/shapely-2.0.2/shapely/_version.py       2023-10-12 22:06:51.502693000 
+0200
+++ new/shapely-2.0.4/shapely/_version.py       2024-04-17 00:01:12.009678400 
+0200
@@ -8,11 +8,11 @@
 
 version_json = '''
 {
- "date": "2023-10-12T21:49:31+0200",
+ "date": "2024-04-16T23:57:44+0200",
  "dirty": false,
  "error": null,
- "full-revisionid": "8d45d434037267ba9b1f1de409d1b5396d6c9219",
- "version": "2.0.2"
+ "full-revisionid": "3853e1170173125b7e86cbb5cc8dab1c274c3999",
+ "version": "2.0.4"
 }
 '''  # END VERSION_JSON
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/shapely-2.0.2/shapely/algorithms/_oriented_envelope.py 
new/shapely-2.0.4/shapely/algorithms/_oriented_envelope.py
--- old/shapely-2.0.2/shapely/algorithms/_oriented_envelope.py  2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/algorithms/_oriented_envelope.py  2024-04-17 
00:00:57.000000000 +0200
@@ -17,8 +17,6 @@
     """
     if geometry is None:
         return None
-    if not hasattr(geometry, "geom_type"):
-        return np.array([_oriented_envelope_min_area(g) for g in geometry])
     if geometry.is_empty:
         return shapely.from_wkt("POLYGON EMPTY")
 
@@ -53,3 +51,8 @@
     # check for the minimum area rectangle and return it
     transf_rect, inv_matrix = min(_transformed_rects(), key=lambda r: 
r[0].area)
     return affine_transform(transf_rect, inv_matrix)
+
+
+_oriented_envelope_min_area_vectorized = np.frompyfunc(
+    _oriented_envelope_min_area, 1, 1
+)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/constructive.py 
new/shapely-2.0.4/shapely/constructive.py
--- old/shapely-2.0.2/shapely/constructive.py   2023-10-12 22:06:28.000000000 
+0200
+++ new/shapely-2.0.4/shapely/constructive.py   2024-04-17 00:00:57.000000000 
+0200
@@ -2,7 +2,7 @@
 
 from shapely import lib
 from shapely._enum import ParamEnum
-from shapely.algorithms._oriented_envelope import _oriented_envelope_min_area
+from shapely.algorithms._oriented_envelope import 
_oriented_envelope_min_area_vectorized
 from shapely.decorators import multithreading_enabled, requires_geos
 
 __all__ = [
@@ -1028,7 +1028,7 @@
     <POLYGON EMPTY>
     """
     if lib.geos_version < (3, 12, 0):
-        f = _oriented_envelope_min_area
+        f = _oriented_envelope_min_area_vectorized
     else:
         f = _oriented_envelope_geos
     return f(geometry, **kwargs)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/decorators.py 
new/shapely-2.0.4/shapely/decorators.py
--- old/shapely-2.0.2/shapely/decorators.py     2023-10-12 22:06:28.000000000 
+0200
+++ new/shapely-2.0.4/shapely/decorators.py     2024-04-17 00:00:57.000000000 
+0200
@@ -39,7 +39,7 @@
             # Insert the message at the first double newline
             position = doc.find("\n\n") + 2
             # Figure out the indentation level
-            indent = 2
+            indent = 0
             while True:
                 if doc[position + indent] == " ":
                     indent += 1
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/geometry/polygon.py 
new/shapely-2.0.4/shapely/geometry/polygon.py
--- old/shapely-2.0.2/shapely/geometry/polygon.py       2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/geometry/polygon.py       2024-04-17 
00:00:57.000000000 +0200
@@ -10,7 +10,7 @@
 from shapely.geometry.linestring import LineString
 from shapely.geometry.point import Point
 
-__all__ = ["Polygon", "LinearRing"]
+__all__ = ["orient", "Polygon", "LinearRing"]
 
 
 def _unpickle_linearring(wkb):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/testing.py 
new/shapely-2.0.4/shapely/testing.py
--- old/shapely-2.0.2/shapely/testing.py        2023-10-12 22:06:28.000000000 
+0200
+++ new/shapely-2.0.4/shapely/testing.py        2024-04-17 00:00:57.000000000 
+0200
@@ -106,8 +106,8 @@
     if normalize:
         x = shapely.normalize(x)
         y = shapely.normalize(y)
-    x = np.array(x, copy=False)
-    y = np.array(y, copy=False)
+    x = np.asarray(x)
+    y = np.asarray(y)
 
     is_scalar = x.ndim == 0 or y.ndim == 0
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/common.py 
new/shapely-2.0.4/shapely/tests/common.py
--- old/shapely-2.0.2/shapely/tests/common.py   2023-10-12 22:06:28.000000000 
+0200
+++ new/shapely-2.0.4/shapely/tests/common.py   2024-04-17 00:00:57.000000000 
+0200
@@ -92,3 +92,34 @@
 
 with ignore_invalid():
     line_string_nan = shapely.LineString([(np.nan, np.nan), (np.nan, np.nan)])
+
+
+class ArrayLike:
+    """
+    Simple numpy Array like class that implements the
+    ufunc protocol.
+    """
+
+    def __init__(self, array):
+        self._array = np.asarray(array)
+
+    def __len__(self):
+        return len(self._array)
+
+    def __getitem(self, key):
+        return self._array[key]
+
+    def __iter__(self):
+        return self._array.__iter__()
+
+    def __array__(self):
+        return np.asarray(self._array)
+
+    def __array_ufunc__(self, ufunc, method, *inputs, **kwargs):
+        if method == "__call__":
+            inputs = [
+                arg._array if isinstance(arg, self.__class__) else arg for arg 
in inputs
+            ]
+            return self.__class__(ufunc(*inputs, **kwargs))
+        else:
+            return NotImplemented
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/geometry/test_format.py 
new/shapely-2.0.4/shapely/tests/geometry/test_format.py
--- old/shapely-2.0.2/shapely/tests/geometry/test_format.py     2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/tests/geometry/test_format.py     2024-04-17 
00:00:57.000000000 +0200
@@ -84,23 +84,28 @@
     assert format(poly, "X") == poly.wkb_hex
 
     # Use f-strings with extra characters and rounding precision
-    assert f"<{poly:.2f}>" == (
-        "<POLYGON ((10.00 0.00, 7.07 -7.07, 0.00 -10.00, -7.07 -7.07, "
-        "-10.00 -0.00, -7.07 7.07, -0.00 10.00, 7.07 7.07, 10.00 0.00))>"
-    )
+    if geos_version < (3, 13, 0):
+        assert f"<{poly:.2f}>" == (
+            "<POLYGON ((10.00 0.00, 7.07 -7.07, 0.00 -10.00, -7.07 -7.07, "
+            "-10.00 -0.00, -7.07 7.07, -0.00 10.00, 7.07 7.07, 10.00 0.00))>"
+        )
+    else:
+        assert f"<{poly:.2f}>" == (
+            "<POLYGON ((10.00 0.00, 7.07 -7.07, 0.00 -10.00, -7.07 -7.07, "
+            "-10.00 0.00, -7.07 7.07, 0.00 10.00, 7.07 7.07, 10.00 0.00))>"
+        )
 
     # 'g' format varies depending on GEOS version
     if geos_version < (3, 10, 0):
-        expected_2G = (
+        assert f"{poly:.2G}" == (
             "POLYGON ((10 0, 7.1 -7.1, 1.6E-14 -10, -7.1 -7.1, "
             "-10 -3.2E-14, -7.1 7.1, -4.6E-14 10, 7.1 7.1, 10 0))"
         )
     else:
-        expected_2G = (
+        assert f"{poly:.2G}" == (
             "POLYGON ((10 0, 7.07 -7.07, 0 -10, -7.07 -7.07, "
             "-10 0, -7.07 7.07, 0 10, 7.07 7.07, 10 0))"
         )
-    assert f"{poly:.2G}" == expected_2G
 
     # check empty
     empty = Polygon()
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/test_constructive.py 
new/shapely-2.0.4/shapely/tests/test_constructive.py
--- old/shapely-2.0.2/shapely/tests/test_constructive.py        2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/tests/test_constructive.py        2024-04-17 
00:00:57.000000000 +0200
@@ -17,6 +17,7 @@
 from shapely.testing import assert_geometries_equal
 from shapely.tests.common import (
     all_types,
+    ArrayLike,
     empty,
     empty_line_string,
     empty_point,
@@ -981,6 +982,17 @@
         assert_geometries_equal(actual, expected, normalize=True, 
tolerance=1e-3)
 
 
+def test_oriented_evelope_array_like():
+    # https://github.com/shapely/shapely/issues/1929
+    # because we have a custom python implementation, need to ensure this has
+    # the same capabilities as numpy ufuncs to work with array-likes
+    geometries = [Point(1, 1).buffer(1), Point(2, 2).buffer(1)]
+    actual = shapely.oriented_envelope(ArrayLike(geometries))
+    assert isinstance(actual, ArrayLike)
+    expected = shapely.oriented_envelope(geometries)
+    assert_geometries_equal(np.asarray(actual), expected)
+
+
 @pytest.mark.skipif(shapely.geos_version < (3, 11, 0), reason="GEOS < 3.11")
 def test_concave_hull_kwargs():
     p = Point(10, 10)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/test_io.py 
new/shapely-2.0.4/shapely/tests/test_io.py
--- old/shapely-2.0.2/shapely/tests/test_io.py  2023-10-12 22:06:28.000000000 
+0200
+++ new/shapely-2.0.4/shapely/tests/test_io.py  2024-04-17 00:00:57.000000000 
+0200
@@ -287,6 +287,15 @@
     assert shapely.to_wkt(None) is None
 
 
+def test_to_wkt_array_with_empty_z():
+    # See GH-2004
+    empty_wkt = ["POINT Z EMPTY", None, "POLYGON Z EMPTY"]
+    empty_geoms = shapely.from_wkt(empty_wkt)
+    if shapely.geos_version < (3, 9, 0):
+        empty_wkt = ["POINT EMPTY", None, "POLYGON EMPTY"]
+    assert list(shapely.to_wkt(empty_geoms)) == empty_wkt
+
+
 def test_to_wkt_exceptions():
     with pytest.raises(TypeError):
         shapely.to_wkt(1)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/test_misc.py 
new/shapely-2.0.4/shapely/tests/test_misc.py
--- old/shapely-2.0.2/shapely/tests/test_misc.py        2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/tests/test_misc.py        2024-04-17 
00:00:57.000000000 +0200
@@ -1,5 +1,6 @@
 import os
 import sys
+from inspect import cleandoc
 from itertools import chain
 from string import ascii_letters, digits
 from unittest import mock
@@ -83,13 +84,22 @@
         """
 
 
-expected_docstring = """Docstring that will be mocked.
+def expected_docstring(**kwds):
+    doc = """Docstring that will be mocked.
 {indent}A multiline.
 
 {indent}.. note:: 'func' requires at least GEOS {version}.
 
 {indent}Some description.
-{indent}"""
+{indent}""".format(
+        **kwds
+    )
+    if sys.version_info[:2] >= (3, 13):
+        # There are subtle differences between inspect.cleandoc() and
+        # _PyCompile_CleanDoc(). Most significantly, the latter does not remove
+        # leading or trailing blank lines.
+        return cleandoc(doc) + "\n"
+    return doc
 
 
 @pytest.mark.parametrize("version", ["3.7.0", "3.7.1", "3.6.2"])
@@ -104,7 +114,7 @@
     with pytest.raises(shapely.errors.UnsupportedGEOSVersionError):
         wrapped()
 
-    assert wrapped.__doc__ == expected_docstring.format(version=version, 
indent=" " * 4)
+    assert wrapped.__doc__ == expected_docstring(version=version, indent=" " * 
4)
 
 
 @pytest.mark.parametrize("version", ["3.6.0", "3.8.0"])
@@ -112,7 +122,7 @@
     """The requires_geos decorator always adapts the docstring."""
     wrapped = requires_geos(version)(func)
 
-    assert wrapped.__doc__ == expected_docstring.format(version=version, 
indent=" " * 4)
+    assert wrapped.__doc__ == expected_docstring(version=version, indent=" " * 
4)
 
 
 @pytest.mark.parametrize("version", ["3.6.0", "3.8.0"])
@@ -120,7 +130,7 @@
     """The requires_geos decorator adjusts methods docstrings correctly"""
     wrapped = requires_geos(version)(SomeClass.func)
 
-    assert wrapped.__doc__ == expected_docstring.format(version=version, 
indent=" " * 8)
+    assert wrapped.__doc__ == expected_docstring(version=version, indent=" " * 
8)
 
 
 @multithreading_enabled
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/test_ragged_array.py 
new/shapely-2.0.4/shapely/tests/test_ragged_array.py
--- old/shapely-2.0.2/shapely/tests/test_ragged_array.py        2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/tests/test_ragged_array.py        2024-04-17 
00:00:57.000000000 +0200
@@ -110,18 +110,30 @@
             "POINT EMPTY",
             "POINT EMPTY",
             "POINT (4 4)",
+            None,
             "POINT EMPTY",
         ]
     )
     typ, result, offsets = shapely.to_ragged_array(arr)
     expected = np.array(
-        [[0, 0], [1, 1], [np.nan, np.nan], [np.nan, np.nan], [4, 4], [np.nan, 
np.nan]]
+        [
+            [0, 0],
+            [1, 1],
+            [np.nan, np.nan],
+            [np.nan, np.nan],
+            [4, 4],
+            [np.nan, np.nan],
+            [np.nan, np.nan],
+        ]
     )
     assert typ == shapely.GeometryType.POINT
+    assert len(result) == len(arr)
     assert_allclose(result, expected)
     assert len(offsets) == 0
 
     geoms = shapely.from_ragged_array(typ, result)
+    # in a roundtrip, missing geometries come back as empty
+    arr[-2] = shapely.from_wkt("POINT EMPTY")
     assert_geometries_equal(geoms, arr)
 
 
@@ -133,6 +145,7 @@
             "LINESTRING EMPTY",
             "LINESTRING EMPTY",
             "LINESTRING (10 10, 20 20, 10 40)",
+            None,
             "LINESTRING EMPTY",
         ]
     )
@@ -151,13 +164,15 @@
             [10.0, 40.0],
         ]
     )
-    expected_offsets = np.array([0, 3, 7, 7, 7, 10, 10])
+    expected_offsets = np.array([0, 3, 7, 7, 7, 10, 10, 10])
     assert typ == shapely.GeometryType.LINESTRING
     assert_allclose(coords, expected)
     assert len(offsets) == 1
     assert_allclose(offsets[0], expected_offsets)
 
     result = shapely.from_ragged_array(typ, coords, offsets)
+    # in a roundtrip, missing geometries come back as empty
+    arr[-2] = shapely.from_wkt("LINESTRING EMPTY")
     assert_geometries_equal(result, arr)
 
 
@@ -169,6 +184,7 @@
             "POLYGON EMPTY",
             "POLYGON EMPTY",
             "POLYGON ((30 10, 40 40, 20 40, 10 20, 30 10))",
+            None,
             "POLYGON EMPTY",
         ]
     )
@@ -197,7 +213,7 @@
         ]
     )
     expected_offsets1 = np.array([0, 5, 10, 14, 19])
-    expected_offsets2 = np.array([0, 1, 3, 3, 3, 4, 4])
+    expected_offsets2 = np.array([0, 1, 3, 3, 3, 4, 4, 4])
 
     assert typ == shapely.GeometryType.POLYGON
     assert_allclose(coords, expected)
@@ -206,6 +222,8 @@
     assert_allclose(offsets[1], expected_offsets2)
 
     result = shapely.from_ragged_array(typ, coords, offsets)
+    # in a roundtrip, missing geometries come back as empty
+    arr[-2] = shapely.from_wkt("POLYGON EMPTY")
     assert_geometries_equal(result, arr)
 
 
@@ -217,6 +235,7 @@
             "MULTIPOINT EMPTY",
             "MULTIPOINT EMPTY",
             "MULTIPOINT (30 10, 10 30, 40 40)",
+            None,
             "MULTIPOINT EMPTY",
         ]
     )
@@ -233,7 +252,7 @@
             [40.0, 40.0],
         ]
     )
-    expected_offsets = np.array([0, 4, 5, 5, 5, 8, 8])
+    expected_offsets = np.array([0, 4, 5, 5, 5, 8, 8, 8])
 
     assert typ == shapely.GeometryType.MULTIPOINT
     assert_allclose(coords, expected)
@@ -241,6 +260,8 @@
     assert_allclose(offsets[0], expected_offsets)
 
     result = shapely.from_ragged_array(typ, coords, offsets)
+    # in a roundtrip, missing geometries come back as empty
+    arr[-2] = shapely.from_wkt("MULTIPOINT EMPTY")
     assert_geometries_equal(result, arr)
 
 
@@ -252,6 +273,7 @@
             "MULTILINESTRING EMPTY",
             "MULTILINESTRING EMPTY",
             "MULTILINESTRING ((35 10, 45 45), (15 40, 10 20), (30 10, 10 30, 
40 40))",
+            None,
             "MULTILINESTRING EMPTY",
         ]
     )
@@ -278,7 +300,7 @@
         ]
     )
     expected_offsets1 = np.array([0, 3, 6, 10, 12, 14, 17])
-    expected_offsets2 = np.array([0, 1, 3, 3, 3, 6, 6])
+    expected_offsets2 = np.array([0, 1, 3, 3, 3, 6, 6, 6])
 
     assert typ == shapely.GeometryType.MULTILINESTRING
     assert_allclose(coords, expected)
@@ -287,6 +309,8 @@
     assert_allclose(offsets[1], expected_offsets2)
 
     result = shapely.from_ragged_array(typ, coords, offsets)
+    # in a roundtrip, missing geometries come back as empty
+    arr[-2] = shapely.from_wkt("MULTILINESTRING EMPTY")
     assert_geometries_equal(result, arr)
 
 
@@ -298,6 +322,7 @@
             "MULTIPOLYGON EMPTY",
             "MULTIPOLYGON EMPTY",
             "MULTIPOLYGON (((40 40, 20 45, 45 30, 40 40)))",
+            None,
             "MULTIPOLYGON EMPTY",
         ]
     )
@@ -335,7 +360,7 @@
     )
     expected_offsets1 = np.array([0, 5, 9, 13, 19, 23, 27])
     expected_offsets2 = np.array([0, 2, 3, 5, 6])
-    expected_offsets3 = np.array([0, 1, 3, 3, 3, 4, 4])
+    expected_offsets3 = np.array([0, 1, 3, 3, 3, 4, 4, 4])
 
     assert typ == shapely.GeometryType.MULTIPOLYGON
     assert_allclose(coords, expected)
@@ -345,6 +370,8 @@
     assert_allclose(offsets[2], expected_offsets3)
 
     result = shapely.from_ragged_array(typ, coords, offsets)
+    # in a roundtrip, missing geometries come back as empty
+    arr[-2] = shapely.from_wkt("MULTIPOLYGON EMPTY")
     assert_geometries_equal(result, arr)
 
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/test_set_operations.py 
new/shapely-2.0.4/shapely/tests/test_set_operations.py
--- old/shapely-2.0.2/shapely/tests/test_set_operations.py      2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/tests/test_set_operations.py      2024-04-17 
00:00:57.000000000 +0200
@@ -53,6 +53,13 @@
 @pytest.mark.parametrize("a", all_types)
 @pytest.mark.parametrize("func", SET_OPERATIONS)
 def test_set_operation_array(a, func):
+    if (
+        func is shapely.difference
+        and a.geom_type == "GeometryCollection"
+        and shapely.get_num_geometries(a) == 2
+        and shapely.geos_version == (3, 9, 5)
+    ):
+        pytest.xfail("GEOS 3.9.5 crashes with mixed collection")
     actual = func(a, point)
     assert isinstance(actual, Geometry)
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely/tests/test_strtree.py 
new/shapely-2.0.4/shapely/tests/test_strtree.py
--- old/shapely-2.0.2/shapely/tests/test_strtree.py     2023-10-12 
22:06:28.000000000 +0200
+++ new/shapely-2.0.4/shapely/tests/test_strtree.py     2024-04-17 
00:00:57.000000000 +0200
@@ -10,7 +10,7 @@
 from numpy.testing import assert_array_equal
 
 import shapely
-from shapely import box, geos_version, MultiPoint, Point, STRtree
+from shapely import box, geos_version, LineString, MultiPoint, Point, STRtree
 from shapely.errors import UnsupportedGEOSVersionError
 from shapely.testing import assert_geometries_equal
 from shapely.tests.common import (
@@ -928,12 +928,12 @@
         # box contains points but touches only those at edges
         (box(3, 3, 6, 6), [3, 6]),
         ([box(3, 3, 6, 6)], [[0, 0], [3, 6]]),
-        # buffer completely contains point in tree
+        # polygon completely contains point in tree
         (shapely.buffer(Point(3, 3), 1), []),
         ([shapely.buffer(Point(3, 3), 1)], [[], []]),
-        # buffer intersects 2 points but touches only one
-        (shapely.buffer(Point(0, 1), 1), [1]),
-        ([shapely.buffer(Point(0, 1), 1)], [[0], [1]]),
+        # linestring intersects 2 points but touches only one
+        (LineString([(-1, -1), (1, 1)]), [1]),
+        ([LineString([(-1, -1), (1, 1)])], [[0], [1]]),
         # multipoints intersect but not valid relation
         (MultiPoint([[5, 5], [7, 7]]), []),
         ([MultiPoint([[5, 5], [7, 7]])], [[], []]),
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely.egg-info/PKG-INFO 
new/shapely-2.0.4/shapely.egg-info/PKG-INFO
--- old/shapely-2.0.2/shapely.egg-info/PKG-INFO 2023-10-12 22:06:51.000000000 
+0200
+++ new/shapely-2.0.4/shapely.egg-info/PKG-INFO 2024-04-17 00:01:11.000000000 
+0200
@@ -1,6 +1,6 @@
 Metadata-Version: 2.1
 Name: shapely
-Version: 2.0.2
+Version: 2.0.4
 Summary: Manipulation and analysis of geometric objects
 Author: Sean Gillies
 Maintainer: Shapely contributors
@@ -26,7 +26,7 @@
 Requires-Python: >=3.7
 Description-Content-Type: text/x-rst
 License-File: LICENSE.txt
-Requires-Dist: numpy>=1.14
+Requires-Dist: numpy<3,>=1.14
 Provides-Extra: test
 Requires-Dist: pytest; extra == "test"
 Requires-Dist: pytest-cov; extra == "test"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/shapely.egg-info/requires.txt 
new/shapely-2.0.4/shapely.egg-info/requires.txt
--- old/shapely-2.0.2/shapely.egg-info/requires.txt     2023-10-12 
22:06:51.000000000 +0200
+++ new/shapely-2.0.4/shapely.egg-info/requires.txt     2024-04-17 
00:01:11.000000000 +0200
@@ -1,4 +1,4 @@
-numpy>=1.14
+numpy<3,>=1.14
 
 [docs]
 numpydoc==1.1.*
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/shapely-2.0.2/src/ufuncs.c 
new/shapely-2.0.4/src/ufuncs.c
--- old/shapely-2.0.2/src/ufuncs.c      2023-10-12 22:06:28.000000000 +0200
+++ new/shapely-2.0.4/src/ufuncs.c      2024-04-17 00:00:57.000000000 +0200
@@ -3351,8 +3351,9 @@
         goto finish;
       }
       if (wkt != NULL) {
+        Py_XDECREF(*out);
         *out = PyUnicode_FromString(wkt);
-        goto finish;
+        continue;
       }
 
 #else

Reply via email to