pyogrio 0.10.0__cp313-cp313-macosx_12_0_arm64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of pyogrio might be problematic. Click here for more details.

Files changed (223) hide show
  1. pyogrio/.dylibs/libgdal.35.3.9.1.dylib +0 -0
  2. pyogrio/__init__.py +55 -0
  3. pyogrio/_compat.py +47 -0
  4. pyogrio/_env.py +59 -0
  5. pyogrio/_err.cpython-313-darwin.so +0 -0
  6. pyogrio/_geometry.cpython-313-darwin.so +0 -0
  7. pyogrio/_io.cpython-313-darwin.so +0 -0
  8. pyogrio/_ogr.cpython-313-darwin.so +0 -0
  9. pyogrio/_version.py +21 -0
  10. pyogrio/_vsi.cpython-313-darwin.so +0 -0
  11. pyogrio/core.py +386 -0
  12. pyogrio/errors.py +25 -0
  13. pyogrio/gdal_data/GDAL-targets-release.cmake +19 -0
  14. pyogrio/gdal_data/GDAL-targets.cmake +105 -0
  15. pyogrio/gdal_data/GDALConfig.cmake +24 -0
  16. pyogrio/gdal_data/GDALConfigVersion.cmake +85 -0
  17. pyogrio/gdal_data/GDALLogoBW.svg +138 -0
  18. pyogrio/gdal_data/GDALLogoColor.svg +126 -0
  19. pyogrio/gdal_data/GDALLogoGS.svg +126 -0
  20. pyogrio/gdal_data/LICENSE.TXT +467 -0
  21. pyogrio/gdal_data/MM_m_idofic.csv +321 -0
  22. pyogrio/gdal_data/copyright +467 -0
  23. pyogrio/gdal_data/cubewerx_extra.wkt +48 -0
  24. pyogrio/gdal_data/default.rsc +0 -0
  25. pyogrio/gdal_data/ecw_cs.wkt +1453 -0
  26. pyogrio/gdal_data/eedaconf.json +23 -0
  27. pyogrio/gdal_data/epsg.wkt +1 -0
  28. pyogrio/gdal_data/esri_StatePlane_extra.wkt +631 -0
  29. pyogrio/gdal_data/gdalicon.png +0 -0
  30. pyogrio/gdal_data/gdalinfo_output.schema.json +346 -0
  31. pyogrio/gdal_data/gdalmdiminfo_output.schema.json +321 -0
  32. pyogrio/gdal_data/gdaltileindex.xsd +269 -0
  33. pyogrio/gdal_data/gdalvrt.xsd +880 -0
  34. pyogrio/gdal_data/gfs.xsd +246 -0
  35. pyogrio/gdal_data/gml_registry.xml +117 -0
  36. pyogrio/gdal_data/gml_registry.xsd +66 -0
  37. pyogrio/gdal_data/grib2_center.csv +251 -0
  38. pyogrio/gdal_data/grib2_process.csv +102 -0
  39. pyogrio/gdal_data/grib2_subcenter.csv +63 -0
  40. pyogrio/gdal_data/grib2_table_4_2_0_0.csv +261 -0
  41. pyogrio/gdal_data/grib2_table_4_2_0_1.csv +261 -0
  42. pyogrio/gdal_data/grib2_table_4_2_0_13.csv +261 -0
  43. pyogrio/gdal_data/grib2_table_4_2_0_14.csv +261 -0
  44. pyogrio/gdal_data/grib2_table_4_2_0_15.csv +261 -0
  45. pyogrio/gdal_data/grib2_table_4_2_0_16.csv +261 -0
  46. pyogrio/gdal_data/grib2_table_4_2_0_17.csv +11 -0
  47. pyogrio/gdal_data/grib2_table_4_2_0_18.csv +261 -0
  48. pyogrio/gdal_data/grib2_table_4_2_0_19.csv +261 -0
  49. pyogrio/gdal_data/grib2_table_4_2_0_190.csv +261 -0
  50. pyogrio/gdal_data/grib2_table_4_2_0_191.csv +261 -0
  51. pyogrio/gdal_data/grib2_table_4_2_0_2.csv +261 -0
  52. pyogrio/gdal_data/grib2_table_4_2_0_20.csv +261 -0
  53. pyogrio/gdal_data/grib2_table_4_2_0_21.csv +261 -0
  54. pyogrio/gdal_data/grib2_table_4_2_0_3.csv +261 -0
  55. pyogrio/gdal_data/grib2_table_4_2_0_4.csv +261 -0
  56. pyogrio/gdal_data/grib2_table_4_2_0_5.csv +261 -0
  57. pyogrio/gdal_data/grib2_table_4_2_0_6.csv +261 -0
  58. pyogrio/gdal_data/grib2_table_4_2_0_7.csv +261 -0
  59. pyogrio/gdal_data/grib2_table_4_2_10_0.csv +261 -0
  60. pyogrio/gdal_data/grib2_table_4_2_10_1.csv +261 -0
  61. pyogrio/gdal_data/grib2_table_4_2_10_191.csv +261 -0
  62. pyogrio/gdal_data/grib2_table_4_2_10_2.csv +261 -0
  63. pyogrio/gdal_data/grib2_table_4_2_10_3.csv +261 -0
  64. pyogrio/gdal_data/grib2_table_4_2_10_4.csv +261 -0
  65. pyogrio/gdal_data/grib2_table_4_2_1_0.csv +261 -0
  66. pyogrio/gdal_data/grib2_table_4_2_1_1.csv +261 -0
  67. pyogrio/gdal_data/grib2_table_4_2_1_2.csv +261 -0
  68. pyogrio/gdal_data/grib2_table_4_2_20_0.csv +261 -0
  69. pyogrio/gdal_data/grib2_table_4_2_20_1.csv +261 -0
  70. pyogrio/gdal_data/grib2_table_4_2_20_2.csv +261 -0
  71. pyogrio/gdal_data/grib2_table_4_2_2_0.csv +261 -0
  72. pyogrio/gdal_data/grib2_table_4_2_2_3.csv +261 -0
  73. pyogrio/gdal_data/grib2_table_4_2_2_4.csv +261 -0
  74. pyogrio/gdal_data/grib2_table_4_2_2_5.csv +261 -0
  75. pyogrio/gdal_data/grib2_table_4_2_2_6.csv +261 -0
  76. pyogrio/gdal_data/grib2_table_4_2_3_0.csv +261 -0
  77. pyogrio/gdal_data/grib2_table_4_2_3_1.csv +261 -0
  78. pyogrio/gdal_data/grib2_table_4_2_3_2.csv +28 -0
  79. pyogrio/gdal_data/grib2_table_4_2_3_3.csv +8 -0
  80. pyogrio/gdal_data/grib2_table_4_2_3_4.csv +14 -0
  81. pyogrio/gdal_data/grib2_table_4_2_3_5.csv +11 -0
  82. pyogrio/gdal_data/grib2_table_4_2_3_6.csv +11 -0
  83. pyogrio/gdal_data/grib2_table_4_2_4_0.csv +261 -0
  84. pyogrio/gdal_data/grib2_table_4_2_4_1.csv +261 -0
  85. pyogrio/gdal_data/grib2_table_4_2_4_10.csv +261 -0
  86. pyogrio/gdal_data/grib2_table_4_2_4_2.csv +261 -0
  87. pyogrio/gdal_data/grib2_table_4_2_4_3.csv +261 -0
  88. pyogrio/gdal_data/grib2_table_4_2_4_4.csv +261 -0
  89. pyogrio/gdal_data/grib2_table_4_2_4_5.csv +261 -0
  90. pyogrio/gdal_data/grib2_table_4_2_4_6.csv +261 -0
  91. pyogrio/gdal_data/grib2_table_4_2_4_7.csv +261 -0
  92. pyogrio/gdal_data/grib2_table_4_2_4_8.csv +261 -0
  93. pyogrio/gdal_data/grib2_table_4_2_4_9.csv +261 -0
  94. pyogrio/gdal_data/grib2_table_4_2_local_Canada.csv +5 -0
  95. pyogrio/gdal_data/grib2_table_4_2_local_HPC.csv +2 -0
  96. pyogrio/gdal_data/grib2_table_4_2_local_MRMS.csv +175 -0
  97. pyogrio/gdal_data/grib2_table_4_2_local_NCEP.csv +401 -0
  98. pyogrio/gdal_data/grib2_table_4_2_local_NDFD.csv +38 -0
  99. pyogrio/gdal_data/grib2_table_4_2_local_index.csv +7 -0
  100. pyogrio/gdal_data/grib2_table_4_5.csv +261 -0
  101. pyogrio/gdal_data/grib2_table_versions.csv +3 -0
  102. pyogrio/gdal_data/gt_datum.csv +229 -0
  103. pyogrio/gdal_data/gt_ellips.csv +24 -0
  104. pyogrio/gdal_data/header.dxf +1124 -0
  105. pyogrio/gdal_data/inspire_cp_BasicPropertyUnit.gfs +57 -0
  106. pyogrio/gdal_data/inspire_cp_CadastralBoundary.gfs +60 -0
  107. pyogrio/gdal_data/inspire_cp_CadastralParcel.gfs +81 -0
  108. pyogrio/gdal_data/inspire_cp_CadastralZoning.gfs +161 -0
  109. pyogrio/gdal_data/jpfgdgml_AdmArea.gfs +59 -0
  110. pyogrio/gdal_data/jpfgdgml_AdmBdry.gfs +49 -0
  111. pyogrio/gdal_data/jpfgdgml_AdmPt.gfs +59 -0
  112. pyogrio/gdal_data/jpfgdgml_BldA.gfs +54 -0
  113. pyogrio/gdal_data/jpfgdgml_BldL.gfs +54 -0
  114. pyogrio/gdal_data/jpfgdgml_Cntr.gfs +54 -0
  115. pyogrio/gdal_data/jpfgdgml_CommBdry.gfs +49 -0
  116. pyogrio/gdal_data/jpfgdgml_CommPt.gfs +59 -0
  117. pyogrio/gdal_data/jpfgdgml_Cstline.gfs +54 -0
  118. pyogrio/gdal_data/jpfgdgml_ElevPt.gfs +54 -0
  119. pyogrio/gdal_data/jpfgdgml_GCP.gfs +94 -0
  120. pyogrio/gdal_data/jpfgdgml_LeveeEdge.gfs +49 -0
  121. pyogrio/gdal_data/jpfgdgml_RailCL.gfs +54 -0
  122. pyogrio/gdal_data/jpfgdgml_RdASL.gfs +44 -0
  123. pyogrio/gdal_data/jpfgdgml_RdArea.gfs +54 -0
  124. pyogrio/gdal_data/jpfgdgml_RdCompt.gfs +59 -0
  125. pyogrio/gdal_data/jpfgdgml_RdEdg.gfs +59 -0
  126. pyogrio/gdal_data/jpfgdgml_RdMgtBdry.gfs +49 -0
  127. pyogrio/gdal_data/jpfgdgml_RdSgmtA.gfs +59 -0
  128. pyogrio/gdal_data/jpfgdgml_RvrMgtBdry.gfs +49 -0
  129. pyogrio/gdal_data/jpfgdgml_SBAPt.gfs +49 -0
  130. pyogrio/gdal_data/jpfgdgml_SBArea.gfs +54 -0
  131. pyogrio/gdal_data/jpfgdgml_SBBdry.gfs +44 -0
  132. pyogrio/gdal_data/jpfgdgml_WA.gfs +54 -0
  133. pyogrio/gdal_data/jpfgdgml_WL.gfs +54 -0
  134. pyogrio/gdal_data/jpfgdgml_WStrA.gfs +54 -0
  135. pyogrio/gdal_data/jpfgdgml_WStrL.gfs +54 -0
  136. pyogrio/gdal_data/nitf_spec.xml +3306 -0
  137. pyogrio/gdal_data/nitf_spec.xsd +189 -0
  138. pyogrio/gdal_data/ogrinfo_output.schema.json +528 -0
  139. pyogrio/gdal_data/ogrvrt.xsd +546 -0
  140. pyogrio/gdal_data/osmconf.ini +132 -0
  141. pyogrio/gdal_data/ozi_datum.csv +131 -0
  142. pyogrio/gdal_data/ozi_ellips.csv +35 -0
  143. pyogrio/gdal_data/pci_datum.txt +530 -0
  144. pyogrio/gdal_data/pci_ellips.txt +129 -0
  145. pyogrio/gdal_data/pdfcomposition.xsd +721 -0
  146. pyogrio/gdal_data/pds4_template.xml +65 -0
  147. pyogrio/gdal_data/plscenesconf.json +1985 -0
  148. pyogrio/gdal_data/ruian_vf_ob_v1.gfs +1455 -0
  149. pyogrio/gdal_data/ruian_vf_st_uvoh_v1.gfs +86 -0
  150. pyogrio/gdal_data/ruian_vf_st_v1.gfs +1489 -0
  151. pyogrio/gdal_data/ruian_vf_v1.gfs +2126 -0
  152. pyogrio/gdal_data/s57agencies.csv +249 -0
  153. pyogrio/gdal_data/s57attributes.csv +484 -0
  154. pyogrio/gdal_data/s57expectedinput.csv +1008 -0
  155. pyogrio/gdal_data/s57objectclasses.csv +287 -0
  156. pyogrio/gdal_data/seed_2d.dgn +0 -0
  157. pyogrio/gdal_data/seed_3d.dgn +0 -0
  158. pyogrio/gdal_data/stateplane.csv +259 -0
  159. pyogrio/gdal_data/tms_LINZAntarticaMapTileGrid.json +190 -0
  160. pyogrio/gdal_data/tms_MapML_APSTILE.json +268 -0
  161. pyogrio/gdal_data/tms_MapML_CBMTILE.json +346 -0
  162. pyogrio/gdal_data/tms_NZTM2000.json +243 -0
  163. pyogrio/gdal_data/trailer.dxf +434 -0
  164. pyogrio/gdal_data/usage +4 -0
  165. pyogrio/gdal_data/vcpkg-cmake-wrapper.cmake +23 -0
  166. pyogrio/gdal_data/vcpkg.spdx.json +264 -0
  167. pyogrio/gdal_data/vcpkg_abi_info.txt +41 -0
  168. pyogrio/gdal_data/vdv452.xml +367 -0
  169. pyogrio/gdal_data/vdv452.xsd +63 -0
  170. pyogrio/gdal_data/vicar.json +164 -0
  171. pyogrio/geopandas.py +683 -0
  172. pyogrio/proj_data/CH +22 -0
  173. pyogrio/proj_data/GL27 +23 -0
  174. pyogrio/proj_data/ITRF2000 +24 -0
  175. pyogrio/proj_data/ITRF2008 +94 -0
  176. pyogrio/proj_data/ITRF2014 +55 -0
  177. pyogrio/proj_data/copyright +34 -0
  178. pyogrio/proj_data/deformation_model.schema.json +582 -0
  179. pyogrio/proj_data/nad.lst +142 -0
  180. pyogrio/proj_data/nad27 +810 -0
  181. pyogrio/proj_data/nad83 +745 -0
  182. pyogrio/proj_data/other.extra +53 -0
  183. pyogrio/proj_data/proj-config-version.cmake +44 -0
  184. pyogrio/proj_data/proj-config.cmake +79 -0
  185. pyogrio/proj_data/proj-targets-release.cmake +19 -0
  186. pyogrio/proj_data/proj-targets.cmake +107 -0
  187. pyogrio/proj_data/proj.db +0 -0
  188. pyogrio/proj_data/proj.ini +51 -0
  189. pyogrio/proj_data/proj4-targets-release.cmake +19 -0
  190. pyogrio/proj_data/proj4-targets.cmake +107 -0
  191. pyogrio/proj_data/projjson.schema.json +1174 -0
  192. pyogrio/proj_data/triangulation.schema.json +214 -0
  193. pyogrio/proj_data/usage +4 -0
  194. pyogrio/proj_data/vcpkg.spdx.json +198 -0
  195. pyogrio/proj_data/vcpkg_abi_info.txt +27 -0
  196. pyogrio/proj_data/world +214 -0
  197. pyogrio/raw.py +887 -0
  198. pyogrio/tests/__init__.py +0 -0
  199. pyogrio/tests/conftest.py +398 -0
  200. pyogrio/tests/fixtures/README.md +108 -0
  201. pyogrio/tests/fixtures/curve.gpkg +0 -0
  202. pyogrio/tests/fixtures/curvepolygon.gpkg +0 -0
  203. pyogrio/tests/fixtures/line_zm.gpkg +0 -0
  204. pyogrio/tests/fixtures/multisurface.gpkg +0 -0
  205. pyogrio/tests/fixtures/naturalearth_lowres/naturalearth_lowres.cpg +1 -0
  206. pyogrio/tests/fixtures/naturalearth_lowres/naturalearth_lowres.dbf +0 -0
  207. pyogrio/tests/fixtures/naturalearth_lowres/naturalearth_lowres.prj +1 -0
  208. pyogrio/tests/fixtures/naturalearth_lowres/naturalearth_lowres.shp +0 -0
  209. pyogrio/tests/fixtures/naturalearth_lowres/naturalearth_lowres.shx +0 -0
  210. pyogrio/tests/fixtures/sample.osm.pbf +0 -0
  211. pyogrio/tests/fixtures/test_gpkg_nulls.gpkg +0 -0
  212. pyogrio/tests/test_arrow.py +1195 -0
  213. pyogrio/tests/test_core.py +678 -0
  214. pyogrio/tests/test_geopandas_io.py +2314 -0
  215. pyogrio/tests/test_path.py +364 -0
  216. pyogrio/tests/test_raw_io.py +1515 -0
  217. pyogrio/tests/test_util.py +56 -0
  218. pyogrio/util.py +247 -0
  219. pyogrio-0.10.0.dist-info/LICENSE +21 -0
  220. pyogrio-0.10.0.dist-info/METADATA +129 -0
  221. pyogrio-0.10.0.dist-info/RECORD +223 -0
  222. pyogrio-0.10.0.dist-info/WHEEL +5 -0
  223. pyogrio-0.10.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,364 @@
1
+ import contextlib
2
+ import os
3
+ from pathlib import Path
4
+ from zipfile import ZIP_DEFLATED, ZipFile
5
+
6
+ import pyogrio
7
+ import pyogrio.raw
8
+ from pyogrio._compat import HAS_PYPROJ
9
+ from pyogrio.util import get_vsi_path_or_buffer, vsi_path
10
+
11
+ import pytest
12
+
13
+ try:
14
+ import geopandas # noqa: F401
15
+
16
+ has_geopandas = True
17
+ except ImportError:
18
+ has_geopandas = False
19
+
20
+
21
+ @contextlib.contextmanager
22
+ def change_cwd(path):
23
+ curdir = os.getcwd()
24
+ os.chdir(str(path))
25
+ try:
26
+ yield
27
+ finally:
28
+ os.chdir(curdir)
29
+
30
+
31
+ @pytest.mark.parametrize(
32
+ "path, expected",
33
+ [
34
+ # local file paths that should be passed through as is
35
+ ("data.gpkg", "data.gpkg"),
36
+ (Path("data.gpkg"), "data.gpkg"),
37
+ ("/home/user/data.gpkg", "/home/user/data.gpkg"),
38
+ (r"C:\User\Documents\data.gpkg", r"C:\User\Documents\data.gpkg"),
39
+ ("file:///home/user/data.gpkg", "/home/user/data.gpkg"),
40
+ ("/home/folder # with hash/data.gpkg", "/home/folder # with hash/data.gpkg"),
41
+ # cloud URIs
42
+ ("https://testing/data.gpkg", "/vsicurl/https://testing/data.gpkg"),
43
+ ("s3://testing/data.gpkg", "/vsis3/testing/data.gpkg"),
44
+ ("gs://testing/data.gpkg", "/vsigs/testing/data.gpkg"),
45
+ ("az://testing/data.gpkg", "/vsiaz/testing/data.gpkg"),
46
+ ("adl://testing/data.gpkg", "/vsiadls/testing/data.gpkg"),
47
+ ("adls://testing/data.gpkg", "/vsiadls/testing/data.gpkg"),
48
+ ("hdfs://testing/data.gpkg", "/vsihdfs/testing/data.gpkg"),
49
+ ("webhdfs://testing/data.gpkg", "/vsiwebhdfs/testing/data.gpkg"),
50
+ # archives
51
+ ("zip://data.zip", "/vsizip/data.zip"),
52
+ ("tar://data.tar", "/vsitar/data.tar"),
53
+ ("gzip://data.gz", "/vsigzip/data.gz"),
54
+ ("tar://./my.tar!my.geojson", "/vsitar/./my.tar/my.geojson"),
55
+ (
56
+ "zip://home/data/shapefile.zip!layer.shp",
57
+ "/vsizip/home/data/shapefile.zip/layer.shp",
58
+ ),
59
+ # combined schemes
60
+ ("zip+s3://testing/shapefile.zip", "/vsizip/vsis3/testing/shapefile.zip"),
61
+ (
62
+ "zip+https://s3.amazonaws.com/testing/shapefile.zip",
63
+ "/vsizip/vsicurl/https://s3.amazonaws.com/testing/shapefile.zip",
64
+ ),
65
+ # auto-prefix zip files
66
+ ("test.zip", "/vsizip/test.zip"),
67
+ ("/a/b/test.zip", "/vsizip//a/b/test.zip"),
68
+ ("a/b/test.zip", "/vsizip/a/b/test.zip"),
69
+ # archives using ! notation should be prefixed by vsizip
70
+ ("test.zip!item.shp", "/vsizip/test.zip/item.shp"),
71
+ ("test.zip!/a/b/item.shp", "/vsizip/test.zip/a/b/item.shp"),
72
+ ("test.zip!a/b/item.shp", "/vsizip/test.zip/a/b/item.shp"),
73
+ ("/vsizip/test.zip/a/b/item.shp", "/vsizip/test.zip/a/b/item.shp"),
74
+ ("zip:///test.zip/a/b/item.shp", "/vsizip//test.zip/a/b/item.shp"),
75
+ # auto-prefix remote zip files
76
+ (
77
+ "https://s3.amazonaws.com/testing/test.zip",
78
+ "/vsizip/vsicurl/https://s3.amazonaws.com/testing/test.zip",
79
+ ),
80
+ (
81
+ "https://s3.amazonaws.com/testing/test.zip!/a/b/item.shp",
82
+ "/vsizip/vsicurl/https://s3.amazonaws.com/testing/test.zip/a/b/item.shp",
83
+ ),
84
+ ("s3://testing/test.zip", "/vsizip/vsis3/testing/test.zip"),
85
+ (
86
+ "s3://testing/test.zip!a/b/item.shp",
87
+ "/vsizip/vsis3/testing/test.zip/a/b/item.shp",
88
+ ),
89
+ ("/vsimem/data.gpkg", "/vsimem/data.gpkg"),
90
+ (Path("/vsimem/data.gpkg"), "/vsimem/data.gpkg"),
91
+ ],
92
+ )
93
+ def test_vsi_path(path, expected):
94
+ assert vsi_path(path) == expected
95
+
96
+
97
+ def test_vsi_path_unknown():
98
+ # unrecognized URI gets passed through as is
99
+ assert vsi_path("s4://test/data.geojson") == "s4://test/data.geojson"
100
+
101
+
102
+ def test_vsi_handling_read_functions(naturalearth_lowres_vsi):
103
+ # test that all different read entry points have the path handling
104
+ # (a zip:// path would otherwise fail)
105
+ path, _ = naturalearth_lowres_vsi
106
+ path = "zip://" + str(path)
107
+
108
+ result = pyogrio.raw.read(path)
109
+ assert len(result[2]) == 177
110
+
111
+ result = pyogrio.read_info(path)
112
+ assert result["features"] == 177
113
+
114
+ result = pyogrio.read_bounds(path)
115
+ assert len(result[0]) == 177
116
+
117
+
118
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
119
+ def test_vsi_handling_read_dataframe(naturalearth_lowres_vsi):
120
+ path, _ = naturalearth_lowres_vsi
121
+ path = "zip://" + str(path)
122
+
123
+ result = pyogrio.read_dataframe(path)
124
+ assert len(result) == 177
125
+
126
+
127
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
128
+ def test_path_absolute(data_dir):
129
+ # pathlib path
130
+ path = data_dir / "naturalearth_lowres/naturalearth_lowres.shp"
131
+ df = pyogrio.read_dataframe(path)
132
+ assert len(df) == 177
133
+
134
+ # str path
135
+ df = pyogrio.read_dataframe(str(path))
136
+ assert len(df) == 177
137
+
138
+
139
+ def test_path_relative(data_dir):
140
+ path = "naturalearth_lowres/naturalearth_lowres.shp"
141
+
142
+ with change_cwd(data_dir):
143
+ result = pyogrio.raw.read(path)
144
+ assert len(result[2]) == 177
145
+
146
+ result = pyogrio.read_info(path)
147
+ assert result["features"] == 177
148
+
149
+ result = pyogrio.read_bounds(path)
150
+ assert len(result[0]) == 177
151
+
152
+
153
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
154
+ def test_path_relative_dataframe(data_dir):
155
+ with change_cwd(data_dir):
156
+ df = pyogrio.read_dataframe("naturalearth_lowres/naturalearth_lowres.shp")
157
+ assert len(df) == 177
158
+
159
+
160
+ def test_uri_local_file(data_dir):
161
+ path = "file://" + str(data_dir / "naturalearth_lowres/naturalearth_lowres.shp")
162
+ result = pyogrio.raw.read(path)
163
+ assert len(result[2]) == 177
164
+
165
+ result = pyogrio.read_info(path)
166
+ assert result["features"] == 177
167
+
168
+ result = pyogrio.read_bounds(path)
169
+ assert len(result[0]) == 177
170
+
171
+
172
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
173
+ def test_uri_local_file_dataframe(data_dir):
174
+ uri = "file://" + str(data_dir / "naturalearth_lowres/naturalearth_lowres.shp")
175
+ df = pyogrio.read_dataframe(uri)
176
+ assert len(df) == 177
177
+
178
+
179
+ def test_zip_path(naturalearth_lowres_vsi):
180
+ path, path_vsi = naturalearth_lowres_vsi
181
+ path_zip = "zip://" + str(path)
182
+
183
+ # absolute zip path
184
+ result = pyogrio.raw.read(path_zip)
185
+ assert len(result[2]) == 177
186
+
187
+ result = pyogrio.read_info(path_zip)
188
+ assert result["features"] == 177
189
+
190
+ result = pyogrio.read_bounds(path_zip)
191
+ assert len(result[0]) == 177
192
+
193
+ # absolute vsizip path
194
+ result = pyogrio.raw.read(path_vsi)
195
+ assert len(result[2]) == 177
196
+
197
+ result = pyogrio.read_info(path_vsi)
198
+ assert result["features"] == 177
199
+
200
+ result = pyogrio.read_bounds(path_vsi)
201
+ assert len(result[0]) == 177
202
+
203
+ # relative zip path
204
+ relative_path = "zip://" + path.name
205
+ with change_cwd(path.parent):
206
+ result = pyogrio.raw.read(relative_path)
207
+ assert len(result[2]) == 177
208
+
209
+ result = pyogrio.read_info(relative_path)
210
+ assert result["features"] == 177
211
+
212
+ result = pyogrio.read_bounds(relative_path)
213
+ assert len(result[0]) == 177
214
+
215
+
216
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
217
+ def test_zip_path_dataframe(naturalearth_lowres_vsi):
218
+ path, path_vsi = naturalearth_lowres_vsi
219
+ path_zip = "zip://" + str(path)
220
+
221
+ # absolute zip path
222
+ df = pyogrio.read_dataframe(path_zip)
223
+ assert len(df) == 177
224
+
225
+ # absolute vsizip path
226
+ df = pyogrio.read_dataframe(path_vsi)
227
+ assert len(df) == 177
228
+
229
+ # relative zip path
230
+ with change_cwd(path.parent):
231
+ df = pyogrio.read_dataframe("zip://" + path.name)
232
+ assert len(df) == 177
233
+
234
+
235
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
236
+ def test_detect_zip_path(tmp_path, naturalearth_lowres):
237
+ # create a zipfile with 2 shapefiles in a set of subdirectories
238
+ df = pyogrio.read_dataframe(naturalearth_lowres, where="iso_a3 in ('CAN', 'PER')")
239
+ pyogrio.write_dataframe(df.loc[df.iso_a3 == "CAN"], tmp_path / "test1.shp")
240
+ pyogrio.write_dataframe(df.loc[df.iso_a3 == "PER"], tmp_path / "test2.shp")
241
+
242
+ path = tmp_path / "test.zip"
243
+ with ZipFile(path, mode="w", compression=ZIP_DEFLATED, compresslevel=5) as out:
244
+ for ext in ["dbf", "prj", "shp", "shx"]:
245
+ if not HAS_PYPROJ and ext == "prj":
246
+ continue
247
+
248
+ filename = f"test1.{ext}"
249
+ out.write(tmp_path / filename, filename)
250
+
251
+ filename = f"test2.{ext}"
252
+ out.write(tmp_path / filename, f"/a/b/{filename}")
253
+
254
+ # defaults to the first shapefile found, at lowest subdirectory
255
+ df = pyogrio.read_dataframe(path)
256
+ assert df.iso_a3[0] == "CAN"
257
+
258
+ # selecting a shapefile from within the zip requires "!"" archive specifier
259
+ df = pyogrio.read_dataframe(f"{path}!test1.shp")
260
+ assert df.iso_a3[0] == "CAN"
261
+
262
+ df = pyogrio.read_dataframe(f"{path}!/a/b/test2.shp")
263
+ assert df.iso_a3[0] == "PER"
264
+
265
+ # specifying zip:// scheme should also work
266
+ df = pyogrio.read_dataframe(f"zip://{path}!/a/b/test2.shp")
267
+ assert df.iso_a3[0] == "PER"
268
+
269
+ # specifying /vsizip/ should also work but path must already be in GDAL ready
270
+ # format without the "!"" archive specifier
271
+ df = pyogrio.read_dataframe(f"/vsizip/{path}/a/b/test2.shp")
272
+ assert df.iso_a3[0] == "PER"
273
+
274
+
275
+ @pytest.mark.network
276
+ def test_url():
277
+ url = "https://raw.githubusercontent.com/geopandas/pyogrio/main/pyogrio/tests/fixtures/naturalearth_lowres/naturalearth_lowres.shp"
278
+
279
+ result = pyogrio.raw.read(url)
280
+ assert len(result[2]) == 177
281
+
282
+ result = pyogrio.read_info(url)
283
+ assert result["features"] == 177
284
+
285
+ result = pyogrio.read_bounds(url)
286
+ assert len(result[0]) == 177
287
+
288
+
289
+ @pytest.mark.network
290
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
291
+ def test_url_dataframe():
292
+ url = "https://raw.githubusercontent.com/geopandas/pyogrio/main/pyogrio/tests/fixtures/naturalearth_lowres/naturalearth_lowres.shp"
293
+
294
+ assert len(pyogrio.read_dataframe(url)) == 177
295
+
296
+
297
+ @pytest.mark.network
298
+ def test_url_with_zip():
299
+ url = "zip+https://s3.amazonaws.com/fiona-testing/coutwildrnp.zip"
300
+
301
+ result = pyogrio.raw.read(url)
302
+ assert len(result[2]) == 67
303
+
304
+ result = pyogrio.read_info(url)
305
+ assert result["features"] == 67
306
+
307
+ result = pyogrio.read_bounds(url)
308
+ assert len(result[0]) == 67
309
+
310
+
311
+ @pytest.mark.network
312
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
313
+ def test_url_with_zip_dataframe():
314
+ url = "zip+https://s3.amazonaws.com/fiona-testing/coutwildrnp.zip"
315
+ df = pyogrio.read_dataframe(url)
316
+ assert len(df) == 67
317
+
318
+
319
+ @pytest.fixture
320
+ def aws_env_setup(monkeypatch):
321
+ monkeypatch.setenv("AWS_NO_SIGN_REQUEST", "YES")
322
+
323
+
324
+ @pytest.mark.network
325
+ def test_uri_s3(aws_env_setup):
326
+ url = "zip+s3://fiona-testing/coutwildrnp.zip"
327
+
328
+ result = pyogrio.raw.read(url)
329
+ assert len(result[2]) == 67
330
+
331
+ result = pyogrio.read_info(url)
332
+ assert result["features"] == 67
333
+
334
+ result = pyogrio.read_bounds(url)
335
+ assert len(result[0]) == 67
336
+
337
+
338
+ @pytest.mark.network
339
+ @pytest.mark.skipif(not has_geopandas, reason="GeoPandas not available")
340
+ def test_uri_s3_dataframe(aws_env_setup):
341
+ df = pyogrio.read_dataframe("zip+s3://fiona-testing/coutwildrnp.zip")
342
+ assert len(df) == 67
343
+
344
+
345
+ @pytest.mark.parametrize(
346
+ "path, expected",
347
+ [
348
+ (Path("/tmp/test.gpkg"), str(Path("/tmp/test.gpkg"))),
349
+ (Path("/vsimem/test.gpkg"), "/vsimem/test.gpkg"),
350
+ ],
351
+ )
352
+ def test_get_vsi_path_or_buffer_obj_to_string(path, expected):
353
+ """Verify that get_vsi_path_or_buffer retains forward slashes in /vsimem paths.
354
+
355
+ The /vsimem paths should keep forward slashes for GDAL to recognize them as such.
356
+ However, on Windows systems, forward slashes are by default replaced by backslashes,
357
+ so this test verifies that this doesn't happen for /vsimem paths.
358
+ """
359
+ assert get_vsi_path_or_buffer(path) == expected
360
+
361
+
362
+ def test_get_vsi_path_or_buffer_fixtures_to_string(tmp_path):
363
+ path = tmp_path / "test.gpkg"
364
+ assert get_vsi_path_or_buffer(path) == str(path)