[fiona] 08/10: Drop patches applied/included upstream. Refresh remaining patches.
Sebastiaan Couwenberg
sebastic at moszumanska.debian.org
Sat Jun 11 12:40:42 UTC 2016
This is an automated email from the git hooks/post-receive script.
sebastic pushed a commit to branch master
in repository fiona.
commit bebe62999f6e9b06a11e68086c8b1a661add1c65
Author: Bas Couwenberg <sebastic at xs4all.nl>
Date: Sat Jun 11 12:50:52 2016 +0200
Drop patches applied/included upstream. Refresh remaining patches.
---
debian/changelog | 1 +
...-fio-command-to-fiona-to-avoid-name-clash.patch | 2 +-
debian/patches/0003-GDAL-2.0.patch | 4582 --------------------
.../0004-Just-use-int-as-a-plain-old-builtin.patch | 36 -
...at-fiona.remove-for-deleting-data-sources.patch | 246 --
.../0006-Remove-unknown-distribution-options.patch | 2 +-
debian/patches/0007-clean.patch | 123 -
.../patches/0008-Disable-GDAL-2-ImportError.patch | 20 -
debian/patches/series | 5 -
9 files changed, 3 insertions(+), 5014 deletions(-)
diff --git a/debian/changelog b/debian/changelog
index 81a44ed..88e3e01 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -5,6 +5,7 @@ fiona (1.7~b1-1) UNRELEASED; urgency=medium
* Override dh_auto_test to ignore test failures on Hurd & kFreeBSD.
* Update watch file to handle pre-releases.
* Add python{,3}-munch to build dependencies.
+ * Drop patches applied/included upstream. Refresh remaining patches.
-- Bas Couwenberg <sebastic at debian.org> Sat, 11 Jun 2016 12:40:06 +0200
diff --git a/debian/patches/0001-Rename-fio-command-to-fiona-to-avoid-name-clash.patch b/debian/patches/0001-Rename-fio-command-to-fiona-to-avoid-name-clash.patch
index fdd825b..f00002b 100644
--- a/debian/patches/0001-Rename-fio-command-to-fiona-to-avoid-name-clash.patch
+++ b/debian/patches/0001-Rename-fio-command-to-fiona-to-avoid-name-clash.patch
@@ -9,7 +9,7 @@ There is already another package providing a binary "fio" (fio).
--- a/setup.py
+++ b/setup.py
-@@ -181,7 +181,7 @@ setup_args = dict(
+@@ -198,7 +198,7 @@ setup_args = dict(
packages=['fiona', 'fiona.fio'],
entry_points='''
[console_scripts]
diff --git a/debian/patches/0003-GDAL-2.0.patch b/debian/patches/0003-GDAL-2.0.patch
deleted file mode 100644
index 2c173e6..0000000
--- a/debian/patches/0003-GDAL-2.0.patch
+++ /dev/null
@@ -1,4582 +0,0 @@
-Origin: https://github.com/Toblerity/Fiona/commit/3ebef78f2d1af1e306ad2a1df043511bfc55c13b
-Bug: https://github.com/Toblerity/Fiona/issues/239
-Bug-Debian: https://bugs.debian.org/802808
-From 84e7ce2786e3d881d0a88156bb1e26167bb2ce0d Mon Sep 17 00:00:00 2001
-From: Rene Buffat <buffat at gmail.com>
-Date: Wed, 23 Sep 2015 22:40:37 +0200
-Subject: [PATCH 01/16] sperate implementation for gdal2
-
----
- .travis.yml | 2 +-
- fiona/ograpi.pxd | 145 --
- fiona/ograpi1.pxd | 145 ++
- fiona/ograpi2.pxd | 183 ++
- fiona/ogrext.pyx | 1233 -----------
- fiona/ogrext1.pyx | 1233 +++++++++++
- fiona/ogrext2.pyx | 6240 +++++++++++++++++++++++++++++++++++++++++++++++++++++
- setup.py | 14 +-
- 8 files changed, 7814 insertions(+), 1381 deletions(-)
- delete mode 100644 fiona/ograpi.pxd
- create mode 100644 fiona/ograpi1.pxd
- create mode 100644 fiona/ograpi2.pxd
- delete mode 100644 fiona/ogrext.pyx
- create mode 100644 fiona/ogrext1.pyx
- create mode 100644 fiona/ogrext2.pyx
-
---- a/.travis.yml
-+++ b/.travis.yml
-@@ -8,6 +8,7 @@ before_install:
- - sudo apt-get update -qq
- - sudo apt-get install -y libgdal1h gdal-bin libgdal-dev
- install:
-+ - "pip install -r requirements.txt"
- - "pip install -r requirements-dev.txt"
- - "pip install pytest"
- - "pip install coveralls"
---- a/fiona/ograpi.pxd
-+++ /dev/null
-@@ -1,145 +0,0 @@
--# Copyright (c) 2007, Sean C. Gillies
--# All rights reserved.
--# See ../LICENSE.txt
--
--cdef extern from "gdal.h":
-- char * GDALVersionInfo (char *pszRequest)
--
--cdef extern from "gdal_version.h":
-- int GDAL_COMPUTE_VERSION(int maj, int min, int rev)
--
--cdef extern from "cpl_conv.h":
-- void * CPLMalloc (size_t)
-- void CPLFree (void *ptr)
-- void CPLSetThreadLocalConfigOption (char *key, char *val)
-- const char *CPLGetConfigOption (char *, char *)
--
--cdef extern from "cpl_string.h":
-- char ** CSLSetNameValue (char **list, char *name, char *value)
-- void CSLDestroy (char **list)
--
--cdef extern from "cpl_vsi.h":
-- ctypedef struct VSILFILE:
-- pass
-- int VSIFCloseL (VSILFILE *)
-- VSILFILE * VSIFileFromMemBuffer (const char * filename,
-- unsigned char * data,
-- int data_len,
-- int take_ownership)
-- int VSIUnlink (const char * pathname)
--
--ctypedef int OGRErr
--ctypedef struct OGREnvelope:
-- double MinX
-- double MaxX
-- double MinY
-- double MaxY
--
--cdef extern from "ogr_core.h":
-- char * OGRGeometryTypeToName(int)
--
--cdef extern from "ogr_srs_api.h":
-- void OSRCleanup ()
-- void * OSRClone (void *srs)
-- void OSRDestroySpatialReference (void *srs)
-- int OSRExportToProj4 (void *srs, char **params)
-- int OSRExportToWkt (void *srs, char **params)
-- int OSRImportFromEPSG (void *srs, int code)
-- int OSRImportFromProj4 (void *srs, char *proj)
-- int OSRSetFromUserInput (void *srs, char *input)
-- int OSRAutoIdentifyEPSG (void *srs)
-- int OSRFixup(void *srs)
-- const char * OSRGetAuthorityName (void *srs, const char *key)
-- const char * OSRGetAuthorityCode (void *srs, const char *key)
-- void * OSRNewSpatialReference (char *wkt)
-- void OSRRelease (void *srs)
-- void * OCTNewCoordinateTransformation (void *source, void *dest)
-- void OCTDestroyCoordinateTransformation (void *source)
-- int OCTTransform (void *ct, int nCount, double *x, double *y, double *z)
--
--cdef extern from "ogr_api.h":
-- char * OGR_Dr_GetName (void *driver)
-- void * OGR_Dr_CreateDataSource (void *driver, const char *path, char **options)
-- int OGR_Dr_DeleteDataSource (void *driver, char *)
-- void * OGR_Dr_Open (void *driver, const char *path, int bupdate)
-- int OGR_DS_DeleteLayer (void *datasource, int n)
-- void * OGR_DS_CreateLayer (void *datasource, char *name, void *crs, int geomType, char **options)
-- void * OGR_DS_ExecuteSQL (void *datasource, char *name, void *filter, char *dialext)
-- void OGR_DS_Destroy (void *datasource)
-- void * OGR_DS_GetDriver (void *layer_defn)
-- void * OGR_DS_GetLayerByName (void *datasource, char *name)
-- int OGR_DS_GetLayerCount (void *datasource)
-- void * OGR_DS_GetLayer (void *datasource, int n)
-- void OGR_DS_ReleaseResultSet (void *datasource, void *results)
-- int OGR_DS_SyncToDisk (void *datasource)
-- void * OGR_F_Create (void *featuredefn)
-- void OGR_F_Destroy (void *feature)
-- long OGR_F_GetFID (void *feature)
-- int OGR_F_IsFieldSet (void *feature, int n)
-- int OGR_F_GetFieldAsDateTime (void *feature, int n, int *y, int *m, int *d, int *h, int *m, int *s, int *z)
-- double OGR_F_GetFieldAsDouble (void *feature, int n)
-- int OGR_F_GetFieldAsInteger (void *feature, int n)
-- char * OGR_F_GetFieldAsString (void *feature, int n)
-- int OGR_F_GetFieldCount (void *feature)
-- void * OGR_F_GetFieldDefnRef (void *feature, int n)
-- int OGR_F_GetFieldIndex (void *feature, char *name)
-- void * OGR_F_GetGeometryRef (void *feature)
-- void OGR_F_SetFieldDateTime (void *feature, int n, int y, int m, int d, int hh, int mm, int ss, int tz)
-- void OGR_F_SetFieldDouble (void *feature, int n, double value)
-- void OGR_F_SetFieldInteger (void *feature, int n, int value)
-- void OGR_F_SetFieldString (void *feature, int n, char *value)
-- int OGR_F_SetGeometryDirectly (void *feature, void *geometry)
-- void * OGR_FD_Create (char *name)
-- int OGR_FD_GetFieldCount (void *featuredefn)
-- void * OGR_FD_GetFieldDefn (void *featuredefn, int n)
-- int OGR_FD_GetGeomType (void *featuredefn)
-- char * OGR_FD_GetName (void *featuredefn)
-- void * OGR_Fld_Create (char *name, int fieldtype)
-- void OGR_Fld_Destroy (void *fielddefn)
-- char * OGR_Fld_GetNameRef (void *fielddefn)
-- int OGR_Fld_GetPrecision (void *fielddefn)
-- int OGR_Fld_GetType (void *fielddefn)
-- int OGR_Fld_GetWidth (void *fielddefn)
-- void OGR_Fld_Set (void *fielddefn, char *name, int fieldtype, int width, int precision, int justification)
-- void OGR_Fld_SetPrecision (void *fielddefn, int n)
-- void OGR_Fld_SetWidth (void *fielddefn, int n)
-- OGRErr OGR_G_AddGeometryDirectly (void *geometry, void *part)
-- void OGR_G_AddPoint (void *geometry, double x, double y, double z)
-- void OGR_G_AddPoint_2D (void *geometry, double x, double y)
-- void OGR_G_CloseRings (void *geometry)
-- void * OGR_G_CreateGeometry (int wkbtypecode)
-- void OGR_G_DestroyGeometry (void *geometry)
-- unsigned char * OGR_G_ExportToJson (void *geometry)
-- void OGR_G_ExportToWkb (void *geometry, int endianness, char *buffer)
-- int OGR_G_GetCoordinateDimension (void *geometry)
-- int OGR_G_GetGeometryCount (void *geometry)
-- unsigned char * OGR_G_GetGeometryName (void *geometry)
-- int OGR_G_GetGeometryType (void *geometry)
-- void * OGR_G_GetGeometryRef (void *geometry, int n)
-- int OGR_G_GetPointCount (void *geometry)
-- double OGR_G_GetX (void *geometry, int n)
-- double OGR_G_GetY (void *geometry, int n)
-- double OGR_G_GetZ (void *geometry, int n)
-- void OGR_G_ImportFromWkb (void *geometry, unsigned char *bytes, int nbytes)
-- int OGR_G_WkbSize (void *geometry)
-- OGRErr OGR_L_CreateFeature (void *layer, void *feature)
-- int OGR_L_CreateField (void *layer, void *fielddefn, int flexible)
-- OGRErr OGR_L_GetExtent (void *layer, void *extent, int force)
-- void * OGR_L_GetFeature (void *layer, int n)
-- int OGR_L_GetFeatureCount (void *layer, int m)
-- void * OGR_L_GetLayerDefn (void *layer)
-- char * OGR_L_GetName (void *layer)
-- void * OGR_L_GetNextFeature (void *layer)
-- void * OGR_L_GetSpatialFilter (void *layer)
-- void * OGR_L_GetSpatialRef (void *layer)
-- void OGR_L_ResetReading (void *layer)
-- void OGR_L_SetSpatialFilter (void *layer, void *geometry)
-- void OGR_L_SetSpatialFilterRect (
-- void *layer, double minx, double miny, double maxx, double maxy
-- )
-- int OGR_L_TestCapability (void *layer, char *name)
-- void * OGRGetDriverByName (char *)
-- void * OGROpen (char *path, int mode, void *x)
-- void * OGROpenShared (char *path, int mode, void *x)
-- int OGRReleaseDataSource (void *datasource)
-- OGRErr OGR_L_SetNextByIndex (void *layer, long nIndex)
---- /dev/null
-+++ b/fiona/ograpi1.pxd
-@@ -0,0 +1,145 @@
-+# Copyright (c) 2007, Sean C. Gillies
-+# All rights reserved.
-+# See ../LICENSE.txt
-+
-+cdef extern from "gdal.h":
-+ char * GDALVersionInfo (char *pszRequest)
-+
-+cdef extern from "gdal_version.h":
-+ int GDAL_COMPUTE_VERSION(int maj, int min, int rev)
-+
-+cdef extern from "cpl_conv.h":
-+ void * CPLMalloc (size_t)
-+ void CPLFree (void *ptr)
-+ void CPLSetThreadLocalConfigOption (char *key, char *val)
-+ const char *CPLGetConfigOption (char *, char *)
-+
-+cdef extern from "cpl_string.h":
-+ char ** CSLSetNameValue (char **list, char *name, char *value)
-+ void CSLDestroy (char **list)
-+
-+cdef extern from "cpl_vsi.h":
-+ ctypedef struct VSILFILE:
-+ pass
-+ int VSIFCloseL (VSILFILE *)
-+ VSILFILE * VSIFileFromMemBuffer (const char * filename,
-+ unsigned char * data,
-+ int data_len,
-+ int take_ownership)
-+ int VSIUnlink (const char * pathname)
-+
-+ctypedef int OGRErr
-+ctypedef struct OGREnvelope:
-+ double MinX
-+ double MaxX
-+ double MinY
-+ double MaxY
-+
-+cdef extern from "ogr_core.h":
-+ char * OGRGeometryTypeToName(int)
-+
-+cdef extern from "ogr_srs_api.h":
-+ void OSRCleanup ()
-+ void * OSRClone (void *srs)
-+ void OSRDestroySpatialReference (void *srs)
-+ int OSRExportToProj4 (void *srs, char **params)
-+ int OSRExportToWkt (void *srs, char **params)
-+ int OSRImportFromEPSG (void *srs, int code)
-+ int OSRImportFromProj4 (void *srs, char *proj)
-+ int OSRSetFromUserInput (void *srs, char *input)
-+ int OSRAutoIdentifyEPSG (void *srs)
-+ int OSRFixup(void *srs)
-+ const char * OSRGetAuthorityName (void *srs, const char *key)
-+ const char * OSRGetAuthorityCode (void *srs, const char *key)
-+ void * OSRNewSpatialReference (char *wkt)
-+ void OSRRelease (void *srs)
-+ void * OCTNewCoordinateTransformation (void *source, void *dest)
-+ void OCTDestroyCoordinateTransformation (void *source)
-+ int OCTTransform (void *ct, int nCount, double *x, double *y, double *z)
-+
-+cdef extern from "ogr_api.h":
-+ char * OGR_Dr_GetName (void *driver)
-+ void * OGR_Dr_CreateDataSource (void *driver, const char *path, char **options)
-+ int OGR_Dr_DeleteDataSource (void *driver, char *)
-+ void * OGR_Dr_Open (void *driver, const char *path, int bupdate)
-+ int OGR_DS_DeleteLayer (void *datasource, int n)
-+ void * OGR_DS_CreateLayer (void *datasource, char *name, void *crs, int geomType, char **options)
-+ void * OGR_DS_ExecuteSQL (void *datasource, char *name, void *filter, char *dialext)
-+ void OGR_DS_Destroy (void *datasource)
-+ void * OGR_DS_GetDriver (void *layer_defn)
-+ void * OGR_DS_GetLayerByName (void *datasource, char *name)
-+ int OGR_DS_GetLayerCount (void *datasource)
-+ void * OGR_DS_GetLayer (void *datasource, int n)
-+ void OGR_DS_ReleaseResultSet (void *datasource, void *results)
-+ int OGR_DS_SyncToDisk (void *datasource)
-+ void * OGR_F_Create (void *featuredefn)
-+ void OGR_F_Destroy (void *feature)
-+ long OGR_F_GetFID (void *feature)
-+ int OGR_F_IsFieldSet (void *feature, int n)
-+ int OGR_F_GetFieldAsDateTime (void *feature, int n, int *y, int *m, int *d, int *h, int *m, int *s, int *z)
-+ double OGR_F_GetFieldAsDouble (void *feature, int n)
-+ int OGR_F_GetFieldAsInteger (void *feature, int n)
-+ char * OGR_F_GetFieldAsString (void *feature, int n)
-+ int OGR_F_GetFieldCount (void *feature)
-+ void * OGR_F_GetFieldDefnRef (void *feature, int n)
-+ int OGR_F_GetFieldIndex (void *feature, char *name)
-+ void * OGR_F_GetGeometryRef (void *feature)
-+ void OGR_F_SetFieldDateTime (void *feature, int n, int y, int m, int d, int hh, int mm, int ss, int tz)
-+ void OGR_F_SetFieldDouble (void *feature, int n, double value)
-+ void OGR_F_SetFieldInteger (void *feature, int n, int value)
-+ void OGR_F_SetFieldString (void *feature, int n, char *value)
-+ int OGR_F_SetGeometryDirectly (void *feature, void *geometry)
-+ void * OGR_FD_Create (char *name)
-+ int OGR_FD_GetFieldCount (void *featuredefn)
-+ void * OGR_FD_GetFieldDefn (void *featuredefn, int n)
-+ int OGR_FD_GetGeomType (void *featuredefn)
-+ char * OGR_FD_GetName (void *featuredefn)
-+ void * OGR_Fld_Create (char *name, int fieldtype)
-+ void OGR_Fld_Destroy (void *fielddefn)
-+ char * OGR_Fld_GetNameRef (void *fielddefn)
-+ int OGR_Fld_GetPrecision (void *fielddefn)
-+ int OGR_Fld_GetType (void *fielddefn)
-+ int OGR_Fld_GetWidth (void *fielddefn)
-+ void OGR_Fld_Set (void *fielddefn, char *name, int fieldtype, int width, int precision, int justification)
-+ void OGR_Fld_SetPrecision (void *fielddefn, int n)
-+ void OGR_Fld_SetWidth (void *fielddefn, int n)
-+ OGRErr OGR_G_AddGeometryDirectly (void *geometry, void *part)
-+ void OGR_G_AddPoint (void *geometry, double x, double y, double z)
-+ void OGR_G_AddPoint_2D (void *geometry, double x, double y)
-+ void OGR_G_CloseRings (void *geometry)
-+ void * OGR_G_CreateGeometry (int wkbtypecode)
-+ void OGR_G_DestroyGeometry (void *geometry)
-+ unsigned char * OGR_G_ExportToJson (void *geometry)
-+ void OGR_G_ExportToWkb (void *geometry, int endianness, char *buffer)
-+ int OGR_G_GetCoordinateDimension (void *geometry)
-+ int OGR_G_GetGeometryCount (void *geometry)
-+ unsigned char * OGR_G_GetGeometryName (void *geometry)
-+ int OGR_G_GetGeometryType (void *geometry)
-+ void * OGR_G_GetGeometryRef (void *geometry, int n)
-+ int OGR_G_GetPointCount (void *geometry)
-+ double OGR_G_GetX (void *geometry, int n)
-+ double OGR_G_GetY (void *geometry, int n)
-+ double OGR_G_GetZ (void *geometry, int n)
-+ void OGR_G_ImportFromWkb (void *geometry, unsigned char *bytes, int nbytes)
-+ int OGR_G_WkbSize (void *geometry)
-+ OGRErr OGR_L_CreateFeature (void *layer, void *feature)
-+ int OGR_L_CreateField (void *layer, void *fielddefn, int flexible)
-+ OGRErr OGR_L_GetExtent (void *layer, void *extent, int force)
-+ void * OGR_L_GetFeature (void *layer, int n)
-+ int OGR_L_GetFeatureCount (void *layer, int m)
-+ void * OGR_L_GetLayerDefn (void *layer)
-+ char * OGR_L_GetName (void *layer)
-+ void * OGR_L_GetNextFeature (void *layer)
-+ void * OGR_L_GetSpatialFilter (void *layer)
-+ void * OGR_L_GetSpatialRef (void *layer)
-+ void OGR_L_ResetReading (void *layer)
-+ void OGR_L_SetSpatialFilter (void *layer, void *geometry)
-+ void OGR_L_SetSpatialFilterRect (
-+ void *layer, double minx, double miny, double maxx, double maxy
-+ )
-+ int OGR_L_TestCapability (void *layer, char *name)
-+ void * OGRGetDriverByName (char *)
-+ void * OGROpen (char *path, int mode, void *x)
-+ void * OGROpenShared (char *path, int mode, void *x)
-+ int OGRReleaseDataSource (void *datasource)
-+ OGRErr OGR_L_SetNextByIndex (void *layer, long nIndex)
---- /dev/null
-+++ b/fiona/ograpi2.pxd
-@@ -0,0 +1,185 @@
-+# Copyright (c) 2007, Sean C. Gillies
-+# All rights reserved.
-+# See ../LICENSE.txt
-+
-+cdef extern from "gdal.h":
-+ char * GDALVersionInfo (char *pszRequest)
-+ void * GDALGetDriverByName(const char * pszName)
-+ void * GDALOpenEx(const char * pszFilename,
-+ unsigned int nOpenFlags,
-+ const char ** papszAllowedDrivers,
-+ const char ** papszOpenOptions,
-+ const char *const *papszSibling1Files
-+ )
-+ int GDAL_OF_UPDATE
-+ int GDAL_OF_READONLY
-+ int GDAL_OF_VECTOR
-+ int GDAL_OF_VERBOSE_ERROR
-+ int GDALDatasetGetLayerCount(void * hds)
-+ void * GDALDatasetGetLayer(void * hDS, int iLayer)
-+ void * GDALDatasetGetLayerByName(void * hDS, char * pszName)
-+ void GDALClose(void * hDS)
-+ void * GDALGetDatasetDriver(void * hDataset)
-+ void * GDALCreate(void * hDriver,
-+ const char * pszFilename,
-+ int nXSize,
-+ int nYSize,
-+ int nBands,
-+ GDALDataType eBandType,
-+ char ** papszOptions)
-+ void * GDALDatasetCreateLayer(void * hDS,
-+ const char * pszName,
-+ void * hSpatialRef,
-+ int eType,
-+ char ** papszOptions)
-+ int GDALDatasetDeleteLayer(void * hDS, int iLayer)
-+ void GDALFlushCache(void * hDS)
-+ char * GDALGetDriverShortName(void * hDriver)
-+ char * GDALGetDatasetDriver (void * hDataset)
-+
-+
-+ ctypedef enum GDALDataType:
-+ GDT_Unknown
-+ GDT_Byte
-+ GDT_UInt16
-+ GDT_Int16
-+ GDT_UInt32
-+ GDT_Int32
-+ GDT_Float32
-+ GDT_Float64
-+ GDT_CInt16
-+ GDT_CInt32
-+ GDT_CFloat32
-+ GDT_CFloat64
-+ GDT_TypeCount
-+
-+cdef extern from "gdal_version.h":
-+ int GDAL_COMPUTE_VERSION(int maj, int min, int rev)
-+
-+cdef extern from "cpl_conv.h":
-+ void * CPLMalloc (size_t)
-+ void CPLFree (void *ptr)
-+ void CPLSetThreadLocalConfigOption (char *key, char *val)
-+ const char *CPLGetConfigOption (char *, char *)
-+
-+cdef extern from "cpl_string.h":
-+ char ** CSLSetNameValue (char **list, char *name, char *value)
-+ void CSLDestroy (char **list)
-+
-+cdef extern from "cpl_vsi.h":
-+ ctypedef struct VSILFILE:
-+ pass
-+ int VSIFCloseL (VSILFILE *)
-+ VSILFILE * VSIFileFromMemBuffer (const char * filename,
-+ unsigned char * data,
-+ int data_len,
-+ int take_ownership)
-+ int VSIUnlink (const char * pathname)
-+
-+ctypedef int OGRErr
-+ctypedef struct OGREnvelope:
-+ double MinX
-+ double MaxX
-+ double MinY
-+ double MaxY
-+
-+cdef extern from "ogr_core.h":
-+ char * OGRGeometryTypeToName(int)
-+
-+cdef extern from "ogr_srs_api.h":
-+ void OSRCleanup ()
-+ void * OSRClone (void *srs)
-+ void OSRDestroySpatialReference (void *srs)
-+ int OSRExportToProj4 (void *srs, char **params)
-+ int OSRExportToWkt (void *srs, char **params)
-+ int OSRImportFromEPSG (void *srs, int code)
-+ int OSRImportFromProj4 (void *srs, char *proj)
-+ int OSRSetFromUserInput (void *srs, char *input)
-+ int OSRAutoIdentifyEPSG (void *srs)
-+ int OSRFixup(void *srs)
-+ const char * OSRGetAuthorityName (void *srs, const char *key)
-+ const char * OSRGetAuthorityCode (void *srs, const char *key)
-+ void * OSRNewSpatialReference (char *wkt)
-+ void OSRRelease (void *srs)
-+ void * OCTNewCoordinateTransformation (void *source, void *dest)
-+ void OCTDestroyCoordinateTransformation (void *source)
-+ int OCTTransform (void *ct, int nCount, double *x, double *y, double *z)
-+
-+cdef extern from "ogr_api.h":
-+ char * OGR_Dr_GetName (void *driver)
-+ void * OGR_Dr_CreateDataSource (void *driver, const char *path, char **options)
-+ int OGR_Dr_DeleteDataSource (void *driver, char *)
-+ void * OGR_Dr_Open (void *driver, const char *path, int bupdate)
-+ void * OGR_F_Create (void *featuredefn)
-+ void OGR_F_Destroy (void *feature)
-+ long OGR_F_GetFID (void *feature)
-+ int OGR_F_IsFieldSet (void *feature, int n)
-+ int OGR_F_GetFieldAsDateTime (void *feature, int n, int *y, int *m, int *d, int *h, int *m, int *s, int *z)
-+ double OGR_F_GetFieldAsDouble (void *feature, int n)
-+ int OGR_F_GetFieldAsInteger (void *feature, int n)
-+ char * OGR_F_GetFieldAsString (void *feature, int n)
-+ int OGR_F_GetFieldCount (void *feature)
-+ void * OGR_F_GetFieldDefnRef (void *feature, int n)
-+ int OGR_F_GetFieldIndex (void *feature, char *name)
-+ void * OGR_F_GetGeometryRef (void *feature)
-+ void OGR_F_SetFieldDateTime (void *feature, int n, int y, int m, int d, int hh, int mm, int ss, int tz)
-+ void OGR_F_SetFieldDouble (void *feature, int n, double value)
-+ void OGR_F_SetFieldInteger (void *feature, int n, int value)
-+ void OGR_F_SetFieldString (void *feature, int n, char *value)
-+ int OGR_F_SetGeometryDirectly (void *feature, void *geometry)
-+ void * OGR_FD_Create (char *name)
-+ int OGR_FD_GetFieldCount (void *featuredefn)
-+ void * OGR_FD_GetFieldDefn (void *featuredefn, int n)
-+ int OGR_FD_GetGeomType (void *featuredefn)
-+ char * OGR_FD_GetName (void *featuredefn)
-+ void * OGR_Fld_Create (char *name, int fieldtype)
-+ void OGR_Fld_Destroy (void *fielddefn)
-+ char * OGR_Fld_GetNameRef (void *fielddefn)
-+ int OGR_Fld_GetPrecision (void *fielddefn)
-+ int OGR_Fld_GetType (void *fielddefn)
-+ int OGR_Fld_GetWidth (void *fielddefn)
-+ void OGR_Fld_Set (void *fielddefn, char *name, int fieldtype, int width, int precision, int justification)
-+ void OGR_Fld_SetPrecision (void *fielddefn, int n)
-+ void OGR_Fld_SetWidth (void *fielddefn, int n)
-+ OGRErr OGR_G_AddGeometryDirectly (void *geometry, void *part)
-+ void OGR_G_AddPoint (void *geometry, double x, double y, double z)
-+ void OGR_G_AddPoint_2D (void *geometry, double x, double y)
-+ void OGR_G_CloseRings (void *geometry)
-+ void * OGR_G_CreateGeometry (int wkbtypecode)
-+ void OGR_G_DestroyGeometry (void *geometry)
-+ unsigned char * OGR_G_ExportToJson (void *geometry)
-+ void OGR_G_ExportToWkb (void *geometry, int endianness, char *buffer)
-+ int OGR_G_GetCoordinateDimension (void *geometry)
-+ int OGR_G_GetGeometryCount (void *geometry)
-+ unsigned char * OGR_G_GetGeometryName (void *geometry)
-+ int OGR_G_GetGeometryType (void *geometry)
-+ void * OGR_G_GetGeometryRef (void *geometry, int n)
-+ int OGR_G_GetPointCount (void *geometry)
-+ double OGR_G_GetX (void *geometry, int n)
-+ double OGR_G_GetY (void *geometry, int n)
-+ double OGR_G_GetZ (void *geometry, int n)
-+ void OGR_G_ImportFromWkb (void *geometry, unsigned char *bytes, int nbytes)
-+ int OGR_G_WkbSize (void *geometry)
-+ OGRErr OGR_L_CreateFeature (void *layer, void *feature)
-+ int OGR_L_CreateField (void *layer, void *fielddefn, int flexible)
-+ OGRErr OGR_L_GetExtent (void *layer, void *extent, int force)
-+ void * OGR_L_GetFeature (void *layer, int n)
-+ int OGR_L_GetFeatureCount (void *layer, int m)
-+ void * OGR_L_GetLayerDefn (void *layer)
-+ char * OGR_L_GetName (void *layer)
-+ void * OGR_L_GetNextFeature (void *layer)
-+ void * OGR_L_GetSpatialFilter (void *layer)
-+ void * OGR_L_GetSpatialRef (void *layer)
-+ void OGR_L_ResetReading (void *layer)
-+ void OGR_L_SetSpatialFilter (void *layer, void *geometry)
-+ void OGR_L_SetSpatialFilterRect (
-+ void *layer, double minx, double miny, double maxx, double maxy
-+ )
-+ int OGR_L_TestCapability (void *layer, char *name)
-+ void * OGRGetDriverByName (char *)
-+ void * OGROpen (char *path, int mode, void *x)
-+ void * OGROpenShared (char *path, int mode, void *x)
-+ int OGRReleaseDataSource (void *datasource)
-+ OGRErr OGR_L_SetNextByIndex (void *layer, long nIndex)
-+ long long OGR_F_GetFieldAsInteger64 (void *feature, int n)
-+ void OGR_F_SetFieldInteger64 (void *feature, int n, long long value)
---- a/fiona/ogrext.pyx
-+++ /dev/null
-@@ -1,1245 +0,0 @@
--# These are extension functions and classes using the OGR C API.
--
--import datetime
--import json
--import locale
--import logging
--import os
--import sys
--import warnings
--import math
--import uuid
--
--from six import integer_types, string_types, text_type
--
--from fiona cimport ograpi
--from fiona._geometry cimport GeomBuilder, OGRGeomBuilder
--from fiona._err import cpl_errs
--from fiona._geometry import GEOMETRY_TYPES
--from fiona.errors import (
-- DriverError, SchemaError, CRSError, FionaValueError, FieldNameEncodeError,
-- StringFieldEncodeError, StringFieldDecodeError)
--from fiona.odict import OrderedDict
--from fiona.rfc3339 import parse_date, parse_datetime, parse_time
--from fiona.rfc3339 import FionaDateType, FionaDateTimeType, FionaTimeType
--
--
--log = logging.getLogger("Fiona")
--class NullHandler(logging.Handler):
-- def emit(self, record):
-- pass
--log.addHandler(NullHandler())
--
--
--# Mapping of OGR integer field types to Fiona field type names.
--#
--# Lists are currently unsupported in this version, but might be done as
--# arrays in a future version.
--
--FIELD_TYPES = [
-- 'int', # OFTInteger, Simple 32bit integer
-- None, # OFTIntegerList, List of 32bit integers
-- 'float', # OFTReal, Double Precision floating point
-- None, # OFTRealList, List of doubles
-- 'str', # OFTString, String of ASCII chars
-- None, # OFTStringList, Array of strings
-- None, # OFTWideString, deprecated
-- None, # OFTWideStringList, deprecated
-- None, # OFTBinary, Raw Binary data
-- 'date', # OFTDate, Date
-- 'time', # OFTTime, Time
-- 'datetime', # OFTDateTime, Date and Time
-- 'int', # OFTInteger64, Single 64bit integer #Not supported
-- None, # OFTInteger64List, List of 64bit integers #Not supported
-- ]
--
--# Mapping of Fiona field type names to Python types.
--FIELD_TYPES_MAP = {
-- 'int': int,
-- 'float': float,
-- 'str': text_type,
-- 'date': FionaDateType,
-- 'time': FionaTimeType,
-- 'datetime': FionaDateTimeType
-- }
--
--# OGR Layer capability
--OLC_RANDOMREAD = b"RandomRead"
--OLC_SEQUENTIALWRITE = b"SequentialWrite"
--OLC_RANDOMWRITE = b"RandomWrite"
--OLC_FASTSPATIALFILTER = b"FastSpatialFilter"
--OLC_FASTFEATURECOUNT = b"FastFeatureCount"
--OLC_FASTGETEXTENT = b"FastGetExtent"
--OLC_FASTSETNEXTBYINDEX = b"FastSetNextByIndex"
--OLC_CREATEFIELD = b"CreateField"
--OLC_CREATEGEOMFIELD = b"CreateGeomField"
--OLC_DELETEFIELD = b"DeleteField"
--OLC_REORDERFIELDS = b"ReorderFields"
--OLC_ALTERFIELDDEFN = b"AlterFieldDefn"
--OLC_DELETEFEATURE = b"DeleteFeature"
--OLC_STRINGSASUTF8 = b"StringsAsUTF8"
--OLC_TRANSACTIONS = b"Transactions"
--
--# OGR integer error types.
--
--OGRERR_NONE = 0
--OGRERR_NOT_ENOUGH_DATA = 1 # not enough data to deserialize */
--OGRERR_NOT_ENOUGH_MEMORY = 2
--OGRERR_UNSUPPORTED_GEOMETRY_TYPE = 3
--OGRERR_UNSUPPORTED_OPERATION = 4
--OGRERR_CORRUPT_DATA = 5
--OGRERR_FAILURE = 6
--OGRERR_UNSUPPORTED_SRS = 7
--OGRERR_INVALID_HANDLE = 8
--
--# Recent versions of OGR can sometimes detect file encoding, but don't
--# provide access yet to the detected encoding. Hence this variable.
--OGR_DETECTED_ENCODING = '-ogr-detected-encoding'
--
--
--def _explode(coords):
-- """Explode a GeoJSON geometry's coordinates object and yield
-- coordinate tuples. As long as the input is conforming, the type of
-- the geometry doesn't matter."""
-- for e in coords:
-- if isinstance(e, (float, int)):
-- yield coords
-- break
-- else:
-- for f in _explode(e):
-- yield f
--
--
--def _bounds(geometry):
-- """Bounding box of a GeoJSON geometry"""
-- try:
-- xyz = tuple(zip(*list(_explode(geometry['coordinates']))))
-- return min(xyz[0]), min(xyz[1]), max(xyz[0]), max(xyz[1])
-- except (KeyError, TypeError):
-- return None
--
--def calc_gdal_version_num(maj, min, rev):
-- """Calculates the internal gdal version number based on major, minor and revision"""
-- return int(maj * 1000000 + min * 10000 + rev*100)
--
--def get_gdal_version_num():
-- """Return current internal version number of gdal"""
-- return int(ograpi.GDALVersionInfo("VERSION_NUM"))
--
--def get_gdal_release_name():
-- """Return release name of gdal"""
-- return ograpi.GDALVersionInfo("RELEASE_NAME")
--
--
--# Feature extension classes and functions follow.
--
--cdef class FeatureBuilder:
-- """Build Fiona features from OGR feature pointers.
--
-- No OGR objects are allocated by this function and the feature
-- argument is not destroyed.
-- """
--
-- cdef build(self, void *feature, encoding='utf-8', bbox=False, driver=None):
-- # The only method anyone ever needs to call
-- cdef void *fdefn
-- cdef int i
-- cdef int y = 0
-- cdef int m = 0
-- cdef int d = 0
-- cdef int hh = 0
-- cdef int mm = 0
-- cdef int ss = 0
-- cdef int tz = 0
-- cdef int retval
-- cdef char *key_c
-- props = OrderedDict()
-- for i in range(ograpi.OGR_F_GetFieldCount(feature)):
-- fdefn = ograpi.OGR_F_GetFieldDefnRef(feature, i)
-- if fdefn == NULL:
-- raise ValueError("Null feature definition")
-- key_c = ograpi.OGR_Fld_GetNameRef(fdefn)
-- if key_c == NULL:
-- raise ValueError("Null field name reference")
-- key_b = key_c
-- key = key_b.decode(encoding)
-- fieldtypename = FIELD_TYPES[ograpi.OGR_Fld_GetType(fdefn)]
-- if not fieldtypename:
-- log.warn(
-- "Skipping field %s: invalid type %s",
-- key,
-- ograpi.OGR_Fld_GetType(fdefn))
-- continue
--
-- # TODO: other types
-- fieldtype = FIELD_TYPES_MAP[fieldtypename]
-- if not ograpi.OGR_F_IsFieldSet(feature, i):
-- props[key] = None
-- elif fieldtype is int:
-- props[key] = ograpi.OGR_F_GetFieldAsInteger(feature, i)
-- elif fieldtype is float:
-- props[key] = ograpi.OGR_F_GetFieldAsDouble(feature, i)
--
-- elif fieldtype is text_type:
-- try:
-- val = ograpi.OGR_F_GetFieldAsString(feature, i)
-- val = val.decode(encoding)
-- except UnicodeError as exc:
-- raise StringFieldDecodeError(
-- "Failed to decode {0} using {1} codec: {2}".format(
-- val, encoding, str(exc)))
--
-- # Does the text contain a JSON object? Let's check.
-- # Let's check as cheaply as we can.
-- if driver == 'GeoJSON' and val.startswith('{'):
-- try:
-- val = json.loads(val)
-- except ValueError as err:
-- log.warn(str(err))
--
-- # Now add to the properties object.
-- props[key] = val
--
-- elif fieldtype in (FionaDateType, FionaTimeType, FionaDateTimeType):
-- retval = ograpi.OGR_F_GetFieldAsDateTime(
-- feature, i, &y, &m, &d, &hh, &mm, &ss, &tz)
-- if fieldtype is FionaDateType:
-- props[key] = datetime.date(y, m, d).isoformat()
-- elif fieldtype is FionaTimeType:
-- props[key] = datetime.time(hh, mm, ss).isoformat()
-- else:
-- props[key] = datetime.datetime(
-- y, m, d, hh, mm, ss).isoformat()
-- else:
-- log.debug("%s: None, fieldtype: %r, %r" % (key, fieldtype, fieldtype in string_types))
-- props[key] = None
--
-- cdef void *cogr_geometry = ograpi.OGR_F_GetGeometryRef(feature)
-- if cogr_geometry is not NULL:
-- geom = GeomBuilder().build(cogr_geometry)
-- else:
-- geom = None
-- return {
-- 'type': 'Feature',
-- 'id': str(ograpi.OGR_F_GetFID(feature)),
-- 'geometry': geom,
-- 'properties': props }
--
--
--cdef class OGRFeatureBuilder:
--
-- """Builds an OGR Feature from a Fiona feature mapping.
--
-- Allocates one OGR Feature which should be destroyed by the caller.
-- Borrows a layer definition from the collection.
-- """
--
-- cdef void * build(self, feature, collection) except NULL:
-- cdef void *cogr_geometry = NULL
-- cdef char *string_c
-- cdef WritingSession session
-- session = collection.session
-- cdef void *cogr_layer = session.cogr_layer
-- if cogr_layer == NULL:
-- raise ValueError("Null layer")
-- cdef void *cogr_featuredefn = ograpi.OGR_L_GetLayerDefn(cogr_layer)
-- if cogr_featuredefn == NULL:
-- raise ValueError("Null feature definition")
-- cdef void *cogr_feature = ograpi.OGR_F_Create(cogr_featuredefn)
-- if cogr_feature == NULL:
-- raise ValueError("Null feature")
--
-- if feature['geometry'] is not None:
-- cogr_geometry = OGRGeomBuilder().build(
-- feature['geometry'])
-- ograpi.OGR_F_SetGeometryDirectly(cogr_feature, cogr_geometry)
--
-- # OGR_F_SetFieldString takes UTF-8 encoded strings ('bytes' in
-- # Python 3).
-- encoding = session.get_internalencoding()
--
-- for key, value in feature['properties'].items():
-- log.debug(
-- "Looking up %s in %s", key, repr(session._schema_mapping))
-- ogr_key = session._schema_mapping[key]
-- schema_type = collection.schema['properties'][key]
--
-- # Catch and re-raise unicode encoding errors.
-- try:
-- key_bytes = ogr_key.encode(encoding)
-- except UnicodeError as exc:
-- raise FieldNameEncodeError(
-- "Failed to encode {0} using {1} codec: {2}".format(
-- key, encoding, str(exc)))
--
-- key_c = key_bytes
-- i = ograpi.OGR_F_GetFieldIndex(cogr_feature, key_c)
-- if i < 0:
-- continue
--
-- # Special case: serialize dicts to assist OGR.
-- if isinstance(value, dict):
-- value = json.dumps(value)
--
-- # Continue over the standard OGR types.
-- if isinstance(value, integer_types):
-- ograpi.OGR_F_SetFieldInteger(cogr_feature, i, value)
-- elif isinstance(value, float):
-- ograpi.OGR_F_SetFieldDouble(cogr_feature, i, value)
-- elif (isinstance(value, string_types)
-- and schema_type in ['date', 'time', 'datetime']):
-- if schema_type == 'date':
-- y, m, d, hh, mm, ss, ff = parse_date(value)
-- elif schema_type == 'time':
-- y, m, d, hh, mm, ss, ff = parse_time(value)
-- else:
-- y, m, d, hh, mm, ss, ff = parse_datetime(value)
-- ograpi.OGR_F_SetFieldDateTime(
-- cogr_feature, i, y, m, d, hh, mm, ss, 0)
-- elif (isinstance(value, datetime.date)
-- and schema_type == 'date'):
-- y, m, d = value.year, value.month, value.day
-- ograpi.OGR_F_SetFieldDateTime(
-- cogr_feature, i, y, m, d, 0, 0, 0, 0)
-- elif (isinstance(value, datetime.datetime)
-- and schema_type == 'datetime'):
-- y, m, d = value.year, value.month, value.day
-- hh, mm, ss = value.hour, value.minute, value.second
-- ograpi.OGR_F_SetFieldDateTime(
-- cogr_feature, i, y, m, d, hh, mm, ss, 0)
-- elif (isinstance(value, datetime.time)
-- and schema_type == 'time'):
-- hh, mm, ss = value.hour, value.minute, value.second
-- ograpi.OGR_F_SetFieldDateTime(
-- cogr_feature, i, 0, 0, 0, hh, mm, ss, 0)
-- elif isinstance(value, string_types):
--
-- # Catch and re-raise string field value encoding errors.
-- try:
-- value_bytes = value.encode(encoding)
-- except UnicodeError as exc:
-- raise StringFieldEncodeError(
-- "Failed to encode {0} using {1} codec: {2}".format(
-- value, encoding, str(exc)))
--
-- string_c = value_bytes
-- ograpi.OGR_F_SetFieldString(cogr_feature, i, string_c)
-- elif value is None:
-- pass # keep field unset/null
-- else:
-- raise ValueError("Invalid field type %s" % type(value))
-- log.debug("Set field %s: %s" % (key, value))
-- return cogr_feature
--
--
--cdef _deleteOgrFeature(void *cogr_feature):
-- """Delete an OGR feature"""
-- if cogr_feature is not NULL:
-- ograpi.OGR_F_Destroy(cogr_feature)
-- cogr_feature = NULL
--
--
--def featureRT(feature, collection):
-- # For testing purposes only, leaks the JSON data
-- cdef void *cogr_feature = OGRFeatureBuilder().build(feature, collection)
-- cdef void *cogr_geometry = ograpi.OGR_F_GetGeometryRef(cogr_feature)
-- if cogr_geometry == NULL:
-- raise ValueError("Null geometry")
-- log.debug("Geometry: %s" % ograpi.OGR_G_ExportToJson(cogr_geometry))
-- encoding = collection.encoding or 'utf-8'
-- result = FeatureBuilder().build(
-- cogr_feature,
-- bbox=False,
-- encoding=encoding,
-- driver=collection.driver
-- )
-- _deleteOgrFeature(cogr_feature)
-- return result
--
--
--# Collection-related extension classes and functions
--
--cdef class Session:
--
-- cdef void *cogr_ds
-- cdef void *cogr_layer
-- cdef object _fileencoding
-- cdef object _encoding
-- cdef object collection
--
-- def __cinit__(self):
-- self.cogr_ds = NULL
-- self.cogr_layer = NULL
-- self._fileencoding = None
-- self._encoding = None
--
-- def __dealloc__(self):
-- self.stop()
--
-- def start(self, collection):
-- cdef const char *path_c = NULL
-- cdef const char *name_c = NULL
-- cdef void *drv = NULL
-- cdef void *ds = NULL
--
-- if collection.path == '-':
-- path = '/vsistdin/'
-- else:
-- path = collection.path
-- try:
-- path_b = path.encode('utf-8')
-- except UnicodeError:
-- # Presume already a UTF-8 encoded string
-- path_b = path
-- path_c = path_b
--
-- with cpl_errs:
-- drivers = []
-- if collection._driver:
-- drivers = [collection._driver]
-- elif collection.enabled_drivers:
-- drivers = collection.enabled_drivers
-- if drivers:
-- for name in drivers:
-- name_b = name.encode()
-- name_c = name_b
-- log.debug("Trying driver: %s", name)
-- drv = ograpi.OGRGetDriverByName(name_c)
-- if drv != NULL:
-- ds = ograpi.OGR_Dr_Open(drv, path_c, 0)
-- if ds != NULL:
-- self.cogr_ds = ds
-- collection._driver = name
-- break
-- else:
-- self.cogr_ds = ograpi.OGROpen(path_c, 0, NULL)
--
-- if self.cogr_ds == NULL:
-- raise FionaValueError(
-- "No dataset found at path '%s' using drivers: %s" % (
-- collection.path,
-- drivers or '*'))
--
-- if isinstance(collection.name, string_types):
-- name_b = collection.name.encode('utf-8')
-- name_c = name_b
-- self.cogr_layer = ograpi.OGR_DS_GetLayerByName(
-- self.cogr_ds, name_c)
-- elif isinstance(collection.name, int):
-- self.cogr_layer = ograpi.OGR_DS_GetLayer(
-- self.cogr_ds, collection.name)
-- name_c = ograpi.OGR_L_GetName(self.cogr_layer)
-- name_b = name_c
-- collection.name = name_b.decode('utf-8')
--
-- if self.cogr_layer == NULL:
-- raise ValueError("Null layer: " + repr(collection.name))
--
-- self.collection = collection
--
-- userencoding = self.collection.encoding
-- if userencoding:
-- ograpi.CPLSetThreadLocalConfigOption('SHAPE_ENCODING', '')
-- self._fileencoding = userencoding.upper()
-- else:
-- self._fileencoding = (
-- ograpi.OGR_L_TestCapability(
-- self.cogr_layer, OLC_STRINGSASUTF8) and
-- OGR_DETECTED_ENCODING) or (
-- self.get_driver() == "ESRI Shapefile" and
-- 'ISO-8859-1') or locale.getpreferredencoding().upper()
--
-- def stop(self):
-- self.cogr_layer = NULL
-- if self.cogr_ds is not NULL:
-- ograpi.OGR_DS_Destroy(self.cogr_ds)
-- self.cogr_ds = NULL
--
-- def get_fileencoding(self):
-- return self._fileencoding
--
-- def get_internalencoding(self):
-- if not self._encoding:
-- fileencoding = self.get_fileencoding()
-- self._encoding = (
-- ograpi.OGR_L_TestCapability(
-- self.cogr_layer, OLC_STRINGSASUTF8) and
-- 'utf-8') or fileencoding
-- return self._encoding
--
-- def get_length(self):
-- if self.cogr_layer == NULL:
-- raise ValueError("Null layer")
-- return ograpi.OGR_L_GetFeatureCount(self.cogr_layer, 0)
--
-- def get_driver(self):
-- cdef void *cogr_driver = ograpi.OGR_DS_GetDriver(self.cogr_ds)
-- if cogr_driver == NULL:
-- raise ValueError("Null driver")
-- cdef char *name = ograpi.OGR_Dr_GetName(cogr_driver)
-- driver_name = name
-- return driver_name.decode()
--
-- def get_schema(self):
-- cdef int i
-- cdef int n
-- cdef void *cogr_featuredefn
-- cdef void *cogr_fielddefn
-- cdef char *key_c
-- props = []
--
-- if self.cogr_layer == NULL:
-- raise ValueError("Null layer")
--
-- cogr_featuredefn = ograpi.OGR_L_GetLayerDefn(self.cogr_layer)
-- if cogr_featuredefn == NULL:
-- raise ValueError("Null feature definition")
-- n = ograpi.OGR_FD_GetFieldCount(cogr_featuredefn)
-- for i from 0 <= i < n:
-- cogr_fielddefn = ograpi.OGR_FD_GetFieldDefn(cogr_featuredefn, i)
-- if cogr_fielddefn == NULL:
-- raise ValueError("Null field definition")
-- key_c = ograpi.OGR_Fld_GetNameRef(cogr_fielddefn)
-- key_b = key_c
-- if not bool(key_b):
-- raise ValueError("Invalid field name ref: %s" % key)
-- key = key_b.decode(self.get_internalencoding())
-- fieldtypename = FIELD_TYPES[ograpi.OGR_Fld_GetType(cogr_fielddefn)]
-- if not fieldtypename:
-- log.warn(
-- "Skipping field %s: invalid type %s",
-- key,
-- ograpi.OGR_Fld_GetType(cogr_fielddefn))
-- continue
-- val = fieldtypename
-- if fieldtypename == 'float':
-- fmt = ""
-- width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-- if width: # and width != 24:
-- fmt = ":%d" % width
-- precision = ograpi.OGR_Fld_GetPrecision(cogr_fielddefn)
-- if precision: # and precision != 15:
-- fmt += ".%d" % precision
-- val = "float" + fmt
-- elif fieldtypename == 'int':
-- fmt = ""
-- width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-- if width: # and width != 11:
-- fmt = ":%d" % width
-- val = fieldtypename + fmt
-- elif fieldtypename == 'str':
-- fmt = ""
-- width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-- if width: # and width != 80:
-- fmt = ":%d" % width
-- val = fieldtypename + fmt
--
-- props.append((key, val))
--
-- cdef unsigned int geom_type = ograpi.OGR_FD_GetGeomType(
-- cogr_featuredefn)
-- return {
-- 'properties': OrderedDict(props),
-- 'geometry': GEOMETRY_TYPES[geom_type]}
--
-- def get_crs(self):
-- cdef char *proj_c = NULL
-- cdef char *auth_key = NULL
-- cdef char *auth_val = NULL
-- cdef void *cogr_crs = NULL
-- if self.cogr_layer == NULL:
-- raise ValueError("Null layer")
-- cogr_crs = ograpi.OGR_L_GetSpatialRef(self.cogr_layer)
-- crs = {}
-- if cogr_crs is not NULL:
-- log.debug("Got coordinate system")
--
-- retval = ograpi.OSRAutoIdentifyEPSG(cogr_crs)
-- if retval > 0:
-- log.info("Failed to auto identify EPSG: %d", retval)
--
-- auth_key = ograpi.OSRGetAuthorityName(cogr_crs, NULL)
-- auth_val = ograpi.OSRGetAuthorityCode(cogr_crs, NULL)
--
-- if auth_key != NULL and auth_val != NULL:
-- key_b = auth_key
-- key = key_b.decode('utf-8')
-- if key == 'EPSG':
-- val_b = auth_val
-- val = val_b.decode('utf-8')
-- crs['init'] = "epsg:" + val
-- else:
-- ograpi.OSRExportToProj4(cogr_crs, &proj_c)
-- if proj_c == NULL:
-- raise ValueError("Null projection")
-- proj_b = proj_c
-- log.debug("Params: %s", proj_b)
-- value = proj_b.decode()
-- value = value.strip()
-- for param in value.split():
-- kv = param.split("=")
-- if len(kv) == 2:
-- k, v = kv
-- try:
-- v = float(v)
-- if v % 1 == 0:
-- v = int(v)
-- except ValueError:
-- # Leave v as a string
-- pass
-- elif len(kv) == 1:
-- k, v = kv[0], True
-- else:
-- raise ValueError("Unexpected proj parameter %s" % param)
-- k = k.lstrip("+")
-- crs[k] = v
--
-- ograpi.CPLFree(proj_c)
-- else:
-- log.debug("Projection not found (cogr_crs was NULL)")
-- return crs
--
-- def get_crs_wkt(self):
-- cdef char *proj_c = NULL
-- if self.cogr_layer == NULL:
-- raise ValueError("Null layer")
-- cogr_crs = ograpi.OGR_L_GetSpatialRef(self.cogr_layer)
-- crs_wkt = ""
-- if cogr_crs is not NULL:
-- log.debug("Got coordinate system")
-- ograpi.OSRExportToWkt(cogr_crs, &proj_c)
-- if proj_c == NULL:
-- raise ValueError("Null projection")
-- proj_b = proj_c
-- crs_wkt = proj_b.decode('utf-8')
-- ograpi.CPLFree(proj_c)
-- else:
-- log.debug("Projection not found (cogr_crs was NULL)")
-- return crs_wkt
--
-- def get_extent(self):
-- if self.cogr_layer == NULL:
-- raise ValueError("Null layer")
-- cdef ograpi.OGREnvelope extent
-- result = ograpi.OGR_L_GetExtent(self.cogr_layer, &extent, 1)
-- return (extent.MinX, extent.MinY, extent.MaxX, extent.MaxY)
--
-- def has_feature(self, fid):
-- """Provides access to feature data by FID.
--
-- Supports Collection.__contains__().
-- """
-- cdef void * cogr_feature
-- fid = int(fid)
-- cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, fid)
-- if cogr_feature != NULL:
-- _deleteOgrFeature(cogr_feature)
-- return True
-- else:
-- return False
--
-- def get_feature(self, fid):
-- """Provides access to feature data by FID.
--
-- Supports Collection.__contains__().
-- """
-- cdef void * cogr_feature
-- fid = int(fid)
-- cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, fid)
-- if cogr_feature != NULL:
-- _deleteOgrFeature(cogr_feature)
-- return True
-- else:
-- return False
--
--
-- def __getitem__(self, item):
-- cdef void * cogr_feature
-- if isinstance(item, slice):
-- itr = Iterator(self.collection, item.start, item.stop, item.step)
-- log.debug("Slice: %r", item)
-- return list(itr)
-- elif isinstance(item, int):
-- index = item
-- # from the back
-- if index < 0:
-- ftcount = ograpi.OGR_L_GetFeatureCount(self.cogr_layer, 0)
-- if ftcount == -1:
-- raise IndexError(
-- "collection's dataset does not support negative indexes")
-- index += ftcount
-- cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, index)
-- if cogr_feature == NULL:
-- return None
-- feature = FeatureBuilder().build(
-- cogr_feature,
-- bbox=False,
-- encoding=self.get_internalencoding(),
-- driver=self.collection.driver
-- )
-- _deleteOgrFeature(cogr_feature)
-- return feature
--
--
-- def isactive(self):
-- if self.cogr_layer != NULL and self.cogr_ds != NULL:
-- return 1
-- else:
-- return 0
--
--
--cdef class WritingSession(Session):
--
-- cdef object _schema_mapping
--
-- def start(self, collection):
-- cdef void *cogr_fielddefn
-- cdef void *cogr_driver
-- cdef void *cogr_ds
-- cdef void *cogr_layer
-- cdef void *cogr_srs = NULL
-- cdef char **options = NULL
-- self.collection = collection
-- cdef char *path_c
-- cdef char *driver_c
-- cdef char *name_c
-- cdef char *proj_c
-- cdef char *fileencoding_c
-- path = collection.path
--
-- if collection.mode == 'a':
-- if os.path.exists(path):
-- try:
-- path_b = path.encode('utf-8')
-- except UnicodeError:
-- path_b = path
-- path_c = path_b
-- with cpl_errs:
-- self.cogr_ds = ograpi.OGROpen(path_c, 1, NULL)
-- if self.cogr_ds == NULL:
-- raise RuntimeError("Failed to open %s" % path)
-- cogr_driver = ograpi.OGR_DS_GetDriver(self.cogr_ds)
-- if cogr_driver == NULL:
-- raise ValueError("Null driver")
--
-- if isinstance(collection.name, string_types):
-- name_b = collection.name.encode()
-- name_c = name_b
-- self.cogr_layer = ograpi.OGR_DS_GetLayerByName(
-- self.cogr_ds, name_c)
-- elif isinstance(collection.name, int):
-- self.cogr_layer = ograpi.OGR_DS_GetLayer(
-- self.cogr_ds, collection.name)
--
-- if self.cogr_layer == NULL:
-- raise RuntimeError(
-- "Failed to get layer %s" % collection.name)
-- else:
-- raise OSError("No such file or directory %s" % path)
--
-- userencoding = self.collection.encoding
-- self._fileencoding = (userencoding or (
-- ograpi.OGR_L_TestCapability(self.cogr_layer, OLC_STRINGSASUTF8) and
-- OGR_DETECTED_ENCODING) or (
-- self.get_driver() == "ESRI Shapefile" and
-- 'ISO-8859-1') or locale.getpreferredencoding()).upper()
--
-- elif collection.mode == 'w':
-- try:
-- path_b = path.encode('utf-8')
-- except UnicodeError:
-- path_b = path
-- path_c = path_b
-- driver_b = collection.driver.encode()
-- driver_c = driver_b
--
-- cogr_driver = ograpi.OGRGetDriverByName(driver_c)
-- if cogr_driver == NULL:
-- raise ValueError("Null driver")
--
-- if not os.path.exists(path):
-- cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-- cogr_driver, path_c, NULL)
--
-- else:
-- with cpl_errs:
-- cogr_ds = ograpi.OGROpen(path_c, 1, NULL)
-- if cogr_ds == NULL:
-- cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-- cogr_driver, path_c, NULL)
--
-- elif collection.name is None:
-- ograpi.OGR_DS_Destroy(cogr_ds)
-- cogr_ds == NULL
-- log.debug("Deleted pre-existing data at %s", path)
--
-- cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-- cogr_driver, path_c, NULL)
--
-- else:
-- pass
--
-- if cogr_ds == NULL:
-- raise RuntimeError("Failed to open %s" % path)
-- else:
-- self.cogr_ds = cogr_ds
--
-- # Set the spatial reference system from the crs given to the
-- # collection constructor. We by-pass the crs_wkt and crs
-- # properties because they aren't accessible until the layer
-- # is constructed (later).
-- col_crs = collection._crs_wkt or collection._crs
-- if col_crs:
-- cogr_srs = ograpi.OSRNewSpatialReference(NULL)
-- if cogr_srs == NULL:
-- raise ValueError("NULL spatial reference")
-- # First, check for CRS strings like "EPSG:3857".
-- if isinstance(col_crs, string_types):
-- proj_b = col_crs.encode('utf-8')
-- proj_c = proj_b
-- ograpi.OSRSetFromUserInput(cogr_srs, proj_c)
-- elif isinstance(col_crs, dict):
-- # EPSG is a special case.
-- init = col_crs.get('init')
-- if init:
-- log.debug("Init: %s", init)
-- auth, val = init.split(':')
-- if auth.upper() == 'EPSG':
-- log.debug("Setting EPSG: %s", val)
-- ograpi.OSRImportFromEPSG(cogr_srs, int(val))
-- else:
-- params = []
-- col_crs['wktext'] = True
-- for k, v in col_crs.items():
-- if v is True or (k in ('no_defs', 'wktext') and v):
-- params.append("+%s" % k)
-- else:
-- params.append("+%s=%s" % (k, v))
-- proj = " ".join(params)
-- log.debug("PROJ.4 to be imported: %r", proj)
-- proj_b = proj.encode('utf-8')
-- proj_c = proj_b
-- ograpi.OSRImportFromProj4(cogr_srs, proj_c)
-- else:
-- raise ValueError("Invalid CRS")
--
-- # Fixup, export to WKT, and set the GDAL dataset's projection.
-- ograpi.OSRFixup(cogr_srs)
--
-- # Figure out what encoding to use. The encoding parameter given
-- # to the collection constructor takes highest precedence, then
-- # 'iso-8859-1', then the system's default encoding as last resort.
-- sysencoding = locale.getpreferredencoding()
-- userencoding = collection.encoding
-- self._fileencoding = (userencoding or (
-- collection.driver == "ESRI Shapefile" and
-- 'ISO-8859-1') or sysencoding).upper()
--
-- fileencoding = self.get_fileencoding()
-- if fileencoding:
-- fileencoding_b = fileencoding.encode()
-- fileencoding_c = fileencoding_b
-- options = ograpi.CSLSetNameValue(options, "ENCODING", fileencoding_c)
--
-- # Does the layer exist already? If so, we delete it.
-- layer_count = ograpi.OGR_DS_GetLayerCount(self.cogr_ds)
-- layer_names = []
-- for i in range(layer_count):
-- cogr_layer = ograpi.OGR_DS_GetLayer(cogr_ds, i)
-- name_c = ograpi.OGR_L_GetName(cogr_layer)
-- name_b = name_c
-- layer_names.append(name_b.decode('utf-8'))
--
-- idx = -1
-- if isinstance(collection.name, string_types):
-- if collection.name in layer_names:
-- idx = layer_names.index(collection.name)
-- elif isinstance(collection.name, int):
-- if collection.name >= 0 and collection.name < layer_count:
-- idx = collection.name
-- if idx >= 0:
-- log.debug("Deleted pre-existing layer at %s", collection.name)
-- ograpi.OGR_DS_DeleteLayer(self.cogr_ds, idx)
--
-- # Create the named layer in the datasource.
-- name_b = collection.name.encode('utf-8')
-- name_c = name_b
-- self.cogr_layer = ograpi.OGR_DS_CreateLayer(
-- self.cogr_ds,
-- name_c,
-- cogr_srs,
-- <unsigned int>[k for k,v in GEOMETRY_TYPES.items() if
-- v == collection.schema.get('geometry', 'Unknown')][0],
-- options
-- )
--
-- if cogr_srs != NULL:
-- ograpi.OSRDestroySpatialReference(cogr_srs)
-- if options != NULL:
-- ograpi.CSLDestroy(options)
--
-- if self.cogr_layer == NULL:
-- raise ValueError("Null layer")
-- log.debug("Created layer")
--
-- # Next, make a layer definition from the given schema properties,
-- # which are an ordered dict since Fiona 1.0.1.
-- for key, value in collection.schema['properties'].items():
-- log.debug("Creating field: %s %s", key, value)
--
-- # Convert 'long' to 'int'. See
-- # https://github.com/Toblerity/Fiona/issues/101.
-- if value == 'long':
-- value = 'int'
--
-- # Is there a field width/precision?
-- width = precision = None
-- if ':' in value:
-- value, fmt = value.split(':')
-- if '.' in fmt:
-- width, precision = map(int, fmt.split('.'))
-- else:
-- width = int(fmt)
--
-- encoding = self.get_internalencoding()
-- key_bytes = key.encode(encoding)
-- cogr_fielddefn = ograpi.OGR_Fld_Create(
-- key_bytes,
-- FIELD_TYPES.index(value) )
-- if cogr_fielddefn == NULL:
-- raise ValueError("Null field definition")
-- if width:
-- ograpi.OGR_Fld_SetWidth(cogr_fielddefn, width)
-- if precision:
-- ograpi.OGR_Fld_SetPrecision(cogr_fielddefn, precision)
-- ograpi.OGR_L_CreateField(self.cogr_layer, cogr_fielddefn, 1)
-- ograpi.OGR_Fld_Destroy(cogr_fielddefn)
-- log.debug("Created fields")
--
-- # Mapping of the Python collection schema to the munged
-- # OGR schema.
-- ogr_schema = self.get_schema()
-- self._schema_mapping = dict(zip(
-- collection.schema['properties'].keys(),
-- ogr_schema['properties'].keys() ))
--
-- log.debug("Writing started")
--
-- def writerecs(self, records, collection):
-- """Writes buffered records to OGR."""
-- cdef void *cogr_driver
-- cdef void *cogr_feature
--
-- cdef void *cogr_layer = self.cogr_layer
-- if cogr_layer == NULL:
-- raise ValueError("Null layer")
--
-- schema_geom_type = collection.schema['geometry']
-- cogr_driver = ograpi.OGR_DS_GetDriver(self.cogr_ds)
-- if ograpi.OGR_Dr_GetName(cogr_driver) == b"GeoJSON":
-- def validate_geometry_type(rec):
-- return True
-- elif ograpi.OGR_Dr_GetName(cogr_driver) == b"ESRI Shapefile" \
-- and "Point" not in collection.schema['geometry']:
-- schema_geom_type = collection.schema['geometry'].lstrip(
-- "3D ").lstrip("Multi")
-- def validate_geometry_type(rec):
-- return rec['geometry'] is None or \
-- rec['geometry']['type'].lstrip(
-- "3D ").lstrip("Multi") == schema_geom_type
-- else:
-- schema_geom_type = collection.schema['geometry'].lstrip("3D ")
-- def validate_geometry_type(rec):
-- return rec['geometry'] is None or \
-- rec['geometry']['type'].lstrip("3D ") == schema_geom_type
--
-- schema_props_keys = set(collection.schema['properties'].keys())
-- for record in records:
-- log.debug("Creating feature in layer: %s" % record)
-- # Validate against collection's schema.
-- if set(record['properties'].keys()) != schema_props_keys:
-- raise ValueError(
-- "Record does not match collection schema: %r != %r" % (
-- record['properties'].keys(),
-- list(schema_props_keys) ))
-- if not validate_geometry_type(record):
-- raise ValueError(
-- "Record's geometry type does not match "
-- "collection schema's geometry type: %r != %r" % (
-- record['geometry']['type'],
-- collection.schema['geometry'] ))
--
-- cogr_feature = OGRFeatureBuilder().build(record, collection)
-- result = ograpi.OGR_L_CreateFeature(cogr_layer, cogr_feature)
-- if result != OGRERR_NONE:
-- raise RuntimeError("Failed to write record: %s" % record)
-- _deleteOgrFeature(cogr_feature)
--
-- def sync(self, collection):
-- """Syncs OGR to disk."""
-- cdef void *cogr_ds = self.cogr_ds
-- cdef void *cogr_layer = self.cogr_layer
-- if cogr_ds == NULL:
-- raise ValueError("Null data source")
-- log.debug("Syncing OGR to disk")
-- retval = ograpi.OGR_DS_SyncToDisk(cogr_ds)
-- if retval != OGRERR_NONE:
-- raise RuntimeError("Failed to sync to disk")
--
--
--cdef class Iterator:
--
-- """Provides iterated access to feature data.
-- """
--
-- # Reference to its Collection
-- cdef collection
-- cdef encoding
-- cdef int next_index
-- cdef stop
-- cdef start
-- cdef step
-- cdef fastindex
-- cdef stepsign
--
-- def __init__(self, collection,
-- start=None, stop=None, step=None, bbox=None, mask=None):
-- if collection.session is None:
-- raise ValueError("I/O operation on closed collection")
-- self.collection = collection
-- cdef Session session
-- cdef void *cogr_geometry
-- session = self.collection.session
-- cdef void *cogr_layer = session.cogr_layer
-- if cogr_layer == NULL:
-- raise ValueError("Null layer")
-- ograpi.OGR_L_ResetReading(cogr_layer)
--
-- if bbox and mask:
-- raise ValueError("mask and bbox can not be set together")
--
-- if bbox:
-- ograpi.OGR_L_SetSpatialFilterRect(
-- cogr_layer, bbox[0], bbox[1], bbox[2], bbox[3])
-- elif mask:
-- cogr_geometry = OGRGeomBuilder().build(mask)
-- ograpi.OGR_L_SetSpatialFilter(cogr_layer, cogr_geometry)
-- ograpi.OGR_G_DestroyGeometry(cogr_geometry)
--
-- else:
-- ograpi.OGR_L_SetSpatialFilter(
-- cogr_layer, NULL)
-- self.encoding = session.get_internalencoding()
--
-- self.fastindex = ograpi.OGR_L_TestCapability(
-- session.cogr_layer, OLC_FASTSETNEXTBYINDEX)
--
-- ftcount = ograpi.OGR_L_GetFeatureCount(session.cogr_layer, 0)
-- if ftcount == -1 and ((start is not None and start < 0) or
-- (stop is not None and stop < 0)):
-- raise IndexError(
-- "collection's dataset does not support negative slice indexes")
--
-- if stop is not None and stop < 0:
-- stop += ftcount
--
-- if start is None:
-- start = 0
-- if start is not None and start < 0:
-- start += ftcount
--
-- # step size
-- if step is None:
-- step = 1
-- if step == 0:
-- raise ValueError("slice step cannot be zero")
-- if step < 0 and not self.fastindex:
-- warnings.warn("Layer does not support" \
-- "OLCFastSetNextByIndex, negative step size may" \
-- " be slow", RuntimeWarning)
-- self.stepsign = int(math.copysign(1, step))
-- self.stop = stop
-- self.start = start
-- self.step = step
--
-- self.next_index = start
-- log.debug("Index: %d", self.next_index)
-- ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
--
--
-- def __iter__(self):
-- return self
--
--
-- def _next(self):
-- """Internal method to set read cursor to next item"""
--
-- cdef Session session
-- session = self.collection.session
--
-- # Check if next_index is valid
-- if self.next_index < 0:
-- raise StopIteration
--
-- if self.stepsign == 1:
-- if self.next_index < self.start or (self.stop is not None and self.next_index >= self.stop):
-- raise StopIteration
-- else:
-- if self.next_index > self.start or (self.stop is not None and self.next_index <= self.stop):
-- raise StopIteration
--
--
-- # Set read cursor to next_item position
-- if self.step > 1 and self.fastindex:
-- ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
--
-- elif self.step > 1 and not self.fastindex and not self.next_index == self.start:
-- for _ in range(self.step - 1):
-- # TODO rbuffat add test -> OGR_L_GetNextFeature increments cursor by 1, therefore self.step - 1 as one increment was performed when feature is read
-- cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-- if cogr_feature == NULL:
-- raise StopIteration
-- elif self.step > 1 and not self.fastindex and self.next_index == self.start:
-- ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
--
-- elif self.step == 0:
-- # ograpi.OGR_L_GetNextFeature increments read cursor by one
-- pass
-- elif self.step < 0:
-- ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
--
-- # set the next index
-- self.next_index += self.step
--
--
-- def __next__(self):
-- cdef void * cogr_feature
-- cdef Session session
-- session = self.collection.session
--
-- #Update read cursor
-- self._next()
--
-- # Get the next feature.
-- cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-- if cogr_feature == NULL:
-- raise StopIteration
--
-- feature = FeatureBuilder().build(
-- cogr_feature,
-- bbox=False,
-- encoding=self.encoding,
-- driver=self.collection.driver
-- )
-- _deleteOgrFeature(cogr_feature)
-- return feature
--
--
--cdef class ItemsIterator(Iterator):
--
-- def __next__(self):
--
-- cdef long fid
-- cdef void * cogr_feature
-- cdef Session session
-- session = self.collection.session
--
-- #Update read cursor
-- self._next()
--
-- # Get the next feature.
-- cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-- if cogr_feature == NULL:
-- raise StopIteration
--
--
-- fid = ograpi.OGR_F_GetFID(cogr_feature)
-- feature = FeatureBuilder().build(
-- cogr_feature,
-- bbox=False,
-- encoding=self.encoding,
-- driver=self.collection.driver
-- )
-- _deleteOgrFeature(cogr_feature)
--
-- return fid, feature
--
--
--cdef class KeysIterator(Iterator):
--
-- def __next__(self):
-- cdef long fid
-- cdef void * cogr_feature
-- cdef Session session
-- session = self.collection.session
--
-- #Update read cursor
-- self._next()
--
-- # Get the next feature.
-- cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-- if cogr_feature == NULL:
-- raise StopIteration
--
-- fid = ograpi.OGR_F_GetFID(cogr_feature)
-- _deleteOgrFeature(cogr_feature)
--
-- return fid
--
--
--def _listlayers(path):
--
-- """Provides a list of the layers in an OGR data source.
-- """
--
-- cdef void *cogr_ds
-- cdef void *cogr_layer
-- cdef char *path_c
-- cdef char *name_c
--
-- # Open OGR data source.
-- try:
-- path_b = path.encode('utf-8')
-- except UnicodeError:
-- path_b = path
-- path_c = path_b
-- with cpl_errs:
-- cogr_ds = ograpi.OGROpen(path_c, 0, NULL)
-- if cogr_ds == NULL:
-- raise ValueError("No data available at path '%s'" % path)
--
-- # Loop over the layers to get their names.
-- layer_count = ograpi.OGR_DS_GetLayerCount(cogr_ds)
-- layer_names = []
-- for i in range(layer_count):
-- cogr_layer = ograpi.OGR_DS_GetLayer(cogr_ds, i)
-- name_c = ograpi.OGR_L_GetName(cogr_layer)
-- name_b = name_c
-- layer_names.append(name_b.decode('utf-8'))
--
-- # Close up data source.
-- if cogr_ds is not NULL:
-- ograpi.OGR_DS_Destroy(cogr_ds)
-- cogr_ds = NULL
--
-- return layer_names
--
--def buffer_to_virtual_file(bytesbuf):
-- """Maps a bytes buffer to a virtual file.
-- """
-- vsi_filename = os.path.join('/vsimem', uuid.uuid4().hex)
-- vsi_cfilename = vsi_filename if not isinstance(vsi_filename, string_types) else vsi_filename.encode('utf-8')
--
-- vsi_handle = ograpi.VSIFileFromMemBuffer(vsi_cfilename, bytesbuf, len(bytesbuf), 0)
-- if vsi_handle == NULL:
-- raise OSError('failed to map buffer to file')
-- if ograpi.VSIFCloseL(vsi_handle) != 0:
-- raise OSError('failed to close mapped file handle')
--
-- return vsi_filename
--
--def remove_virtual_file(vsi_filename):
-- vsi_cfilename = vsi_filename if not isinstance(vsi_filename, string_types) else vsi_filename.encode('utf-8')
-- return ograpi.VSIUnlink(vsi_cfilename)
--
--
---- /dev/null
-+++ b/fiona/ogrext1.pyx
-@@ -0,0 +1,1231 @@
-+# These are extension functions and classes using the OGR C API.
-+
-+import datetime
-+import json
-+import locale
-+import logging
-+import os
-+import sys
-+import warnings
-+import math
-+import uuid
-+
-+from six import integer_types, string_types, text_type
-+
-+from fiona cimport ograpi
-+from fiona._geometry cimport GeomBuilder, OGRGeomBuilder
-+from fiona._err import cpl_errs
-+from fiona._geometry import GEOMETRY_TYPES
-+from fiona.errors import DriverError, SchemaError, CRSError, FionaValueError
-+from fiona.odict import OrderedDict
-+from fiona.rfc3339 import parse_date, parse_datetime, parse_time
-+from fiona.rfc3339 import FionaDateType, FionaDateTimeType, FionaTimeType
-+
-+
-+log = logging.getLogger("Fiona")
-+class NullHandler(logging.Handler):
-+ def emit(self, record):
-+ pass
-+log.addHandler(NullHandler())
-+
-+
-+# Mapping of OGR integer field types to Fiona field type names.
-+#
-+# Lists are currently unsupported in this version, but might be done as
-+# arrays in a future version.
-+
-+FIELD_TYPES = [
-+ 'int', # OFTInteger, Simple 32bit integer
-+ None, # OFTIntegerList, List of 32bit integers
-+ 'float', # OFTReal, Double Precision floating point
-+ None, # OFTRealList, List of doubles
-+ 'str', # OFTString, String of ASCII chars
-+ None, # OFTStringList, Array of strings
-+ None, # OFTWideString, deprecated
-+ None, # OFTWideStringList, deprecated
-+ None, # OFTBinary, Raw Binary data
-+ 'date', # OFTDate, Date
-+ 'time', # OFTTime, Time
-+ 'datetime', # OFTDateTime, Date and Time
-+ 'int', # OFTInteger64, Single 64bit integer #Not supported
-+ None, # OFTInteger64List, List of 64bit integers #Not supported
-+ ]
-+
-+# Mapping of Fiona field type names to Python types.
-+FIELD_TYPES_MAP = {
-+ 'int': int,
-+ 'float': float,
-+ 'str': text_type,
-+ 'date': FionaDateType,
-+ 'time': FionaTimeType,
-+ 'datetime': FionaDateTimeType
-+ }
-+
-+# OGR Layer capability
-+OLC_RANDOMREAD = b"RandomRead"
-+OLC_SEQUENTIALWRITE = b"SequentialWrite"
-+OLC_RANDOMWRITE = b"RandomWrite"
-+OLC_FASTSPATIALFILTER = b"FastSpatialFilter"
-+OLC_FASTFEATURECOUNT = b"FastFeatureCount"
-+OLC_FASTGETEXTENT = b"FastGetExtent"
-+OLC_FASTSETNEXTBYINDEX = b"FastSetNextByIndex"
-+OLC_CREATEFIELD = b"CreateField"
-+OLC_CREATEGEOMFIELD = b"CreateGeomField"
-+OLC_DELETEFIELD = b"DeleteField"
-+OLC_REORDERFIELDS = b"ReorderFields"
-+OLC_ALTERFIELDDEFN = b"AlterFieldDefn"
-+OLC_DELETEFEATURE = b"DeleteFeature"
-+OLC_STRINGSASUTF8 = b"StringsAsUTF8"
-+OLC_TRANSACTIONS = b"Transactions"
-+
-+# OGR integer error types.
-+
-+OGRERR_NONE = 0
-+OGRERR_NOT_ENOUGH_DATA = 1 # not enough data to deserialize */
-+OGRERR_NOT_ENOUGH_MEMORY = 2
-+OGRERR_UNSUPPORTED_GEOMETRY_TYPE = 3
-+OGRERR_UNSUPPORTED_OPERATION = 4
-+OGRERR_CORRUPT_DATA = 5
-+OGRERR_FAILURE = 6
-+OGRERR_UNSUPPORTED_SRS = 7
-+OGRERR_INVALID_HANDLE = 8
-+
-+
-+def _explode(coords):
-+ """Explode a GeoJSON geometry's coordinates object and yield
-+ coordinate tuples. As long as the input is conforming, the type of
-+ the geometry doesn't matter."""
-+ for e in coords:
-+ if isinstance(e, (float, int)):
-+ yield coords
-+ break
-+ else:
-+ for f in _explode(e):
-+ yield f
-+
-+
-+def _bounds(geometry):
-+ """Bounding box of a GeoJSON geometry"""
-+ try:
-+ xyz = tuple(zip(*list(_explode(geometry['coordinates']))))
-+ return min(xyz[0]), min(xyz[1]), max(xyz[0]), max(xyz[1])
-+ except (KeyError, TypeError):
-+ return None
-+
-+def calc_gdal_version_num(maj, min, rev):
-+ """Calculates the internal gdal version number based on major, minor and revision"""
-+ return int(maj * 1000000 + min * 10000 + rev*100)
-+
-+def get_gdal_version_num():
-+ """Return current internal version number of gdal"""
-+ return int(ograpi.GDALVersionInfo("VERSION_NUM"))
-+
-+def get_gdal_release_name():
-+ """Return release name of gdal"""
-+ return ograpi.GDALVersionInfo("RELEASE_NAME")
-+
-+
-+# Feature extension classes and functions follow.
-+
-+cdef class FeatureBuilder:
-+ """Build Fiona features from OGR feature pointers.
-+
-+ No OGR objects are allocated by this function and the feature
-+ argument is not destroyed.
-+ """
-+
-+ cdef build(self, void *feature, encoding='utf-8', bbox=False, driver=None):
-+ # The only method anyone ever needs to call
-+ cdef void *fdefn
-+ cdef int i
-+ cdef int y = 0
-+ cdef int m = 0
-+ cdef int d = 0
-+ cdef int hh = 0
-+ cdef int mm = 0
-+ cdef int ss = 0
-+ cdef int tz = 0
-+ cdef int retval
-+ cdef char *key_c
-+ props = OrderedDict()
-+ for i in range(ograpi.OGR_F_GetFieldCount(feature)):
-+ fdefn = ograpi.OGR_F_GetFieldDefnRef(feature, i)
-+ if fdefn == NULL:
-+ raise ValueError("Null feature definition")
-+ key_c = ograpi.OGR_Fld_GetNameRef(fdefn)
-+ if key_c == NULL:
-+ raise ValueError("Null field name reference")
-+ key_b = key_c
-+ key = key_b.decode(encoding)
-+ fieldtypename = FIELD_TYPES[ograpi.OGR_Fld_GetType(fdefn)]
-+ if not fieldtypename:
-+ log.warn(
-+ "Skipping field %s: invalid type %s",
-+ key,
-+ ograpi.OGR_Fld_GetType(fdefn))
-+ continue
-+
-+ # TODO: other types
-+ fieldtype = FIELD_TYPES_MAP[fieldtypename]
-+ if not ograpi.OGR_F_IsFieldSet(feature, i):
-+ props[key] = None
-+ elif fieldtype is int:
-+ props[key] = ograpi.OGR_F_GetFieldAsInteger(feature, i)
-+ elif fieldtype is float:
-+ props[key] = ograpi.OGR_F_GetFieldAsDouble(feature, i)
-+
-+ elif fieldtype is text_type:
-+ try:
-+ val = ograpi.OGR_F_GetFieldAsString(feature, i)
-+ val = val.decode(encoding)
-+ except UnicodeDecodeError:
-+ log.warn(
-+ "Failed to decode %s using %s codec", val, encoding)
-+
-+ # Does the text contain a JSON object? Let's check.
-+ # Let's check as cheaply as we can.
-+ if driver == 'GeoJSON' and val.startswith('{'):
-+ try:
-+ val = json.loads(val)
-+ except ValueError as err:
-+ log.warn(str(err))
-+
-+ # Now add to the properties object.
-+ props[key] = val
-+
-+ elif fieldtype in (FionaDateType, FionaTimeType, FionaDateTimeType):
-+ retval = ograpi.OGR_F_GetFieldAsDateTime(
-+ feature, i, &y, &m, &d, &hh, &mm, &ss, &tz)
-+ if fieldtype is FionaDateType:
-+ props[key] = datetime.date(y, m, d).isoformat()
-+ elif fieldtype is FionaTimeType:
-+ props[key] = datetime.time(hh, mm, ss).isoformat()
-+ else:
-+ props[key] = datetime.datetime(
-+ y, m, d, hh, mm, ss).isoformat()
-+ else:
-+ log.debug("%s: None, fieldtype: %r, %r" % (key, fieldtype, fieldtype in string_types))
-+ props[key] = None
-+
-+ cdef void *cogr_geometry = ograpi.OGR_F_GetGeometryRef(feature)
-+ if cogr_geometry is not NULL:
-+ geom = GeomBuilder().build(cogr_geometry)
-+ else:
-+ geom = None
-+ return {
-+ 'type': 'Feature',
-+ 'id': str(ograpi.OGR_F_GetFID(feature)),
-+ 'geometry': geom,
-+ 'properties': props }
-+
-+
-+cdef class OGRFeatureBuilder:
-+
-+ """Builds an OGR Feature from a Fiona feature mapping.
-+
-+ Allocates one OGR Feature which should be destroyed by the caller.
-+ Borrows a layer definition from the collection.
-+ """
-+
-+ cdef void * build(self, feature, collection) except NULL:
-+ cdef void *cogr_geometry = NULL
-+ cdef char *string_c
-+ cdef WritingSession session
-+ session = collection.session
-+ cdef void *cogr_layer = session.cogr_layer
-+ if cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cdef void *cogr_featuredefn = ograpi.OGR_L_GetLayerDefn(cogr_layer)
-+ if cogr_featuredefn == NULL:
-+ raise ValueError("Null feature definition")
-+ cdef void *cogr_feature = ograpi.OGR_F_Create(cogr_featuredefn)
-+ if cogr_feature == NULL:
-+ raise ValueError("Null feature")
-+
-+ if feature['geometry'] is not None:
-+ cogr_geometry = OGRGeomBuilder().build(
-+ feature['geometry'])
-+ ograpi.OGR_F_SetGeometryDirectly(cogr_feature, cogr_geometry)
-+
-+ # OGR_F_SetFieldString takes UTF-8 encoded strings ('bytes' in
-+ # Python 3).
-+ encoding = session.get_internalencoding()
-+
-+ for key, value in feature['properties'].items():
-+ log.debug(
-+ "Looking up %s in %s", key, repr(session._schema_mapping))
-+ ogr_key = session._schema_mapping[key]
-+ schema_type = collection.schema['properties'][key]
-+ try:
-+ key_bytes = ogr_key.encode(encoding)
-+ except UnicodeDecodeError:
-+ log.warn("Failed to encode %s using %s codec", key, encoding)
-+ key_bytes = ogr_key
-+ key_c = key_bytes
-+ i = ograpi.OGR_F_GetFieldIndex(cogr_feature, key_c)
-+ if i < 0:
-+ continue
-+
-+ # Special case: serialize dicts to assist OGR.
-+ if isinstance(value, dict):
-+ value = json.dumps(value)
-+
-+ # Continue over the standard OGR types.
-+ if isinstance(value, integer_types):
-+ ograpi.OGR_F_SetFieldInteger(cogr_feature, i, value)
-+ elif isinstance(value, float):
-+ ograpi.OGR_F_SetFieldDouble(cogr_feature, i, value)
-+ elif (isinstance(value, string_types)
-+ and schema_type in ['date', 'time', 'datetime']):
-+ if schema_type == 'date':
-+ y, m, d, hh, mm, ss, ff = parse_date(value)
-+ elif schema_type == 'time':
-+ y, m, d, hh, mm, ss, ff = parse_time(value)
-+ else:
-+ y, m, d, hh, mm, ss, ff = parse_datetime(value)
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, y, m, d, hh, mm, ss, 0)
-+ elif (isinstance(value, datetime.date)
-+ and schema_type == 'date'):
-+ y, m, d = value.year, value.month, value.day
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, y, m, d, 0, 0, 0, 0)
-+ elif (isinstance(value, datetime.datetime)
-+ and schema_type == 'datetime'):
-+ y, m, d = value.year, value.month, value.day
-+ hh, mm, ss = value.hour, value.minute, value.second
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, y, m, d, hh, mm, ss, 0)
-+ elif (isinstance(value, datetime.time)
-+ and schema_type == 'time'):
-+ hh, mm, ss = value.hour, value.minute, value.second
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, 0, 0, 0, hh, mm, ss, 0)
-+ elif isinstance(value, string_types):
-+ try:
-+ value_bytes = value.encode(encoding)
-+ except UnicodeDecodeError:
-+ log.warn(
-+ "Failed to encode %s using %s codec", value, encoding)
-+ value_bytes = value
-+ string_c = value_bytes
-+ ograpi.OGR_F_SetFieldString(cogr_feature, i, string_c)
-+ elif value is None:
-+ pass # keep field unset/null
-+ else:
-+ raise ValueError("Invalid field type %s" % type(value))
-+ log.debug("Set field %s: %s" % (key, value))
-+ return cogr_feature
-+
-+
-+cdef _deleteOgrFeature(void *cogr_feature):
-+ """Delete an OGR feature"""
-+ if cogr_feature is not NULL:
-+ ograpi.OGR_F_Destroy(cogr_feature)
-+ cogr_feature = NULL
-+
-+
-+def featureRT(feature, collection):
-+ # For testing purposes only, leaks the JSON data
-+ cdef void *cogr_feature = OGRFeatureBuilder().build(feature, collection)
-+ cdef void *cogr_geometry = ograpi.OGR_F_GetGeometryRef(cogr_feature)
-+ if cogr_geometry == NULL:
-+ raise ValueError("Null geometry")
-+ log.debug("Geometry: %s" % ograpi.OGR_G_ExportToJson(cogr_geometry))
-+ encoding = collection.encoding or 'utf-8'
-+ result = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=encoding,
-+ driver=collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+ return result
-+
-+
-+# Collection-related extension classes and functions
-+
-+cdef class Session:
-+
-+ cdef void *cogr_ds
-+ cdef void *cogr_layer
-+ cdef object _fileencoding
-+ cdef object _encoding
-+ cdef object collection
-+
-+ def __cinit__(self):
-+ self.cogr_ds = NULL
-+ self.cogr_layer = NULL
-+ self._fileencoding = None
-+ self._encoding = None
-+
-+ def __dealloc__(self):
-+ self.stop()
-+
-+ def start(self, collection):
-+ cdef const char *path_c = NULL
-+ cdef const char *name_c = NULL
-+ cdef void *drv = NULL
-+ cdef void *ds = NULL
-+
-+ if collection.path == '-':
-+ path = '/vsistdin/'
-+ else:
-+ path = collection.path
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ # Presume already a UTF-8 encoded string
-+ path_b = path
-+ path_c = path_b
-+
-+ with cpl_errs:
-+ drivers = []
-+ if collection._driver:
-+ drivers = [collection._driver]
-+ elif collection.enabled_drivers:
-+ drivers = collection.enabled_drivers
-+ if drivers:
-+ for name in drivers:
-+ name_b = name.encode()
-+ name_c = name_b
-+ log.debug("Trying driver: %s", name)
-+ drv = ograpi.OGRGetDriverByName(name_c)
-+ if drv != NULL:
-+ ds = ograpi.OGR_Dr_Open(drv, path_c, 0)
-+ if ds != NULL:
-+ self.cogr_ds = ds
-+ collection._driver = name
-+ break
-+ else:
-+ self.cogr_ds = ograpi.OGROpen(path_c, 0, NULL)
-+
-+ if self.cogr_ds == NULL:
-+ raise FionaValueError(
-+ "No dataset found at path '%s' using drivers: %s" % (
-+ collection.path,
-+ drivers or '*'))
-+
-+ if isinstance(collection.name, string_types):
-+ name_b = collection.name.encode('utf-8')
-+ name_c = name_b
-+ self.cogr_layer = ograpi.OGR_DS_GetLayerByName(
-+ self.cogr_ds, name_c)
-+ elif isinstance(collection.name, int):
-+ self.cogr_layer = ograpi.OGR_DS_GetLayer(
-+ self.cogr_ds, collection.name)
-+ name_c = ograpi.OGR_L_GetName(self.cogr_layer)
-+ name_b = name_c
-+ collection.name = name_b.decode('utf-8')
-+
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer: " + repr(collection.name))
-+
-+ self.collection = collection
-+
-+ userencoding = self.collection.encoding
-+ if userencoding:
-+ ograpi.CPLSetThreadLocalConfigOption('SHAPE_ENCODING', '')
-+ self._fileencoding = userencoding.upper()
-+ else:
-+ self._fileencoding = (
-+ ograpi.OGR_L_TestCapability(
-+ self.cogr_layer, OLC_STRINGSASUTF8) and
-+ 'utf-8') or (
-+ self.get_driver() == "ESRI Shapefile" and
-+ 'ISO-8859-1') or locale.getpreferredencoding().upper()
-+
-+ def stop(self):
-+ self.cogr_layer = NULL
-+ if self.cogr_ds is not NULL:
-+ ograpi.OGR_DS_Destroy(self.cogr_ds)
-+ self.cogr_ds = NULL
-+
-+ def get_fileencoding(self):
-+ return self._fileencoding
-+
-+ def get_internalencoding(self):
-+ if not self._encoding:
-+ fileencoding = self.get_fileencoding()
-+ self._encoding = (
-+ ograpi.OGR_L_TestCapability(
-+ self.cogr_layer, OLC_STRINGSASUTF8) and
-+ 'utf-8') or fileencoding
-+ return self._encoding
-+
-+ def get_length(self):
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ return ograpi.OGR_L_GetFeatureCount(self.cogr_layer, 0)
-+
-+ def get_driver(self):
-+ cdef void *cogr_driver = ograpi.OGR_DS_GetDriver(self.cogr_ds)
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+ cdef char *name = ograpi.OGR_Dr_GetName(cogr_driver)
-+ driver_name = name
-+ return driver_name.decode()
-+
-+ def get_schema(self):
-+ cdef int i
-+ cdef int n
-+ cdef void *cogr_featuredefn
-+ cdef void *cogr_fielddefn
-+ cdef char *key_c
-+ props = []
-+
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+
-+ cogr_featuredefn = ograpi.OGR_L_GetLayerDefn(self.cogr_layer)
-+ if cogr_featuredefn == NULL:
-+ raise ValueError("Null feature definition")
-+ n = ograpi.OGR_FD_GetFieldCount(cogr_featuredefn)
-+ for i from 0 <= i < n:
-+ cogr_fielddefn = ograpi.OGR_FD_GetFieldDefn(cogr_featuredefn, i)
-+ if cogr_fielddefn == NULL:
-+ raise ValueError("Null field definition")
-+ key_c = ograpi.OGR_Fld_GetNameRef(cogr_fielddefn)
-+ key_b = key_c
-+ if not bool(key_b):
-+ raise ValueError("Invalid field name ref: %s" % key)
-+ key = key_b.decode(self.get_internalencoding())
-+ fieldtypename = FIELD_TYPES[ograpi.OGR_Fld_GetType(cogr_fielddefn)]
-+ if not fieldtypename:
-+ log.warn(
-+ "Skipping field %s: invalid type %s",
-+ key,
-+ ograpi.OGR_Fld_GetType(cogr_fielddefn))
-+ continue
-+ val = fieldtypename
-+ if fieldtypename == 'float':
-+ fmt = ""
-+ width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-+ if width: # and width != 24:
-+ fmt = ":%d" % width
-+ precision = ograpi.OGR_Fld_GetPrecision(cogr_fielddefn)
-+ if precision: # and precision != 15:
-+ fmt += ".%d" % precision
-+ val = "float" + fmt
-+ elif fieldtypename == 'int':
-+ fmt = ""
-+ width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-+ if width: # and width != 11:
-+ fmt = ":%d" % width
-+ val = fieldtypename + fmt
-+ elif fieldtypename == 'str':
-+ fmt = ""
-+ width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-+ if width: # and width != 80:
-+ fmt = ":%d" % width
-+ val = fieldtypename + fmt
-+
-+ props.append((key, val))
-+
-+ cdef unsigned int geom_type = ograpi.OGR_FD_GetGeomType(
-+ cogr_featuredefn)
-+ return {
-+ 'properties': OrderedDict(props),
-+ 'geometry': GEOMETRY_TYPES[geom_type]}
-+
-+ def get_crs(self):
-+ cdef char *proj_c = NULL
-+ cdef char *auth_key = NULL
-+ cdef char *auth_val = NULL
-+ cdef void *cogr_crs = NULL
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cogr_crs = ograpi.OGR_L_GetSpatialRef(self.cogr_layer)
-+ crs = {}
-+ if cogr_crs is not NULL:
-+ log.debug("Got coordinate system")
-+
-+ retval = ograpi.OSRAutoIdentifyEPSG(cogr_crs)
-+ if retval > 0:
-+ log.info("Failed to auto identify EPSG: %d", retval)
-+
-+ auth_key = ograpi.OSRGetAuthorityName(cogr_crs, NULL)
-+ auth_val = ograpi.OSRGetAuthorityCode(cogr_crs, NULL)
-+
-+ if auth_key != NULL and auth_val != NULL:
-+ key_b = auth_key
-+ key = key_b.decode('utf-8')
-+ if key == 'EPSG':
-+ val_b = auth_val
-+ val = val_b.decode('utf-8')
-+ crs['init'] = "epsg:" + val
-+ else:
-+ ograpi.OSRExportToProj4(cogr_crs, &proj_c)
-+ if proj_c == NULL:
-+ raise ValueError("Null projection")
-+ proj_b = proj_c
-+ log.debug("Params: %s", proj_b)
-+ value = proj_b.decode()
-+ value = value.strip()
-+ for param in value.split():
-+ kv = param.split("=")
-+ if len(kv) == 2:
-+ k, v = kv
-+ try:
-+ v = float(v)
-+ if v % 1 == 0:
-+ v = int(v)
-+ except ValueError:
-+ # Leave v as a string
-+ pass
-+ elif len(kv) == 1:
-+ k, v = kv[0], True
-+ else:
-+ raise ValueError("Unexpected proj parameter %s" % param)
-+ k = k.lstrip("+")
-+ crs[k] = v
-+
-+ ograpi.CPLFree(proj_c)
-+ else:
-+ log.debug("Projection not found (cogr_crs was NULL)")
-+ return crs
-+
-+ def get_crs_wkt(self):
-+ cdef char *proj_c = NULL
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cogr_crs = ograpi.OGR_L_GetSpatialRef(self.cogr_layer)
-+ crs_wkt = ""
-+ if cogr_crs is not NULL:
-+ log.debug("Got coordinate system")
-+ ograpi.OSRExportToWkt(cogr_crs, &proj_c)
-+ if proj_c == NULL:
-+ raise ValueError("Null projection")
-+ proj_b = proj_c
-+ crs_wkt = proj_b.decode('utf-8')
-+ ograpi.CPLFree(proj_c)
-+ else:
-+ log.debug("Projection not found (cogr_crs was NULL)")
-+ return crs_wkt
-+
-+ def get_extent(self):
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cdef ograpi.OGREnvelope extent
-+ result = ograpi.OGR_L_GetExtent(self.cogr_layer, &extent, 1)
-+ return (extent.MinX, extent.MinY, extent.MaxX, extent.MaxY)
-+
-+ def has_feature(self, fid):
-+ """Provides access to feature data by FID.
-+
-+ Supports Collection.__contains__().
-+ """
-+ cdef void * cogr_feature
-+ fid = int(fid)
-+ cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, fid)
-+ if cogr_feature != NULL:
-+ _deleteOgrFeature(cogr_feature)
-+ return True
-+ else:
-+ return False
-+
-+ def get_feature(self, fid):
-+ """Provides access to feature data by FID.
-+
-+ Supports Collection.__contains__().
-+ """
-+ cdef void * cogr_feature
-+ fid = int(fid)
-+ cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, fid)
-+ if cogr_feature != NULL:
-+ _deleteOgrFeature(cogr_feature)
-+ return True
-+ else:
-+ return False
-+
-+
-+ def __getitem__(self, item):
-+ cdef void * cogr_feature
-+ if isinstance(item, slice):
-+ itr = Iterator(self.collection, item.start, item.stop, item.step)
-+ log.debug("Slice: %r", item)
-+ return list(itr)
-+ elif isinstance(item, int):
-+ index = item
-+ # from the back
-+ if index < 0:
-+ ftcount = ograpi.OGR_L_GetFeatureCount(self.cogr_layer, 0)
-+ if ftcount == -1:
-+ raise IndexError(
-+ "collection's dataset does not support negative indexes")
-+ index += ftcount
-+ cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, index)
-+ if cogr_feature == NULL:
-+ return None
-+ feature = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=self.get_internalencoding(),
-+ driver=self.collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+ return feature
-+
-+
-+ def isactive(self):
-+ if self.cogr_layer != NULL and self.cogr_ds != NULL:
-+ return 1
-+ else:
-+ return 0
-+
-+
-+cdef class WritingSession(Session):
-+
-+ cdef object _schema_mapping
-+
-+ def start(self, collection):
-+ cdef void *cogr_fielddefn
-+ cdef void *cogr_driver
-+ cdef void *cogr_ds
-+ cdef void *cogr_layer
-+ cdef void *cogr_srs = NULL
-+ cdef char **options = NULL
-+ self.collection = collection
-+ cdef char *path_c
-+ cdef char *driver_c
-+ cdef char *name_c
-+ cdef char *proj_c
-+ cdef char *fileencoding_c
-+ path = collection.path
-+
-+ if collection.mode == 'a':
-+ if os.path.exists(path):
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ path_b = path
-+ path_c = path_b
-+ with cpl_errs:
-+ self.cogr_ds = ograpi.OGROpen(path_c, 1, NULL)
-+ if self.cogr_ds == NULL:
-+ raise RuntimeError("Failed to open %s" % path)
-+ cogr_driver = ograpi.OGR_DS_GetDriver(self.cogr_ds)
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+
-+ if isinstance(collection.name, string_types):
-+ name_b = collection.name.encode()
-+ name_c = name_b
-+ self.cogr_layer = ograpi.OGR_DS_GetLayerByName(
-+ self.cogr_ds, name_c)
-+ elif isinstance(collection.name, int):
-+ self.cogr_layer = ograpi.OGR_DS_GetLayer(
-+ self.cogr_ds, collection.name)
-+
-+ if self.cogr_layer == NULL:
-+ raise RuntimeError(
-+ "Failed to get layer %s" % collection.name)
-+ else:
-+ raise OSError("No such file or directory %s" % path)
-+
-+ userencoding = self.collection.encoding
-+ self._fileencoding = (userencoding or (
-+ ograpi.OGR_L_TestCapability(self.cogr_layer, OLC_STRINGSASUTF8) and
-+ 'utf-8') or (
-+ self.get_driver() == "ESRI Shapefile" and
-+ 'ISO-8859-1') or locale.getpreferredencoding()).upper()
-+
-+ elif collection.mode == 'w':
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ path_b = path
-+ path_c = path_b
-+ driver_b = collection.driver.encode()
-+ driver_c = driver_b
-+
-+ cogr_driver = ograpi.OGRGetDriverByName(driver_c)
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+
-+ if not os.path.exists(path):
-+ cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-+ cogr_driver, path_c, NULL)
-+
-+ else:
-+ with cpl_errs:
-+ cogr_ds = ograpi.OGROpen(path_c, 1, NULL)
-+ if cogr_ds == NULL:
-+ cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-+ cogr_driver, path_c, NULL)
-+
-+ elif collection.name is None:
-+ ograpi.OGR_DS_Destroy(cogr_ds)
-+ cogr_ds == NULL
-+ log.debug("Deleted pre-existing data at %s", path)
-+
-+ cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-+ cogr_driver, path_c, NULL)
-+
-+ else:
-+ pass
-+
-+ if cogr_ds == NULL:
-+ raise RuntimeError("Failed to open %s" % path)
-+ else:
-+ self.cogr_ds = cogr_ds
-+
-+ # Set the spatial reference system from the crs given to the
-+ # collection constructor. We by-pass the crs_wkt and crs
-+ # properties because they aren't accessible until the layer
-+ # is constructed (later).
-+ col_crs = collection._crs_wkt or collection._crs
-+ if col_crs:
-+ cogr_srs = ograpi.OSRNewSpatialReference(NULL)
-+ if cogr_srs == NULL:
-+ raise ValueError("NULL spatial reference")
-+ # First, check for CRS strings like "EPSG:3857".
-+ if isinstance(col_crs, string_types):
-+ proj_b = col_crs.encode('utf-8')
-+ proj_c = proj_b
-+ ograpi.OSRSetFromUserInput(cogr_srs, proj_c)
-+ elif isinstance(col_crs, dict):
-+ # EPSG is a special case.
-+ init = col_crs.get('init')
-+ if init:
-+ log.debug("Init: %s", init)
-+ auth, val = init.split(':')
-+ if auth.upper() == 'EPSG':
-+ log.debug("Setting EPSG: %s", val)
-+ ograpi.OSRImportFromEPSG(cogr_srs, int(val))
-+ else:
-+ params = []
-+ col_crs['wktext'] = True
-+ for k, v in col_crs.items():
-+ if v is True or (k in ('no_defs', 'wktext') and v):
-+ params.append("+%s" % k)
-+ else:
-+ params.append("+%s=%s" % (k, v))
-+ proj = " ".join(params)
-+ log.debug("PROJ.4 to be imported: %r", proj)
-+ proj_b = proj.encode('utf-8')
-+ proj_c = proj_b
-+ ograpi.OSRImportFromProj4(cogr_srs, proj_c)
-+ else:
-+ raise ValueError("Invalid CRS")
-+
-+ # Fixup, export to WKT, and set the GDAL dataset's projection.
-+ ograpi.OSRFixup(cogr_srs)
-+
-+ # Figure out what encoding to use. The encoding parameter given
-+ # to the collection constructor takes highest precedence, then
-+ # 'iso-8859-1', then the system's default encoding as last resort.
-+ sysencoding = locale.getpreferredencoding()
-+ userencoding = collection.encoding
-+ self._fileencoding = (userencoding or (
-+ collection.driver == "ESRI Shapefile" and
-+ 'ISO-8859-1') or sysencoding).upper()
-+
-+ fileencoding = self.get_fileencoding()
-+ if fileencoding:
-+ fileencoding_b = fileencoding.encode()
-+ fileencoding_c = fileencoding_b
-+ options = ograpi.CSLSetNameValue(options, "ENCODING", fileencoding_c)
-+
-+ # Does the layer exist already? If so, we delete it.
-+ layer_count = ograpi.OGR_DS_GetLayerCount(self.cogr_ds)
-+ layer_names = []
-+ for i in range(layer_count):
-+ cogr_layer = ograpi.OGR_DS_GetLayer(cogr_ds, i)
-+ name_c = ograpi.OGR_L_GetName(cogr_layer)
-+ name_b = name_c
-+ layer_names.append(name_b.decode('utf-8'))
-+
-+ idx = -1
-+ if isinstance(collection.name, string_types):
-+ if collection.name in layer_names:
-+ idx = layer_names.index(collection.name)
-+ elif isinstance(collection.name, int):
-+ if collection.name >= 0 and collection.name < layer_count:
-+ idx = collection.name
-+ if idx >= 0:
-+ log.debug("Deleted pre-existing layer at %s", collection.name)
-+ ograpi.OGR_DS_DeleteLayer(self.cogr_ds, idx)
-+
-+ # Create the named layer in the datasource.
-+ name_b = collection.name.encode('utf-8')
-+ name_c = name_b
-+ self.cogr_layer = ograpi.OGR_DS_CreateLayer(
-+ self.cogr_ds,
-+ name_c,
-+ cogr_srs,
-+ <unsigned int>[k for k,v in GEOMETRY_TYPES.items() if
-+ v == collection.schema.get('geometry', 'Unknown')][0],
-+ options
-+ )
-+
-+ if cogr_srs != NULL:
-+ ograpi.OSRDestroySpatialReference(cogr_srs)
-+ if options != NULL:
-+ ograpi.CSLDestroy(options)
-+
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ log.debug("Created layer")
-+
-+ # Next, make a layer definition from the given schema properties,
-+ # which are an ordered dict since Fiona 1.0.1.
-+ for key, value in collection.schema['properties'].items():
-+ log.debug("Creating field: %s %s", key, value)
-+
-+ # Convert 'long' to 'int'. See
-+ # https://github.com/Toblerity/Fiona/issues/101.
-+ if value == 'long':
-+ value = 'int'
-+
-+ # Is there a field width/precision?
-+ width = precision = None
-+ if ':' in value:
-+ value, fmt = value.split(':')
-+ if '.' in fmt:
-+ width, precision = map(int, fmt.split('.'))
-+ else:
-+ width = int(fmt)
-+
-+ encoding = self.get_internalencoding()
-+ key_bytes = key.encode(encoding)
-+ cogr_fielddefn = ograpi.OGR_Fld_Create(
-+ key_bytes,
-+ FIELD_TYPES.index(value) )
-+ if cogr_fielddefn == NULL:
-+ raise ValueError("Null field definition")
-+ if width:
-+ ograpi.OGR_Fld_SetWidth(cogr_fielddefn, width)
-+ if precision:
-+ ograpi.OGR_Fld_SetPrecision(cogr_fielddefn, precision)
-+ ograpi.OGR_L_CreateField(self.cogr_layer, cogr_fielddefn, 1)
-+ ograpi.OGR_Fld_Destroy(cogr_fielddefn)
-+ log.debug("Created fields")
-+
-+ # Mapping of the Python collection schema to the munged
-+ # OGR schema.
-+ ogr_schema = self.get_schema()
-+ self._schema_mapping = dict(zip(
-+ collection.schema['properties'].keys(),
-+ ogr_schema['properties'].keys() ))
-+
-+ log.debug("Writing started")
-+
-+ def writerecs(self, records, collection):
-+ """Writes buffered records to OGR."""
-+ cdef void *cogr_driver
-+ cdef void *cogr_feature
-+
-+ cdef void *cogr_layer = self.cogr_layer
-+ if cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+
-+ schema_geom_type = collection.schema['geometry']
-+ cogr_driver = ograpi.OGR_DS_GetDriver(self.cogr_ds)
-+ if ograpi.OGR_Dr_GetName(cogr_driver) == b"GeoJSON":
-+ def validate_geometry_type(rec):
-+ return True
-+ elif ograpi.OGR_Dr_GetName(cogr_driver) == b"ESRI Shapefile" \
-+ and "Point" not in collection.schema['geometry']:
-+ schema_geom_type = collection.schema['geometry'].lstrip(
-+ "3D ").lstrip("Multi")
-+ def validate_geometry_type(rec):
-+ return rec['geometry'] is None or \
-+ rec['geometry']['type'].lstrip(
-+ "3D ").lstrip("Multi") == schema_geom_type
-+ else:
-+ schema_geom_type = collection.schema['geometry'].lstrip("3D ")
-+ def validate_geometry_type(rec):
-+ return rec['geometry'] is None or \
-+ rec['geometry']['type'].lstrip("3D ") == schema_geom_type
-+
-+ schema_props_keys = set(collection.schema['properties'].keys())
-+ for record in records:
-+ log.debug("Creating feature in layer: %s" % record)
-+ # Validate against collection's schema.
-+ if set(record['properties'].keys()) != schema_props_keys:
-+ raise ValueError(
-+ "Record does not match collection schema: %r != %r" % (
-+ record['properties'].keys(),
-+ list(schema_props_keys) ))
-+ if not validate_geometry_type(record):
-+ raise ValueError(
-+ "Record's geometry type does not match "
-+ "collection schema's geometry type: %r != %r" % (
-+ record['geometry']['type'],
-+ collection.schema['geometry'] ))
-+
-+ cogr_feature = OGRFeatureBuilder().build(record, collection)
-+ result = ograpi.OGR_L_CreateFeature(cogr_layer, cogr_feature)
-+ if result != OGRERR_NONE:
-+ raise RuntimeError("Failed to write record: %s" % record)
-+ _deleteOgrFeature(cogr_feature)
-+
-+ def sync(self, collection):
-+ """Syncs OGR to disk."""
-+ cdef void *cogr_ds = self.cogr_ds
-+ cdef void *cogr_layer = self.cogr_layer
-+ if cogr_ds == NULL:
-+ raise ValueError("Null data source")
-+ log.debug("Syncing OGR to disk")
-+ retval = ograpi.OGR_DS_SyncToDisk(cogr_ds)
-+ if retval != OGRERR_NONE:
-+ raise RuntimeError("Failed to sync to disk")
-+
-+
-+cdef class Iterator:
-+
-+ """Provides iterated access to feature data.
-+ """
-+
-+ # Reference to its Collection
-+ cdef collection
-+ cdef encoding
-+ cdef int next_index
-+ cdef stop
-+ cdef start
-+ cdef step
-+ cdef fastindex
-+ cdef stepsign
-+
-+ def __init__(self, collection,
-+ start=None, stop=None, step=None, bbox=None, mask=None):
-+ if collection.session is None:
-+ raise ValueError("I/O operation on closed collection")
-+ self.collection = collection
-+ cdef Session session
-+ cdef void *cogr_geometry
-+ session = self.collection.session
-+ cdef void *cogr_layer = session.cogr_layer
-+ if cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ ograpi.OGR_L_ResetReading(cogr_layer)
-+
-+ if bbox and mask:
-+ raise ValueError("mask and bbox can not be set together")
-+
-+ if bbox:
-+ ograpi.OGR_L_SetSpatialFilterRect(
-+ cogr_layer, bbox[0], bbox[1], bbox[2], bbox[3])
-+ elif mask:
-+ cogr_geometry = OGRGeomBuilder().build(mask)
-+ ograpi.OGR_L_SetSpatialFilter(cogr_layer, cogr_geometry)
-+ ograpi.OGR_G_DestroyGeometry(cogr_geometry)
-+
-+ else:
-+ ograpi.OGR_L_SetSpatialFilter(
-+ cogr_layer, NULL)
-+ self.encoding = session.get_internalencoding()
-+
-+ self.fastindex = ograpi.OGR_L_TestCapability(
-+ session.cogr_layer, OLC_FASTSETNEXTBYINDEX)
-+
-+ ftcount = ograpi.OGR_L_GetFeatureCount(session.cogr_layer, 0)
-+ if ftcount == -1 and ((start is not None and start < 0) or
-+ (stop is not None and stop < 0)):
-+ raise IndexError(
-+ "collection's dataset does not support negative slice indexes")
-+
-+ if stop is not None and stop < 0:
-+ stop += ftcount
-+
-+ if start is None:
-+ start = 0
-+ if start is not None and start < 0:
-+ start += ftcount
-+
-+ # step size
-+ if step is None:
-+ step = 1
-+ if step == 0:
-+ raise ValueError("slice step cannot be zero")
-+ if step < 0 and not self.fastindex:
-+ warnings.warn("Layer does not support" \
-+ "OLCFastSetNextByIndex, negative step size may" \
-+ " be slow", RuntimeWarning)
-+ self.stepsign = int(math.copysign(1, step))
-+ self.stop = stop
-+ self.start = start
-+ self.step = step
-+
-+ self.next_index = start
-+ log.debug("Index: %d", self.next_index)
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+
-+ def __iter__(self):
-+ return self
-+
-+
-+ def _next(self):
-+ """Internal method to set read cursor to next item"""
-+
-+ cdef Session session
-+ session = self.collection.session
-+
-+ # Check if next_index is valid
-+ if self.next_index < 0:
-+ raise StopIteration
-+
-+ if self.stepsign == 1:
-+ if self.next_index < self.start or (self.stop is not None and self.next_index >= self.stop):
-+ raise StopIteration
-+ else:
-+ if self.next_index > self.start or (self.stop is not None and self.next_index <= self.stop):
-+ raise StopIteration
-+
-+
-+ # Set read cursor to next_item position
-+ if self.step > 1 and self.fastindex:
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+ elif self.step > 1 and not self.fastindex and not self.next_index == self.start:
-+ for _ in range(self.step - 1):
-+ # TODO rbuffat add test -> OGR_L_GetNextFeature increments cursor by 1, therefore self.step - 1 as one increment was performed when feature is read
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+ elif self.step > 1 and not self.fastindex and self.next_index == self.start:
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+ elif self.step == 0:
-+ # ograpi.OGR_L_GetNextFeature increments read cursor by one
-+ pass
-+ elif self.step < 0:
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+ # set the next index
-+ self.next_index += self.step
-+
-+
-+ def __next__(self):
-+ cdef void * cogr_feature
-+ cdef Session session
-+ session = self.collection.session
-+
-+ #Update read cursor
-+ self._next()
-+
-+ # Get the next feature.
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+
-+ feature = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=self.encoding,
-+ driver=self.collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+ return feature
-+
-+
-+cdef class ItemsIterator(Iterator):
-+
-+ def __next__(self):
-+
-+ cdef long fid
-+ cdef void * cogr_feature
-+ cdef Session session
-+ session = self.collection.session
-+
-+ #Update read cursor
-+ self._next()
-+
-+ # Get the next feature.
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+
-+
-+ fid = ograpi.OGR_F_GetFID(cogr_feature)
-+ feature = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=self.encoding,
-+ driver=self.collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+
-+ return fid, feature
-+
-+
-+cdef class KeysIterator(Iterator):
-+
-+ def __next__(self):
-+ cdef long fid
-+ cdef void * cogr_feature
-+ cdef Session session
-+ session = self.collection.session
-+
-+ #Update read cursor
-+ self._next()
-+
-+ # Get the next feature.
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+
-+ fid = ograpi.OGR_F_GetFID(cogr_feature)
-+ _deleteOgrFeature(cogr_feature)
-+
-+ return fid
-+
-+
-+def _listlayers(path):
-+
-+ """Provides a list of the layers in an OGR data source.
-+ """
-+
-+ cdef void *cogr_ds
-+ cdef void *cogr_layer
-+ cdef char *path_c
-+ cdef char *name_c
-+
-+ # Open OGR data source.
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ path_b = path
-+ path_c = path_b
-+ with cpl_errs:
-+ cogr_ds = ograpi.OGROpen(path_c, 0, NULL)
-+ if cogr_ds == NULL:
-+ raise ValueError("No data available at path '%s'" % path)
-+
-+ # Loop over the layers to get their names.
-+ layer_count = ograpi.OGR_DS_GetLayerCount(cogr_ds)
-+ layer_names = []
-+ for i in range(layer_count):
-+ cogr_layer = ograpi.OGR_DS_GetLayer(cogr_ds, i)
-+ name_c = ograpi.OGR_L_GetName(cogr_layer)
-+ name_b = name_c
-+ layer_names.append(name_b.decode('utf-8'))
-+
-+ # Close up data source.
-+ if cogr_ds is not NULL:
-+ ograpi.OGR_DS_Destroy(cogr_ds)
-+ cogr_ds = NULL
-+
-+ return layer_names
-+
-+def buffer_to_virtual_file(bytesbuf):
-+ """Maps a bytes buffer to a virtual file.
-+ """
-+ vsi_filename = os.path.join('/vsimem', uuid.uuid4().hex)
-+ vsi_cfilename = vsi_filename if not isinstance(vsi_filename, string_types) else vsi_filename.encode('utf-8')
-+
-+ vsi_handle = ograpi.VSIFileFromMemBuffer(vsi_cfilename, bytesbuf, len(bytesbuf), 0)
-+ if vsi_handle == NULL:
-+ raise OSError('failed to map buffer to file')
-+ if ograpi.VSIFCloseL(vsi_handle) != 0:
-+ raise OSError('failed to close mapped file handle')
-+
-+ return vsi_filename
-+
-+def remove_virtual_file(vsi_filename):
-+ vsi_cfilename = vsi_filename if not isinstance(vsi_filename, string_types) else vsi_filename.encode('utf-8')
-+ return ograpi.VSIUnlink(vsi_cfilename)
-+
-+
---- /dev/null
-+++ b/fiona/ogrext2.pyx
-@@ -0,0 +1,1312 @@
-+# These are extension functions and classes using the OGR C API.
-+
-+import datetime
-+import json
-+import locale
-+import logging
-+import os
-+import sys
-+import warnings
-+import math
-+import uuid
-+
-+if sys.version_info > (3,):
-+ from builtins import int
-+else:
-+ from __builtin__ import int
-+
-+from six import integer_types, string_types, text_type
-+
-+from fiona cimport ograpi
-+from fiona._geometry cimport GeomBuilder, OGRGeomBuilder
-+from fiona._err import cpl_errs
-+from fiona._geometry import GEOMETRY_TYPES
-+from fiona.errors import DriverError, SchemaError, CRSError, FionaValueError
-+from fiona.odict import OrderedDict
-+from fiona.rfc3339 import parse_date, parse_datetime, parse_time
-+from fiona.rfc3339 import FionaDateType, FionaDateTimeType, FionaTimeType
-+
-+from libc.stdlib cimport malloc, free
-+from libc.string cimport strcmp
-+
-+
-+log = logging.getLogger("Fiona")
-+class NullHandler(logging.Handler):
-+ def emit(self, record):
-+ pass
-+log.addHandler(NullHandler())
-+
-+
-+# Mapping of OGR integer field types to Fiona field type names.
-+#
-+# Lists are currently unsupported in this version, but might be done as
-+# arrays in a future version.
-+
-+FIELD_TYPES = [
-+ 'int', # OFTInteger, Simple 32bit integer
-+ None, # OFTIntegerList, List of 32bit integers
-+ 'float', # OFTReal, Double Precision floating point
-+ None, # OFTRealList, List of doubles
-+ 'str', # OFTString, String of ASCII chars
-+ None, # OFTStringList, Array of strings
-+ None, # OFTWideString, deprecated
-+ None, # OFTWideStringList, deprecated
-+ None, # OFTBinary, Raw Binary data
-+ 'date', # OFTDate, Date
-+ 'time', # OFTTime, Time
-+ 'datetime', # OFTDateTime, Date and Time
-+ 'int', # OFTInteger64, Single 64bit integer
-+ None, # OFTInteger64List, List of 64bit integers
-+ ]
-+
-+# Mapping of Fiona field type names to Python types.
-+FIELD_TYPES_MAP = {
-+ 'int': int,
-+ 'float': float,
-+ 'str': text_type,
-+ 'date': FionaDateType,
-+ 'time': FionaTimeType,
-+ 'datetime': FionaDateTimeType
-+ }
-+
-+# OGR Layer capability
-+OLC_RANDOMREAD = b"RandomRead"
-+OLC_SEQUENTIALWRITE = b"SequentialWrite"
-+OLC_RANDOMWRITE = b"RandomWrite"
-+OLC_FASTSPATIALFILTER = b"FastSpatialFilter"
-+OLC_FASTFEATURECOUNT = b"FastFeatureCount"
-+OLC_FASTGETEXTENT = b"FastGetExtent"
-+OLC_FASTSETNEXTBYINDEX = b"FastSetNextByIndex"
-+OLC_CREATEFIELD = b"CreateField"
-+OLC_CREATEGEOMFIELD = b"CreateGeomField"
-+OLC_DELETEFIELD = b"DeleteField"
-+OLC_REORDERFIELDS = b"ReorderFields"
-+OLC_ALTERFIELDDEFN = b"AlterFieldDefn"
-+OLC_DELETEFEATURE = b"DeleteFeature"
-+OLC_STRINGSASUTF8 = b"StringsAsUTF8"
-+OLC_TRANSACTIONS = b"Transactions"
-+
-+# OGR integer error types.
-+
-+OGRERR_NONE = 0
-+OGRERR_NOT_ENOUGH_DATA = 1 # not enough data to deserialize */
-+OGRERR_NOT_ENOUGH_MEMORY = 2
-+OGRERR_UNSUPPORTED_GEOMETRY_TYPE = 3
-+OGRERR_UNSUPPORTED_OPERATION = 4
-+OGRERR_CORRUPT_DATA = 5
-+OGRERR_FAILURE = 6
-+OGRERR_UNSUPPORTED_SRS = 7
-+OGRERR_INVALID_HANDLE = 8
-+
-+
-+cdef char ** string_list(list_str):
-+ """
-+ Function by Stackoverflow User falsetru
-+ https://stackoverflow.com/questions/17511309/fast-string-array-cython
-+ """
-+ cdef char* s
-+ cdef char **ret = <char **>malloc(len(list_str) * sizeof(char *))
-+ for i in range(len(list_str)):
-+ s = list_str[i]
-+ ret[i] = s
-+ ret[i + 1] = NULL
-+ return ret
-+
-+def _explode(coords):
-+ """Explode a GeoJSON geometry's coordinates object and yield
-+ coordinate tuples. As long as the input is conforming, the type of
-+ the geometry doesn't matter."""
-+ for e in coords:
-+ if isinstance(e, (float, int)):
-+ yield coords
-+ break
-+ else:
-+ for f in _explode(e):
-+ yield f
-+
-+
-+def _bounds(geometry):
-+ """Bounding box of a GeoJSON geometry"""
-+ try:
-+ xyz = tuple(zip(*list(_explode(geometry['coordinates']))))
-+ return min(xyz[0]), min(xyz[1]), max(xyz[0]), max(xyz[1])
-+ except (KeyError, TypeError):
-+ return None
-+
-+def calc_gdal_version_num(maj, min, rev):
-+ """Calculates the internal gdal version number based on major, minor and revision"""
-+ return int(maj * 1000000 + min * 10000 + rev*100)
-+
-+def get_gdal_version_num():
-+ """Return current internal version number of gdal"""
-+ return int(ograpi.GDALVersionInfo("VERSION_NUM"))
-+
-+def get_gdal_release_name():
-+ """Return release name of gdal"""
-+ return ograpi.GDALVersionInfo("RELEASE_NAME")
-+
-+
-+# Feature extension classes and functions follow.
-+
-+cdef class FeatureBuilder:
-+ """Build Fiona features from OGR feature pointers.
-+
-+ No OGR objects are allocated by this function and the feature
-+ argument is not destroyed.
-+ """
-+
-+ cdef build(self, void *feature, encoding='utf-8', bbox=False, driver=None):
-+ # The only method anyone ever needs to call
-+ cdef void *fdefn
-+ cdef int i
-+ cdef int y = 0
-+ cdef int m = 0
-+ cdef int d = 0
-+ cdef int hh = 0
-+ cdef int mm = 0
-+ cdef int ss = 0
-+ cdef int tz = 0
-+ cdef int retval
-+ cdef char *key_c
-+ props = OrderedDict()
-+ for i in range(ograpi.OGR_F_GetFieldCount(feature)):
-+ fdefn = ograpi.OGR_F_GetFieldDefnRef(feature, i)
-+ if fdefn == NULL:
-+ raise ValueError("Null feature definition")
-+ key_c = ograpi.OGR_Fld_GetNameRef(fdefn)
-+ if key_c == NULL:
-+ raise ValueError("Null field name reference")
-+ key_b = key_c
-+ key = key_b.decode(encoding)
-+ fieldtypename = FIELD_TYPES[ograpi.OGR_Fld_GetType(fdefn)]
-+ if not fieldtypename:
-+ log.warn(
-+ "Skipping field %s: invalid type %s",
-+ key,
-+ ograpi.OGR_Fld_GetType(fdefn))
-+ continue
-+
-+ # TODO: other types
-+ fieldtype = FIELD_TYPES_MAP[fieldtypename]
-+ if not ograpi.OGR_F_IsFieldSet(feature, i):
-+ props[key] = None
-+ elif fieldtype is int:
-+ props[key] = ograpi.OGR_F_GetFieldAsInteger64(feature, i)
-+ elif fieldtype is float:
-+ props[key] = ograpi.OGR_F_GetFieldAsDouble(feature, i)
-+
-+ elif fieldtype is text_type:
-+ try:
-+ val = ograpi.OGR_F_GetFieldAsString(feature, i)
-+ val = val.decode(encoding)
-+ except UnicodeDecodeError:
-+ log.warn(
-+ "Failed to decode %s using %s codec", val, encoding)
-+
-+ # Does the text contain a JSON object? Let's check.
-+ # Let's check as cheaply as we can.
-+ if driver == 'GeoJSON' and val.startswith('{'):
-+ try:
-+ val = json.loads(val)
-+ except ValueError as err:
-+ log.warn(str(err))
-+
-+ # Now add to the properties object.
-+ props[key] = val
-+
-+ elif fieldtype in (FionaDateType, FionaTimeType, FionaDateTimeType):
-+ retval = ograpi.OGR_F_GetFieldAsDateTime(
-+ feature, i, &y, &m, &d, &hh, &mm, &ss, &tz)
-+ if fieldtype is FionaDateType:
-+ props[key] = datetime.date(y, m, d).isoformat()
-+ elif fieldtype is FionaTimeType:
-+ props[key] = datetime.time(hh, mm, ss).isoformat()
-+ else:
-+ props[key] = datetime.datetime(
-+ y, m, d, hh, mm, ss).isoformat()
-+ else:
-+ log.debug("%s: None, fieldtype: %r, %r" % (key, fieldtype, fieldtype in string_types))
-+ props[key] = None
-+
-+ cdef void *cogr_geometry = ograpi.OGR_F_GetGeometryRef(feature)
-+ if cogr_geometry is not NULL:
-+ geom = GeomBuilder().build(cogr_geometry)
-+ else:
-+ geom = None
-+ return {
-+ 'type': 'Feature',
-+ 'id': str(ograpi.OGR_F_GetFID(feature)),
-+ 'geometry': geom,
-+ 'properties': props }
-+
-+
-+cdef class OGRFeatureBuilder:
-+
-+ """Builds an OGR Feature from a Fiona feature mapping.
-+
-+ Allocates one OGR Feature which should be destroyed by the caller.
-+ Borrows a layer definition from the collection.
-+ """
-+
-+ cdef void * build(self, feature, collection) except NULL:
-+ cdef void *cogr_geometry = NULL
-+ cdef char *string_c
-+ cdef WritingSession session
-+ session = collection.session
-+ cdef void *cogr_layer = session.cogr_layer
-+ if cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cdef void *cogr_featuredefn = ograpi.OGR_L_GetLayerDefn(cogr_layer)
-+ if cogr_featuredefn == NULL:
-+ raise ValueError("Null feature definition")
-+ cdef void *cogr_feature = ograpi.OGR_F_Create(cogr_featuredefn)
-+ if cogr_feature == NULL:
-+ raise ValueError("Null feature")
-+
-+ if feature['geometry'] is not None:
-+ cogr_geometry = OGRGeomBuilder().build(
-+ feature['geometry'])
-+ ograpi.OGR_F_SetGeometryDirectly(cogr_feature, cogr_geometry)
-+
-+ # OGR_F_SetFieldString takes UTF-8 encoded strings ('bytes' in
-+ # Python 3).
-+ encoding = session.get_internalencoding()
-+
-+ for key, value in feature['properties'].items():
-+ log.debug(
-+ "Looking up %s in %s", key, repr(session._schema_mapping))
-+ ogr_key = session._schema_mapping[key]
-+ schema_type = collection.schema['properties'][key]
-+ try:
-+ key_bytes = ogr_key.encode(encoding)
-+ except UnicodeDecodeError:
-+ log.warn("Failed to encode %s using %s codec", key, encoding)
-+ key_bytes = ogr_key
-+ key_c = key_bytes
-+ i = ograpi.OGR_F_GetFieldIndex(cogr_feature, key_c)
-+ if i < 0:
-+ continue
-+
-+ # Special case: serialize dicts to assist OGR.
-+ if isinstance(value, dict):
-+ value = json.dumps(value)
-+
-+ # Continue over the standard OGR types.
-+ if isinstance(value, integer_types):
-+ ograpi.OGR_F_SetFieldInteger64(cogr_feature, i, value)
-+ elif isinstance(value, float):
-+ ograpi.OGR_F_SetFieldDouble(cogr_feature, i, value)
-+ elif (isinstance(value, string_types)
-+ and schema_type in ['date', 'time', 'datetime']):
-+ if schema_type == 'date':
-+ y, m, d, hh, mm, ss, ff = parse_date(value)
-+ elif schema_type == 'time':
-+ y, m, d, hh, mm, ss, ff = parse_time(value)
-+ else:
-+ y, m, d, hh, mm, ss, ff = parse_datetime(value)
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, y, m, d, hh, mm, ss, 0)
-+ elif (isinstance(value, datetime.date)
-+ and schema_type == 'date'):
-+ y, m, d = value.year, value.month, value.day
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, y, m, d, 0, 0, 0, 0)
-+ elif (isinstance(value, datetime.datetime)
-+ and schema_type == 'datetime'):
-+ y, m, d = value.year, value.month, value.day
-+ hh, mm, ss = value.hour, value.minute, value.second
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, y, m, d, hh, mm, ss, 0)
-+ elif (isinstance(value, datetime.time)
-+ and schema_type == 'time'):
-+ hh, mm, ss = value.hour, value.minute, value.second
-+ ograpi.OGR_F_SetFieldDateTime(
-+ cogr_feature, i, 0, 0, 0, hh, mm, ss, 0)
-+ elif isinstance(value, string_types):
-+ try:
-+ value_bytes = value.encode(encoding)
-+ except UnicodeDecodeError:
-+ log.warn(
-+ "Failed to encode %s using %s codec", value, encoding)
-+ value_bytes = value
-+ string_c = value_bytes
-+ ograpi.OGR_F_SetFieldString(cogr_feature, i, string_c)
-+ elif value is None:
-+ pass # keep field unset/null
-+ else:
-+ raise ValueError("Invalid field type %s" % type(value))
-+ log.debug("Set field %s: %s" % (key, value))
-+ return cogr_feature
-+
-+
-+cdef _deleteOgrFeature(void *cogr_feature):
-+ """Delete an OGR feature"""
-+ if cogr_feature is not NULL:
-+ ograpi.OGR_F_Destroy(cogr_feature)
-+ cogr_feature = NULL
-+
-+
-+def featureRT(feature, collection):
-+ # For testing purposes only, leaks the JSON data
-+ cdef void *cogr_feature = OGRFeatureBuilder().build(feature, collection)
-+ cdef void *cogr_geometry = ograpi.OGR_F_GetGeometryRef(cogr_feature)
-+ if cogr_geometry == NULL:
-+ raise ValueError("Null geometry")
-+ log.debug("Geometry: %s" % ograpi.OGR_G_ExportToJson(cogr_geometry))
-+ encoding = collection.encoding or 'utf-8'
-+ result = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=encoding,
-+ driver=collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+ return result
-+
-+
-+# Collection-related extension classes and functions
-+
-+cdef class Session:
-+
-+ cdef void *cogr_ds
-+ cdef void *cogr_layer
-+ cdef object _fileencoding
-+ cdef object _encoding
-+ cdef object collection
-+
-+ def __cinit__(self):
-+ self.cogr_ds = NULL
-+ self.cogr_layer = NULL
-+ self._fileencoding = None
-+ self._encoding = None
-+
-+ def __dealloc__(self):
-+ self.stop()
-+
-+ def start(self, collection):
-+ cdef const char *path_c = NULL
-+ cdef const char *name_c = NULL
-+ cdef void *drv = NULL
-+ cdef void *ds = NULL
-+ cdef char ** drvs = NULL
-+ if collection.path == '-':
-+ path = '/vsistdin/'
-+ else:
-+ path = collection.path
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ # Presume already a UTF-8 encoded string
-+ path_b = path
-+ path_c = path_b
-+
-+ with cpl_errs:
-+ drivers = []
-+ if collection._driver:
-+ drivers = [collection._driver]
-+ elif collection.enabled_drivers:
-+ drivers = collection.enabled_drivers
-+ if drivers:
-+ for name in drivers:
-+ name_b = name.encode()
-+ name_c = name_b
-+ log.debug("Trying driver: %s", name)
-+ drv = ograpi.GDALGetDriverByName(name_c)
-+ if drv != NULL:
-+ drvs = string_list([name_b])
-+
-+ flags = ograpi.GDAL_OF_VECTOR | ograpi.GDAL_OF_READONLY
-+ log.debug("GDALOpenEx({}, {}, {})".format(path_c, flags, [name_b]))
-+ ds = ograpi.GDALOpenEx(path_c,
-+ flags,
-+ drvs,
-+ NULL,
-+ NULL)
-+ if ds != NULL:
-+ self.cogr_ds = ds
-+ collection._driver = name
-+ _driver = ograpi.GDALGetDatasetDriver(ds)
-+ drv_name = ograpi.GDALGetDriverShortName(_driver)
-+ log.debug("Driver: {} Success".format(drv_name))
-+
-+ break
-+ else:
-+ self.cogr_ds = ograpi.GDALOpenEx(path_c,
-+ ograpi.GDAL_OF_VECTOR | ograpi.GDAL_OF_READONLY,
-+ NULL,
-+ NULL,
-+ NULL)
-+
-+ if self.cogr_ds == NULL:
-+ raise FionaValueError(
-+ "No dataset found at path '%s' using drivers: %s" % (
-+ collection.path,
-+ drivers or '*'))
-+
-+ if isinstance(collection.name, string_types):
-+ name_b = collection.name.encode('utf-8')
-+ name_c = name_b
-+ self.cogr_layer = ograpi.GDALDatasetGetLayerByName(
-+ self.cogr_ds, name_c)
-+ elif isinstance(collection.name, int):
-+ self.cogr_layer = ograpi.GDALDatasetGetLayer(
-+ self.cogr_ds, collection.name)
-+ name_c = ograpi.OGR_L_GetName(self.cogr_layer)
-+ name_b = name_c
-+ collection.name = name_b.decode('utf-8')
-+
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer: " + repr(collection.name))
-+
-+ self.collection = collection
-+
-+ userencoding = self.collection.encoding
-+ if userencoding:
-+ ograpi.CPLSetThreadLocalConfigOption('SHAPE_ENCODING', '')
-+ self._fileencoding = userencoding.upper()
-+ else:
-+ self._fileencoding = (
-+ ograpi.OGR_L_TestCapability(
-+ self.cogr_layer, OLC_STRINGSASUTF8) and
-+ 'utf-8') or (
-+ self.get_driver() == "ESRI Shapefile" and
-+ 'ISO-8859-1') or locale.getpreferredencoding().upper()
-+
-+ def stop(self):
-+ self.cogr_layer = NULL
-+ if self.cogr_ds is not NULL:
-+ ograpi.GDALClose(self.cogr_ds)
-+ self.cogr_ds = NULL
-+
-+ def get_fileencoding(self):
-+ return self._fileencoding
-+
-+ def get_internalencoding(self):
-+ if not self._encoding:
-+ fileencoding = self.get_fileencoding()
-+ self._encoding = (
-+ ograpi.OGR_L_TestCapability(
-+ self.cogr_layer, OLC_STRINGSASUTF8) and
-+ 'utf-8') or fileencoding
-+ return self._encoding
-+
-+ def get_length(self):
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ return ograpi.OGR_L_GetFeatureCount(self.cogr_layer, 0)
-+
-+ def get_driver(self):
-+ cdef void *cogr_driver = ograpi.GDALGetDatasetDriver(self.cogr_ds)
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+ cdef char *name = ograpi.OGR_Dr_GetName(cogr_driver)
-+ driver_name = name
-+ return driver_name.decode()
-+
-+ def get_schema(self):
-+ cdef int i
-+ cdef int n
-+ cdef void *cogr_featuredefn
-+ cdef void *cogr_fielddefn
-+ cdef char *key_c
-+ props = []
-+
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+
-+ cogr_featuredefn = ograpi.OGR_L_GetLayerDefn(self.cogr_layer)
-+ if cogr_featuredefn == NULL:
-+ raise ValueError("Null feature definition")
-+ n = ograpi.OGR_FD_GetFieldCount(cogr_featuredefn)
-+ for i from 0 <= i < n:
-+ cogr_fielddefn = ograpi.OGR_FD_GetFieldDefn(cogr_featuredefn, i)
-+ if cogr_fielddefn == NULL:
-+ raise ValueError("Null field definition")
-+ key_c = ograpi.OGR_Fld_GetNameRef(cogr_fielddefn)
-+ key_b = key_c
-+ if not bool(key_b):
-+ raise ValueError("Invalid field name ref: %s" % key)
-+ key = key_b.decode(self.get_internalencoding())
-+ fieldtypename = FIELD_TYPES[ograpi.OGR_Fld_GetType(cogr_fielddefn)]
-+ if not fieldtypename:
-+ log.warn(
-+ "Skipping field %s: invalid type %s",
-+ key,
-+ ograpi.OGR_Fld_GetType(cogr_fielddefn))
-+ continue
-+ val = fieldtypename
-+ if fieldtypename == 'float':
-+ fmt = ""
-+ width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-+ if width: # and width != 24:
-+ fmt = ":%d" % width
-+ precision = ograpi.OGR_Fld_GetPrecision(cogr_fielddefn)
-+ if precision: # and precision != 15:
-+ fmt += ".%d" % precision
-+ val = "float" + fmt
-+ elif fieldtypename == 'int':
-+ fmt = ""
-+ width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-+ if width: # and width != 11:
-+ fmt = ":%d" % width
-+ val = fieldtypename + fmt
-+ elif fieldtypename == 'str':
-+ fmt = ""
-+ width = ograpi.OGR_Fld_GetWidth(cogr_fielddefn)
-+ if width: # and width != 80:
-+ fmt = ":%d" % width
-+ val = fieldtypename + fmt
-+
-+ props.append((key, val))
-+
-+ cdef unsigned int geom_type = ograpi.OGR_FD_GetGeomType(
-+ cogr_featuredefn)
-+ return {
-+ 'properties': OrderedDict(props),
-+ 'geometry': GEOMETRY_TYPES[geom_type]}
-+
-+ def get_crs(self):
-+ cdef char *proj_c = NULL
-+ cdef char *auth_key = NULL
-+ cdef char *auth_val = NULL
-+ cdef void *cogr_crs = NULL
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cogr_crs = ograpi.OGR_L_GetSpatialRef(self.cogr_layer)
-+ crs = {}
-+ if cogr_crs is not NULL:
-+ log.debug("Got coordinate system")
-+
-+ retval = ograpi.OSRAutoIdentifyEPSG(cogr_crs)
-+ if retval > 0:
-+ log.info("Failed to auto identify EPSG: %d", retval)
-+
-+ auth_key = ograpi.OSRGetAuthorityName(cogr_crs, NULL)
-+ auth_val = ograpi.OSRGetAuthorityCode(cogr_crs, NULL)
-+
-+ if auth_key != NULL and auth_val != NULL:
-+ key_b = auth_key
-+ key = key_b.decode('utf-8')
-+ if key == 'EPSG':
-+ val_b = auth_val
-+ val = val_b.decode('utf-8')
-+ crs['init'] = "epsg:" + val
-+ else:
-+ ograpi.OSRExportToProj4(cogr_crs, &proj_c)
-+ if proj_c == NULL:
-+ raise ValueError("Null projection")
-+ proj_b = proj_c
-+ log.debug("Params: %s", proj_b)
-+ value = proj_b.decode()
-+ value = value.strip()
-+ for param in value.split():
-+ kv = param.split("=")
-+ if len(kv) == 2:
-+ k, v = kv
-+ try:
-+ v = float(v)
-+ if v % 1 == 0:
-+ v = int(v)
-+ except ValueError:
-+ # Leave v as a string
-+ pass
-+ elif len(kv) == 1:
-+ k, v = kv[0], True
-+ else:
-+ raise ValueError("Unexpected proj parameter %s" % param)
-+ k = k.lstrip("+")
-+ crs[k] = v
-+
-+ ograpi.CPLFree(proj_c)
-+ else:
-+ log.debug("Projection not found (cogr_crs was NULL)")
-+ return crs
-+
-+ def get_crs_wkt(self):
-+ cdef char *proj_c = NULL
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cogr_crs = ograpi.OGR_L_GetSpatialRef(self.cogr_layer)
-+ crs_wkt = ""
-+ if cogr_crs is not NULL:
-+ log.debug("Got coordinate system")
-+ ograpi.OSRExportToWkt(cogr_crs, &proj_c)
-+ if proj_c == NULL:
-+ raise ValueError("Null projection")
-+ proj_b = proj_c
-+ crs_wkt = proj_b.decode('utf-8')
-+ ograpi.CPLFree(proj_c)
-+ else:
-+ log.debug("Projection not found (cogr_crs was NULL)")
-+ return crs_wkt
-+
-+ def get_extent(self):
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ cdef ograpi.OGREnvelope extent
-+ result = ograpi.OGR_L_GetExtent(self.cogr_layer, &extent, 1)
-+ return (extent.MinX, extent.MinY, extent.MaxX, extent.MaxY)
-+
-+ def has_feature(self, fid):
-+ """Provides access to feature data by FID.
-+
-+ Supports Collection.__contains__().
-+ """
-+ cdef void * cogr_feature
-+ fid = int(fid)
-+ cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, fid)
-+ if cogr_feature != NULL:
-+ _deleteOgrFeature(cogr_feature)
-+ return True
-+ else:
-+ return False
-+
-+ def get_feature(self, fid):
-+ """Provides access to feature data by FID.
-+
-+ Supports Collection.__contains__().
-+ """
-+ cdef void * cogr_feature
-+ fid = int(fid)
-+ cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, fid)
-+ if cogr_feature != NULL:
-+ _deleteOgrFeature(cogr_feature)
-+ return True
-+ else:
-+ return False
-+
-+
-+ def __getitem__(self, item):
-+ cdef void * cogr_feature
-+ if isinstance(item, slice):
-+ itr = Iterator(self.collection, item.start, item.stop, item.step)
-+ log.debug("Slice: %r", item)
-+ return list(itr)
-+ elif isinstance(item, int):
-+ index = item
-+ # from the back
-+ if index < 0:
-+ ftcount = ograpi.OGR_L_GetFeatureCount(self.cogr_layer, 0)
-+ if ftcount == -1:
-+ raise IndexError(
-+ "collection's dataset does not support negative indexes")
-+ index += ftcount
-+ cogr_feature = ograpi.OGR_L_GetFeature(self.cogr_layer, index)
-+ if cogr_feature == NULL:
-+ return None
-+ feature = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=self.get_internalencoding(),
-+ driver=self.collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+ return feature
-+
-+
-+ def isactive(self):
-+ if self.cogr_layer != NULL and self.cogr_ds != NULL:
-+ return 1
-+ else:
-+ return 0
-+
-+
-+cdef class WritingSession(Session):
-+
-+ cdef object _schema_mapping
-+
-+ def start(self, collection):
-+ cdef void *cogr_fielddefn
-+ cdef void *cogr_driver
-+ cdef void *cogr_ds
-+ cdef void *cogr_layer
-+ cdef void *cogr_srs = NULL
-+ cdef char **options = NULL
-+ self.collection = collection
-+ cdef char *path_c
-+ cdef char *driver_c
-+ cdef char *name_c
-+ cdef char *proj_c
-+ cdef char *fileencoding_c
-+ path = collection.path
-+
-+ if collection.mode == 'a':
-+ if os.path.exists(path):
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ path_b = path
-+ path_c = path_b
-+ with cpl_errs:
-+ self.cogr_ds = ograpi.GDALOpenEx(path_c,
-+ ograpi.GDAL_OF_VECTOR | ograpi.GDAL_OF_UPDATE,
-+ NULL,
-+ NULL,
-+ NULL)
-+# self.cogr_ds = ograpi.OGROpen(path_c, 1, NULL)
-+ if self.cogr_ds == NULL:
-+ raise RuntimeError("Failed to open %s" % path)
-+ cogr_driver = ograpi.GDALGetDatasetDriver(self.cogr_ds)
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+
-+ if isinstance(collection.name, string_types):
-+ name_b = collection.name.encode()
-+ name_c = name_b
-+ self.cogr_layer = ograpi.GDALDatasetGetLayerByName(
-+ self.cogr_ds, name_c)
-+ elif isinstance(collection.name, int):
-+ self.cogr_layer = ograpi.GDALDatasetGetLayer(
-+ self.cogr_ds, collection.name)
-+
-+ if self.cogr_layer == NULL:
-+ raise RuntimeError(
-+ "Failed to get layer %s" % collection.name)
-+ else:
-+ raise OSError("No such file or directory %s" % path)
-+
-+ userencoding = self.collection.encoding
-+ self._fileencoding = (userencoding or (
-+ ograpi.OGR_L_TestCapability(self.cogr_layer, OLC_STRINGSASUTF8) and
-+ 'utf-8') or (
-+ self.get_driver() == "ESRI Shapefile" and
-+ 'ISO-8859-1') or locale.getpreferredencoding()).upper()
-+
-+ elif collection.mode == 'w':
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ path_b = path
-+ path_c = path_b
-+ driver_b = collection.driver.encode()
-+ driver_c = driver_b
-+
-+ cogr_driver = ograpi.GDALGetDriverByName(driver_c)
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+
-+ if not os.path.exists(path):
-+# cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-+# cogr_driver, path_c, NULL)
-+ cogr_ds = ograpi.GDALCreate(
-+ cogr_driver,
-+ path_c,
-+ 0,
-+ 0,
-+ 0,
-+ ograpi.GDT_Unknown,
-+ NULL)
-+ pass
-+
-+ else:
-+ with cpl_errs:
-+ cogr_ds = ograpi.GDALOpenEx(path_c,
-+ ograpi.GDAL_OF_VECTOR | ograpi.GDAL_OF_UPDATE,
-+ NULL,
-+ NULL,
-+ NULL)
-+# cogr_ds = ograpi.OGROpen(path_c, 1, NULL)
-+ if cogr_ds == NULL:
-+ cogr_ds = ograpi.GDALCreate(
-+ cogr_driver,
-+ path_c,
-+ 0,
-+ 0,
-+ 0,
-+ ograpi.GDT_Unknown,
-+ NULL)
-+# cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-+# cogr_driver, path_c, NULL)
-+
-+ elif collection.name is None:
-+ ograpi.GDALClose(cogr_ds)
-+ cogr_ds == NULL
-+ log.debug("Deleted pre-existing data at %s", path)
-+ cogr_ds = ograpi.GDALCreate(
-+ cogr_driver,
-+ path_c,
-+ 0,
-+ 0,
-+ 0,
-+ ograpi.GDT_Unknown,
-+ NULL)
-+# cogr_ds = ograpi.OGR_Dr_CreateDataSource(
-+# cogr_driver, path_c, NULL)
-+
-+ else:
-+ pass
-+
-+ if cogr_ds == NULL:
-+ raise RuntimeError("Failed to open %s" % path)
-+ else:
-+ self.cogr_ds = cogr_ds
-+
-+ # Set the spatial reference system from the crs given to the
-+ # collection constructor. We by-pass the crs_wkt and crs
-+ # properties because they aren't accessible until the layer
-+ # is constructed (later).
-+ col_crs = collection._crs_wkt or collection._crs
-+ if col_crs:
-+ cogr_srs = ograpi.OSRNewSpatialReference(NULL)
-+ if cogr_srs == NULL:
-+ raise ValueError("NULL spatial reference")
-+ # First, check for CRS strings like "EPSG:3857".
-+ if isinstance(col_crs, string_types):
-+ proj_b = col_crs.encode('utf-8')
-+ proj_c = proj_b
-+ ograpi.OSRSetFromUserInput(cogr_srs, proj_c)
-+ elif isinstance(col_crs, dict):
-+ # EPSG is a special case.
-+ init = col_crs.get('init')
-+ if init:
-+ log.debug("Init: %s", init)
-+ auth, val = init.split(':')
-+ if auth.upper() == 'EPSG':
-+ log.debug("Setting EPSG: %s", val)
-+ ograpi.OSRImportFromEPSG(cogr_srs, int(val))
-+ else:
-+ params = []
-+ col_crs['wktext'] = True
-+ for k, v in col_crs.items():
-+ if v is True or (k in ('no_defs', 'wktext') and v):
-+ params.append("+%s" % k)
-+ else:
-+ params.append("+%s=%s" % (k, v))
-+ proj = " ".join(params)
-+ log.debug("PROJ.4 to be imported: %r", proj)
-+ proj_b = proj.encode('utf-8')
-+ proj_c = proj_b
-+ ograpi.OSRImportFromProj4(cogr_srs, proj_c)
-+ else:
-+ raise ValueError("Invalid CRS")
-+
-+ # Fixup, export to WKT, and set the GDAL dataset's projection.
-+ ograpi.OSRFixup(cogr_srs)
-+
-+ # Figure out what encoding to use. The encoding parameter given
-+ # to the collection constructor takes highest precedence, then
-+ # 'iso-8859-1', then the system's default encoding as last resort.
-+ sysencoding = locale.getpreferredencoding()
-+ userencoding = collection.encoding
-+ self._fileencoding = (userencoding or (
-+ collection.driver == "ESRI Shapefile" and
-+ 'ISO-8859-1') or sysencoding).upper()
-+
-+ fileencoding = self.get_fileencoding()
-+ if fileencoding:
-+ fileencoding_b = fileencoding.encode()
-+ fileencoding_c = fileencoding_b
-+ options = ograpi.CSLSetNameValue(options, "ENCODING", fileencoding_c)
-+
-+ # Does the layer exist already? If so, we delete it.
-+ layer_count = ograpi.GDALDatasetGetLayerCount(self.cogr_ds)
-+ layer_names = []
-+ for i in range(layer_count):
-+ cogr_layer = ograpi.GDALDatasetGetLayer(cogr_ds, i)
-+ name_c = ograpi.OGR_L_GetName(cogr_layer)
-+ name_b = name_c
-+ layer_names.append(name_b.decode('utf-8'))
-+
-+ idx = -1
-+ if isinstance(collection.name, string_types):
-+ if collection.name in layer_names:
-+ idx = layer_names.index(collection.name)
-+ elif isinstance(collection.name, int):
-+ if collection.name >= 0 and collection.name < layer_count:
-+ idx = collection.name
-+ if idx >= 0:
-+ log.debug("Deleted pre-existing layer at %s", collection.name)
-+ ograpi.GDALDatasetDeleteLayer(self.cogr_ds, idx)
-+
-+ # Create the named layer in the datasource.
-+ name_b = collection.name.encode('utf-8')
-+ name_c = name_b
-+ self.cogr_layer = ograpi.GDALDatasetCreateLayer(
-+ self.cogr_ds,
-+ name_c,
-+ cogr_srs,
-+ <unsigned int>[k for k,v in GEOMETRY_TYPES.items() if
-+ v == collection.schema.get('geometry', 'Unknown')][0],
-+ options
-+ )
-+
-+ if cogr_srs != NULL:
-+ ograpi.OSRDestroySpatialReference(cogr_srs)
-+ if options != NULL:
-+ ograpi.CSLDestroy(options)
-+
-+ if self.cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ log.debug("Created layer")
-+
-+ # Next, make a layer definition from the given schema properties,
-+ # which are an ordered dict since Fiona 1.0.1.
-+ for key, value in collection.schema['properties'].items():
-+ log.debug("Creating field: %s %s", key, value)
-+
-+ # Convert 'long' to 'int'. See
-+ # https://github.com/Toblerity/Fiona/issues/101.
-+ if value == 'long':
-+ value = 'int'
-+
-+ # Is there a field width/precision?
-+ width = precision = None
-+ if ':' in value:
-+ value, fmt = value.split(':')
-+ if '.' in fmt:
-+ width, precision = map(int, fmt.split('.'))
-+ else:
-+ width = int(fmt)
-+
-+ field_type = FIELD_TYPES.index(value)
-+ # See https://trac.osgeo.org/gdal/wiki/rfc31_ogr_64
-+ if value == 'int' and (width is not None and width >= 10):
-+ field_type = 12
-+
-+ encoding = self.get_internalencoding()
-+ key_bytes = key.encode(encoding)
-+
-+ cogr_fielddefn = ograpi.OGR_Fld_Create(
-+ key_bytes,
-+ field_type)
-+ if cogr_fielddefn == NULL:
-+ raise ValueError("Null field definition")
-+ if width:
-+ ograpi.OGR_Fld_SetWidth(cogr_fielddefn, width)
-+ if precision:
-+ ograpi.OGR_Fld_SetPrecision(cogr_fielddefn, precision)
-+ ograpi.OGR_L_CreateField(self.cogr_layer, cogr_fielddefn, 1)
-+ ograpi.OGR_Fld_Destroy(cogr_fielddefn)
-+ log.debug("Created fields")
-+
-+ # Mapping of the Python collection schema to the munged
-+ # OGR schema.
-+ ogr_schema = self.get_schema()
-+ self._schema_mapping = dict(zip(
-+ collection.schema['properties'].keys(),
-+ ogr_schema['properties'].keys() ))
-+
-+ log.debug("Writing started")
-+
-+ def writerecs(self, records, collection):
-+ """Writes buffered records to OGR."""
-+ cdef void *cogr_driver
-+ cdef void *cogr_feature
-+
-+ cdef void *cogr_layer = self.cogr_layer
-+ if cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+
-+ schema_geom_type = collection.schema['geometry']
-+ cogr_driver = ograpi.GDALGetDatasetDriver(self.cogr_ds)
-+ if ograpi.OGR_Dr_GetName(cogr_driver) == b"GeoJSON":
-+ def validate_geometry_type(rec):
-+ return True
-+ elif ograpi.OGR_Dr_GetName(cogr_driver) == b"ESRI Shapefile" \
-+ and "Point" not in collection.schema['geometry']:
-+ schema_geom_type = collection.schema['geometry'].lstrip(
-+ "3D ").lstrip("Multi")
-+ def validate_geometry_type(rec):
-+ return rec['geometry'] is None or \
-+ rec['geometry']['type'].lstrip(
-+ "3D ").lstrip("Multi") == schema_geom_type
-+ else:
-+ schema_geom_type = collection.schema['geometry'].lstrip("3D ")
-+ def validate_geometry_type(rec):
-+ return rec['geometry'] is None or \
-+ rec['geometry']['type'].lstrip("3D ") == schema_geom_type
-+
-+ schema_props_keys = set(collection.schema['properties'].keys())
-+ for record in records:
-+ log.debug("Creating feature in layer: %s" % record)
-+ # Validate against collection's schema.
-+ if set(record['properties'].keys()) != schema_props_keys:
-+ raise ValueError(
-+ "Record does not match collection schema: %r != %r" % (
-+ record['properties'].keys(),
-+ list(schema_props_keys) ))
-+ if not validate_geometry_type(record):
-+ raise ValueError(
-+ "Record's geometry type does not match "
-+ "collection schema's geometry type: %r != %r" % (
-+ record['geometry']['type'],
-+ collection.schema['geometry'] ))
-+
-+ cogr_feature = OGRFeatureBuilder().build(record, collection)
-+ result = ograpi.OGR_L_CreateFeature(cogr_layer, cogr_feature)
-+ if result != OGRERR_NONE:
-+ raise RuntimeError("Failed to write record: %s" % record)
-+ _deleteOgrFeature(cogr_feature)
-+
-+ def sync(self, collection):
-+ """Syncs OGR to disk."""
-+ cdef void *cogr_ds = self.cogr_ds
-+ cdef void *cogr_layer = self.cogr_layer
-+ if cogr_ds == NULL:
-+ raise ValueError("Null data source")
-+ log.debug("Syncing OGR to disk")
-+
-+ ograpi.GDALFlushCache(cogr_ds)
-+
-+
-+cdef class Iterator:
-+
-+ """Provides iterated access to feature data.
-+ """
-+
-+ # Reference to its Collection
-+ cdef collection
-+ cdef encoding
-+ cdef int next_index
-+ cdef stop
-+ cdef start
-+ cdef step
-+ cdef fastindex
-+ cdef stepsign
-+
-+ def __init__(self, collection,
-+ start=None, stop=None, step=None, bbox=None, mask=None):
-+ if collection.session is None:
-+ raise ValueError("I/O operation on closed collection")
-+ self.collection = collection
-+ cdef Session session
-+ cdef void *cogr_geometry
-+ session = self.collection.session
-+ cdef void *cogr_layer = session.cogr_layer
-+ if cogr_layer == NULL:
-+ raise ValueError("Null layer")
-+ ograpi.OGR_L_ResetReading(cogr_layer)
-+
-+ if bbox and mask:
-+ raise ValueError("mask and bbox can not be set together")
-+
-+ if bbox:
-+ ograpi.OGR_L_SetSpatialFilterRect(
-+ cogr_layer, bbox[0], bbox[1], bbox[2], bbox[3])
-+ elif mask:
-+ cogr_geometry = OGRGeomBuilder().build(mask)
-+ ograpi.OGR_L_SetSpatialFilter(cogr_layer, cogr_geometry)
-+ ograpi.OGR_G_DestroyGeometry(cogr_geometry)
-+
-+ else:
-+ ograpi.OGR_L_SetSpatialFilter(
-+ cogr_layer, NULL)
-+ self.encoding = session.get_internalencoding()
-+
-+ self.fastindex = ograpi.OGR_L_TestCapability(
-+ session.cogr_layer, OLC_FASTSETNEXTBYINDEX)
-+
-+ ftcount = ograpi.OGR_L_GetFeatureCount(session.cogr_layer, 0)
-+ if ftcount == -1 and ((start is not None and start < 0) or
-+ (stop is not None and stop < 0)):
-+ raise IndexError(
-+ "collection's dataset does not support negative slice indexes")
-+
-+ if stop is not None and stop < 0:
-+ stop += ftcount
-+
-+ if start is None:
-+ start = 0
-+ if start is not None and start < 0:
-+ start += ftcount
-+
-+ # step size
-+ if step is None:
-+ step = 1
-+ if step == 0:
-+ raise ValueError("slice step cannot be zero")
-+ if step < 0 and not self.fastindex:
-+ warnings.warn("Layer does not support" \
-+ "OLCFastSetNextByIndex, negative step size may" \
-+ " be slow", RuntimeWarning)
-+ self.stepsign = int(math.copysign(1, step))
-+ self.stop = stop
-+ self.start = start
-+ self.step = step
-+
-+ self.next_index = start
-+ log.debug("Index: %d", self.next_index)
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+
-+ def __iter__(self):
-+ return self
-+
-+
-+ def _next(self):
-+ """Internal method to set read cursor to next item"""
-+
-+ cdef Session session
-+ session = self.collection.session
-+
-+ # Check if next_index is valid
-+ if self.next_index < 0:
-+ raise StopIteration
-+
-+ if self.stepsign == 1:
-+ if self.next_index < self.start or (self.stop is not None and self.next_index >= self.stop):
-+ raise StopIteration
-+ else:
-+ if self.next_index > self.start or (self.stop is not None and self.next_index <= self.stop):
-+ raise StopIteration
-+
-+
-+ # Set read cursor to next_item position
-+ if self.step > 1 and self.fastindex:
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+ elif self.step > 1 and not self.fastindex and not self.next_index == self.start:
-+ for _ in range(self.step - 1):
-+ # TODO rbuffat add test -> OGR_L_GetNextFeature increments cursor by 1, therefore self.step - 1 as one increment was performed when feature is read
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+ elif self.step > 1 and not self.fastindex and self.next_index == self.start:
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+ elif self.step == 0:
-+ # ograpi.OGR_L_GetNextFeature increments read cursor by one
-+ pass
-+ elif self.step < 0:
-+ ograpi.OGR_L_SetNextByIndex(session.cogr_layer, self.next_index)
-+
-+ # set the next index
-+ self.next_index += self.step
-+
-+
-+ def __next__(self):
-+ cdef void * cogr_feature
-+ cdef Session session
-+ session = self.collection.session
-+
-+ #Update read cursor
-+ self._next()
-+
-+ # Get the next feature.
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+
-+ feature = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=self.encoding,
-+ driver=self.collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+ return feature
-+
-+
-+cdef class ItemsIterator(Iterator):
-+
-+ def __next__(self):
-+
-+ cdef long fid
-+ cdef void * cogr_feature
-+ cdef Session session
-+ session = self.collection.session
-+
-+ #Update read cursor
-+ self._next()
-+
-+ # Get the next feature.
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+
-+
-+ fid = ograpi.OGR_F_GetFID(cogr_feature)
-+ feature = FeatureBuilder().build(
-+ cogr_feature,
-+ bbox=False,
-+ encoding=self.encoding,
-+ driver=self.collection.driver
-+ )
-+ _deleteOgrFeature(cogr_feature)
-+
-+ return fid, feature
-+
-+
-+cdef class KeysIterator(Iterator):
-+
-+ def __next__(self):
-+ cdef long fid
-+ cdef void * cogr_feature
-+ cdef Session session
-+ session = self.collection.session
-+
-+ #Update read cursor
-+ self._next()
-+
-+ # Get the next feature.
-+ cogr_feature = ograpi.OGR_L_GetNextFeature(session.cogr_layer)
-+ if cogr_feature == NULL:
-+ raise StopIteration
-+
-+ fid = ograpi.OGR_F_GetFID(cogr_feature)
-+ _deleteOgrFeature(cogr_feature)
-+
-+ return fid
-+
-+
-+def _listlayers(path):
-+
-+ """Provides a list of the layers in an OGR data source.
-+ """
-+
-+ cdef void *cogr_ds
-+ cdef void *cogr_layer
-+ cdef char *path_c
-+ cdef char *name_c
-+
-+ # Open OGR data source.
-+ try:
-+ path_b = path.encode('utf-8')
-+ except UnicodeDecodeError:
-+ path_b = path
-+ path_c = path_b
-+ with cpl_errs:
-+ cogr_ds = ograpi.GDALOpenEx(path_c,
-+ ograpi.GDAL_OF_VECTOR | ograpi.GDAL_OF_READONLY,
-+ NULL,
-+ NULL,
-+ NULL)
-+# cogr_ds = ograpi.OGROpen(path_c, 0, NULL)
-+ if cogr_ds == NULL:
-+ raise ValueError("No data available at path '%s'" % path)
-+
-+ # Loop over the layers to get their names.
-+ layer_count = ograpi.GDALDatasetGetLayerCount(cogr_ds)
-+ layer_names = []
-+ for i in range(layer_count):
-+ cogr_layer = ograpi.GDALDatasetGetLayer(cogr_ds, i)
-+ name_c = ograpi.OGR_L_GetName(cogr_layer)
-+ name_b = name_c
-+ layer_names.append(name_b.decode('utf-8'))
-+
-+ # Close up data source.
-+ if cogr_ds is not NULL:
-+ ograpi.GDALClose(cogr_ds)
-+ cogr_ds = NULL
-+
-+ return layer_names
-+
-+def buffer_to_virtual_file(bytesbuf):
-+ """Maps a bytes buffer to a virtual file.
-+ """
-+ vsi_filename = os.path.join('/vsimem', uuid.uuid4().hex)
-+ vsi_cfilename = vsi_filename if not isinstance(vsi_filename, string_types) else vsi_filename.encode('utf-8')
-+
-+ vsi_handle = ograpi.VSIFileFromMemBuffer(vsi_cfilename, bytesbuf, len(bytesbuf), 0)
-+ if vsi_handle == NULL:
-+ raise OSError('failed to map buffer to file')
-+ if ograpi.VSIFCloseL(vsi_handle) != 0:
-+ raise OSError('failed to close mapped file handle')
-+
-+ return vsi_filename
-+
-+def remove_virtual_file(vsi_filename):
-+ vsi_cfilename = vsi_filename if not isinstance(vsi_filename, string_types) else vsi_filename.encode('utf-8')
-+ return ograpi.VSIUnlink(vsi_cfilename)
-+
-+
---- a/setup.py
-+++ b/setup.py
-@@ -66,17 +66,34 @@ with open('CREDITS.txt', **open_kwds) as
- with open('CHANGES.txt', **open_kwds) as f:
- changes = f.read()
-
-+
-+def copy_gdalapi(gdalversion):
-+ if gdalversion[0] == u'1':
-+ log.info("Building Fiona for gdal 1.x: {}".format(gdal_output[3]))
-+ shutil.copy('fiona/ogrext1.pyx', 'fiona/ogrext.pyx')
-+ shutil.copy('fiona/ograpi1.pxd', 'fiona/ograpi.pxd')
-+ else:
-+ log.info("Building Fiona for gdal 2.x: {}".format(gdal_output[3]))
-+ shutil.copy('fiona/ogrext2.pyx', 'fiona/ogrext.pyx')
-+ shutil.copy('fiona/ograpi2.pxd', 'fiona/ograpi.pxd')
-+
-+if '--gdalversion' in sys.argv:
-+ index = sys.argv.index('--gdalversion')
-+ sys.argv.pop(index)
-+ gdalversion = sys.argv.pop(index)
-+ copy_gdalapi(gdalversion)
-+
- # By default we'll try to get options via gdal-config. On systems without,
- # options will need to be set in setup.cfg or on the setup command line.
- include_dirs = []
- library_dirs = []
- libraries = []
- extra_link_args = []
--gdal_output = [None]*3
-+gdal_output = [None] * 4
-
- try:
- gdal_config = os.environ.get('GDAL_CONFIG', 'gdal-config')
-- for i, flag in enumerate(("--cflags", "--libs", "--datadir")):
-+ for i, flag in enumerate(("--cflags", "--libs", "--datadir", "--version")):
- gdal_output[i] = check_output([gdal_config, flag]).strip()
-
- for item in gdal_output[0].split():
-@@ -91,6 +108,8 @@ try:
- # e.g. -framework GDAL
- extra_link_args.append(item)
-
-+ copy_gdalapi(gdal_output[3])
-+
- except Exception as e:
- if os.name == "nt":
- log.info(("Building on Windows requires extra options to setup.py to locate needed GDAL files.\n"
-@@ -131,13 +150,14 @@ ext_options = dict(
- extra_link_args=extra_link_args)
-
- # When building from a repo, Cython is required.
--if os.path.exists("MANIFEST.in"):
-+if os.path.exists("MANIFEST.in") and "clean" not in sys.argv:
- log.info("MANIFEST.in found, presume a repo, cythonizing...")
- if not cythonize:
- log.critical(
- "Cython.Build.cythonize not found. "
- "Cython is required to build from a repo.")
- sys.exit(1)
-+
- ext_modules = cythonize([
- Extension('fiona._geometry', ['fiona/_geometry.pyx'], **ext_options),
- Extension('fiona._transform', ['fiona/_transform.pyx'], **ext_options),
-@@ -166,8 +186,8 @@ setup_args = dict(
- metadata_version='1.2',
- name='Fiona',
- version=version,
-- requires_python = '>=2.6',
-- requires_external = 'GDAL (>=1.8)',
-+ requires_python='>=2.6',
-+ requires_external='GDAL (>=1.8)',
- description="Fiona reads and writes spatial data files",
- license='BSD',
- keywords='gis vector feature data',
---- a/requirements.txt
-+++ b/requirements.txt
-@@ -2,3 +2,4 @@ argparse
- cligj
- six
- ordereddict
-+munch
---- /dev/null
-+++ b/tests/test_bigint.py
-@@ -0,0 +1,69 @@
-+import fiona
-+import os
-+import shutil
-+import tempfile
-+import unittest
-+from fiona.ogrext import calc_gdal_version_num, get_gdal_version_num
-+
-+"""
-+
-+OGR 54bit handling: https://trac.osgeo.org/gdal/wiki/rfc31_ogr_64
-+
-+Shapefile: OFTInteger fields are created by default with a width of 9
-+characters, so to be unambiguously read as OFTInteger (and if specifying
-+integer that require 10 or 11 characters. the field is dynamically extended
-+like managed since a few versions). OFTInteger64 fields are created by default
-+with a width of 18 digits, so to be unambiguously read as OFTInteger64, and
-+extented to 19 or 20 if needed. Integer fields of width between 10 and 18
-+will be read as OFTInteger64. Above they will be treated as OFTReal. In
-+previous GDAL versions, Integer fields were created with a default with of 10,
-+and thus will be now read as OFTInteger64. An open option, DETECT_TYPE=YES, can
-+be specified so as OGR does a full scan of the DBF file to see if integer
-+fields of size 10 or 11 hold 32 bit or 64 bit values and adjust the type
-+accordingly (and same for integer fields of size 19 or 20, in case of overflow
-+of 64 bit integer, OFTReal is chosen)
-+"""
-+class TestBigInt(unittest.TestCase):
-+
-+ def setUp(self):
-+ self.tempdir = tempfile.mkdtemp()
-+
-+ def tearDown(self):
-+ shutil.rmtree(self.tempdir)
-+
-+ def testCreateBigIntSchema(self):
-+ name = os.path.join(self.tempdir, 'output1.shp')
-+
-+ a_bigint = 10 ** 18 - 1
-+ fieldname = 'abigint'
-+
-+ kwargs = {
-+ 'driver': 'ESRI Shapefile',
-+ 'crs': 'EPSG:4326',
-+ 'schema': {
-+ 'geometry': 'Point',
-+ 'properties': [(fieldname, 'int:10')]}}
-+ if get_gdal_version_num() < calc_gdal_version_num(2, 0, 0):
-+ with self.assertRaises(OverflowError):
-+ with fiona.open(name, 'w', **kwargs) as dst:
-+ rec = {}
-+ rec['geometry'] = {'type': 'Point', 'coordinates': (0, 0)}
-+ rec['properties'] = {fieldname: a_bigint}
-+ dst.write(rec)
-+ else:
-+
-+ with fiona.open(name, 'w', **kwargs) as dst:
-+ rec = {}
-+ rec['geometry'] = {'type': 'Point', 'coordinates': (0, 0)}
-+ rec['properties'] = {fieldname: a_bigint}
-+ dst.write(rec)
-+
-+ with fiona.open(name) as src:
-+ if get_gdal_version_num() >= calc_gdal_version_num(2, 0, 0):
-+ first = next(src)
-+ self.assertEqual(first['properties'][fieldname], a_bigint)
-+
-+
-+if __name__ == "__main__":
-+ # import sys;sys.argv = ['', 'Test.testName']
-+ unittest.main()
---- a/tests/test_props.py
-+++ b/tests/test_props.py
-@@ -22,8 +22,8 @@ def test_width_other():
- def test_types():
- assert prop_type('str:254') == text_type
- assert prop_type('str') == text_type
-- assert prop_type('int') == type(0)
-- assert prop_type('float') == type(0.0)
-+ assert isinstance(0, prop_type('int'))
-+ assert isinstance(0.0, prop_type('float'))
- assert prop_type('date') == FionaDateType
-
-
---- /dev/null
-+++ b/.gitignore
-@@ -0,0 +1,69 @@
-+# Byte-compiled / optimized / DLL files
-+__pycache__/
-+*.py[cod]
-+
-+# C extensions
-+*.so
-+
-+# Distribution / packaging
-+.Python
-+env/
-+build/
-+develop-eggs/
-+dist/
-+downloads/
-+eggs/
-+.eggs/
-+lib/
-+lib64/
-+parts/
-+sdist/
-+var/
-+*.egg-info/
-+.installed.cfg
-+*.egg
-+
-+# PyInstaller
-+# Usually these files are written by a python script from a template
-+# before PyInstaller builds the exe, so as to inject date/other infos into it.
-+*.manifest
-+*.spec
-+
-+# Installer logs
-+pip-log.txt
-+pip-delete-this-directory.txt
-+
-+# Unit test / coverage reports
-+htmlcov/
-+.tox/
-+.coverage
-+.coverage.*
-+.cache
-+nosetests.xml
-+coverage.xml
-+*,cover
-+
-+# Translations
-+*.mo
-+*.pot
-+
-+# Django stuff:
-+*.log
-+
-+# Sphinx documentation
-+docs/_build/
-+
-+# PyBuilder
-+target/
-+
-+# IDE's etc.
-+.idea/
-+venv/
-+venv2/
-+
-+#fiona
-+fiona/ogrext.c
-+fiona/_drivers.c
-+fiona/_err.c
-+fiona/_geometry.c
-+fiona/_transform.cpp
---- a/README.rst
-+++ b/README.rst
-@@ -236,7 +236,7 @@ gdal``).
- Python Requirements
- -------------------
-
--Fiona depends on the modules ``six``, ``cligj``, ``argparse``, and
-+Fiona depends on the modules ``six``, ``cligj``, ``future``, ``munch``, ``argparse``, and
- ``ordereddict`` (the two latter modules are standard in Python 2.7+). Pip will
- fetch these requirements for you, but users installing Fiona from a Windows
- installer must get them separately.
-@@ -314,7 +314,7 @@ locations on your system (via your syste
- If you have a non-standard environment, you'll need to specify the include and
- lib dirs and GDAL library on the command line::
-
-- (fiona_env)$ python setup.py build_ext -I/path/to/gdal/include -L/path/to/gdal/lib -lgdal develop
-+ (fiona_env)$ python setup.py build_ext -I/path/to/gdal/include -L/path/to/gdal/lib -lgdal --gdalversion 2.0.1 develop
- (fiona_env)$ nosetests
-
- .. _OGR: http://www.gdal.org/ogr
---- a/requirements-dev.txt
-+++ b/requirements-dev.txt
-@@ -1,3 +1,4 @@
-+-r requirements.txt
- cython>=0.21.2
- nose
- pytest
diff --git a/debian/patches/0004-Just-use-int-as-a-plain-old-builtin.patch b/debian/patches/0004-Just-use-int-as-a-plain-old-builtin.patch
deleted file mode 100644
index 2b74377..0000000
--- a/debian/patches/0004-Just-use-int-as-a-plain-old-builtin.patch
+++ /dev/null
@@ -1,36 +0,0 @@
-Origin: https://github.com/Toblerity/Fiona/commit/805bb6224df389d493cee5b933a65f5b9e4026c9
-From c1b7189bfd5f1613eea017e474034a6a5f56827a Mon Sep 17 00:00:00 2001
-From: Sean Gillies <sean at mapbox.com>
-Date: Tue, 27 Oct 2015 13:04:39 -0600
-Subject: [PATCH] Just use int as a plain old builtin
-
----
- README.rst | 2 +-
- fiona/ogrext2.pyx | 5 -----
- 2 files changed, 1 insertion(+), 6 deletions(-)
-
---- a/README.rst
-+++ b/README.rst
-@@ -236,7 +236,7 @@ gdal``).
- Python Requirements
- -------------------
-
--Fiona depends on the modules ``six``, ``cligj``, ``future``, ``munch``, ``argparse``, and
-+Fiona depends on the modules ``six``, ``cligj``, ``munch``, ``argparse``, and
- ``ordereddict`` (the two latter modules are standard in Python 2.7+). Pip will
- fetch these requirements for you, but users installing Fiona from a Windows
- installer must get them separately.
---- a/fiona/ogrext2.pyx
-+++ b/fiona/ogrext2.pyx
-@@ -10,11 +10,6 @@ import warnings
- import math
- import uuid
-
--if sys.version_info > (3,):
-- from builtins import int
--else:
-- from __builtin__ import int
--
- from six import integer_types, string_types, text_type
-
- from fiona cimport ograpi
diff --git a/debian/patches/0005-Initial-attempt-at-fiona.remove-for-deleting-data-sources.patch b/debian/patches/0005-Initial-attempt-at-fiona.remove-for-deleting-data-sources.patch
deleted file mode 100644
index cae6f00..0000000
--- a/debian/patches/0005-Initial-attempt-at-fiona.remove-for-deleting-data-sources.patch
+++ /dev/null
@@ -1,246 +0,0 @@
-From d8fcdeb95e10de9a1c8a6d2fbdcd5b8e861ae725 Mon Sep 17 00:00:00 2001
-From: Joshua Arnott <josh at snorfalorpagus.net>
-Date: Tue, 27 Oct 2015 23:40:38 +0000
-Subject: [PATCH 1/6] Initial attempt at fiona.remove from deleting data
- sources
-
----
- fiona/__init__.py | 12 +++++++++++-
- fiona/ogrext1.pyx | 18 ++++++++++++++++++
- 2 files changed, 29 insertions(+), 1 deletion(-)
-
---- a/fiona/__init__.py
-+++ b/fiona/__init__.py
-@@ -69,7 +69,7 @@ from six import string_types
- from fiona.collection import Collection, BytesCollection, vsi_path
- from fiona._drivers import driver_count, GDALEnv, supported_drivers
- from fiona.odict import OrderedDict
--from fiona.ogrext import _bounds, _listlayers, FIELD_TYPES_MAP
-+from fiona.ogrext import _bounds, _listlayers, FIELD_TYPES_MAP, _remove
- from fiona.ogrext import (
- calc_gdal_version_num, get_gdal_version_num, get_gdal_release_name)
- import warnings
-@@ -191,6 +191,33 @@ def open(
- collection = open
-
-
-+def remove(path_or_collection, driver=None):
-+ """Deletes an OGR data source
-+
-+ The required ``path`` argument may be an absolute or relative file path.
-+ Alternatively, a Collection can be passed instead in which case the path
-+ and driver are automatically determined. Otherwise the ``driver`` argument
-+ must be specified.
-+
-+ Raises a ``RuntimeError`` if the data source cannot be deleted.
-+
-+ Example usage:
-+
-+ fiona.remove('test.shp', 'ESRI Shapefile')
-+
-+ """
-+ if isinstance(path_or_collection, Collection):
-+ collection = path_or_collection
-+ path = collection.path
-+ driver = collection.driver
-+ collection.close()
-+ else:
-+ path = path_or_collection
-+ if driver is None:
-+ raise ValueError("The driver argument is required when removing a path")
-+ _remove(path, driver)
-+
-+
- def listlayers(path, vfs=None):
- """Returns a list of layer names in their index order.
-
---- a/fiona/ogrext1.pyx
-+++ b/fiona/ogrext1.pyx
-@@ -61,6 +61,10 @@ FIELD_TYPES_MAP = {
- 'datetime': FionaDateTimeType
- }
-
-+# OGR Driver capability
-+ODrCCreateDataSource = b"CreateDataSource"
-+ODrCDeleteDataSource = b"DeleteDataSource"
-+
- # OGR Layer capability
- OLC_RANDOMREAD = b"RandomRead"
- OLC_SEQUENTIALWRITE = b"SequentialWrite"
-@@ -1173,6 +1177,27 @@ cdef class KeysIterator(Iterator):
- return fid
-
-
-+def _remove(path, driver=None):
-+ """Deletes an OGR data source
-+ """
-+ cdef void *cogr_driver
-+ cdef int result
-+
-+ if driver is None:
-+ driver = 'ESRI Shapefile'
-+
-+ cogr_driver = ograpi.OGRGetDriverByName(driver.encode('utf-8'))
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+
-+ if not ograpi.OGR_Dr_TestCapability(cogr_driver, ODrCDeleteDataSource):
-+ raise RuntimeError("Driver does not support dataset removal operation")
-+
-+ result = ograpi.OGR_Dr_DeleteDataSource(cogr_driver, path.encode('utf-8'))
-+ if result != OGRERR_NONE:
-+ raise RuntimeError("Failed to remove data source {}".format(path))
-+
-+
- def _listlayers(path):
-
- """Provides a list of the layers in an OGR data source.
---- /dev/null
-+++ b/tests/test_remove.py
-@@ -0,0 +1,77 @@
-+import logging
-+import sys
-+import os
-+
-+import tempfile
-+import pytest
-+
-+import fiona
-+
-+
-+logging.basicConfig(stream=sys.stderr, level=logging.DEBUG)
-+
-+
-+def create_sample_data(filename, driver):
-+ meta = {
-+ 'driver': driver,
-+ 'schema': {
-+ 'geometry': 'Point',
-+ 'properties': {}
-+ }
-+ }
-+ with fiona.open(filename, 'w', **meta) as dst:
-+ dst.write({
-+ 'geometry': {
-+ 'type': 'Point',
-+ 'coordinates': (0, 0),
-+ },
-+ 'properties': {},
-+ })
-+ assert(os.path.exists(filename))
-+
-+
-+def test_remove(tmpdir=None):
-+ if tmpdir is None:
-+ tmpdir = tempfile.mkdtemp()
-+ filename_shp = os.path.join(tmpdir, 'test.shp')
-+
-+ create_sample_data(filename_shp, driver='ESRI Shapefile')
-+ fiona.remove(filename_shp, driver='ESRI Shapefile')
-+ assert(not os.path.exists(filename_shp))
-+
-+ with pytest.raises(RuntimeError):
-+ fiona.remove(filename_shp, driver='ESRI Shapefile')
-+
-+def test_remove_driver(tmpdir=None):
-+ if tmpdir is None:
-+ tmpdir = tempfile.mkdtemp()
-+ filename_shp = os.path.join(tmpdir, 'test.shp')
-+ filename_json = os.path.join(tmpdir, 'test.json')
-+
-+ create_sample_data(filename_shp, driver='ESRI Shapefile')
-+ create_sample_data(filename_json, driver='GeoJSON')
-+ fiona.remove(filename_json, driver='GeoJSON')
-+ assert(not os.path.exists(filename_json))
-+ assert(os.path.exists(filename_shp))
-+
-+def test_remove_collection(tmpdir=None):
-+ if tmpdir is None:
-+ tmpdir = tempfile.mkdtemp()
-+ filename_shp = os.path.join(tmpdir, 'test.shp')
-+
-+ create_sample_data(filename_shp, driver='ESRI Shapefile')
-+ collection = fiona.open(filename_shp, 'r')
-+ fiona.remove(collection)
-+ assert(not os.path.exists(filename_shp))
-+
-+def test_remove_path_without_driver(tmpdir=None):
-+ if tmpdir is None:
-+ tmpdir = tempfile.mkdtemp()
-+ filename_shp = os.path.join(tmpdir, 'test.shp')
-+
-+ create_sample_data(filename_shp, driver='ESRI Shapefile')
-+
-+ with pytest.raises(Exception):
-+ fiona.remove(filename_shp)
-+
-+ assert(os.path.exists(filename_shp))
---- a/fiona/ogrext2.pyx
-+++ b/fiona/ogrext2.pyx
-@@ -64,6 +64,10 @@ FIELD_TYPES_MAP = {
- 'datetime': FionaDateTimeType
- }
-
-+# OGR Driver capability
-+ODrCCreateDataSource = b"CreateDataSource"
-+ODrCDeleteDataSource = b"DeleteDataSource"
-+
- # OGR Layer capability
- OLC_RANDOMREAD = b"RandomRead"
- OLC_SEQUENTIALWRITE = b"SequentialWrite"
-@@ -1244,6 +1248,27 @@ cdef class KeysIterator(Iterator):
- return fid
-
-
-+def _remove(path, driver=None):
-+ """Deletes an OGR data source
-+ """
-+ cdef void *cogr_driver
-+ cdef int result
-+
-+ if driver is None:
-+ driver = 'ESRI Shapefile'
-+
-+ cogr_driver = ograpi.OGRGetDriverByName(driver.encode('utf-8'))
-+ if cogr_driver == NULL:
-+ raise ValueError("Null driver")
-+
-+ if not ograpi.OGR_Dr_TestCapability(cogr_driver, ODrCDeleteDataSource):
-+ raise RuntimeError("Driver does not support dataset removal operation")
-+
-+ result = ograpi.GDALDeleteDataset(cogr_driver, path.encode('utf-8'))
-+ if result != OGRERR_NONE:
-+ raise RuntimeError("Failed to remove data source {}".format(path))
-+
-+
- def _listlayers(path):
-
- """Provides a list of the layers in an OGR data source.
---- a/fiona/ograpi2.pxd
-+++ b/fiona/ograpi2.pxd
-@@ -36,6 +36,7 @@ cdef extern from "gdal.h":
- void GDALFlushCache(void * hDS)
- char * GDALGetDriverShortName(void * hDriver)
- char * GDALGetDatasetDriver (void * hDataset)
-+ int GDALDeleteDataset(void * hDriver, const char * pszFilename)
-
-
- ctypedef enum GDALDataType:
-@@ -110,6 +111,7 @@ cdef extern from "ogr_api.h":
- void * OGR_Dr_CreateDataSource (void *driver, const char *path, char **options)
- int OGR_Dr_DeleteDataSource (void *driver, char *)
- void * OGR_Dr_Open (void *driver, const char *path, int bupdate)
-+ int OGR_Dr_TestCapability (void *driver, const char *)
- void * OGR_F_Create (void *featuredefn)
- void OGR_F_Destroy (void *feature)
- long OGR_F_GetFID (void *feature)
---- a/fiona/ograpi1.pxd
-+++ b/fiona/ograpi1.pxd
-@@ -62,6 +62,7 @@ cdef extern from "ogr_api.h":
- void * OGR_Dr_CreateDataSource (void *driver, const char *path, char **options)
- int OGR_Dr_DeleteDataSource (void *driver, char *)
- void * OGR_Dr_Open (void *driver, const char *path, int bupdate)
-+ int OGR_Dr_TestCapability (void *driver, const char *)
- int OGR_DS_DeleteLayer (void *datasource, int n)
- void * OGR_DS_CreateLayer (void *datasource, char *name, void *crs, int geomType, char **options)
- void * OGR_DS_ExecuteSQL (void *datasource, char *name, void *filter, char *dialext)
diff --git a/debian/patches/0006-Remove-unknown-distribution-options.patch b/debian/patches/0006-Remove-unknown-distribution-options.patch
index 75848fd..fd1a019 100644
--- a/debian/patches/0006-Remove-unknown-distribution-options.patch
+++ b/debian/patches/0006-Remove-unknown-distribution-options.patch
@@ -6,7 +6,7 @@ Author: Bas Couwenberg <sebastic at debian.org>
--- a/setup.py
+++ b/setup.py
-@@ -183,11 +183,8 @@ if sys.version_info < (2, 7):
+@@ -180,11 +180,8 @@ if sys.version_info < (2, 7):
requirements.append('ordereddict')
setup_args = dict(
diff --git a/debian/patches/0007-clean.patch b/debian/patches/0007-clean.patch
deleted file mode 100644
index e7548ad..0000000
--- a/debian/patches/0007-clean.patch
+++ /dev/null
@@ -1,123 +0,0 @@
-Description: Don't copy gdalapi files in clean target.
-Author: Bas Couwenberg <sebastic at debian.org>
-Forwarded: https://github.com/Toblerity/Fiona/pull/322
-Applied-Upstream: https://github.com/Toblerity/Fiona/commit/8f3d471e510bafc3d653387675d1e7999f5c71e7
-
---- a/setup.py
-+++ b/setup.py
-@@ -77,7 +77,7 @@ def copy_gdalapi(gdalversion):
- shutil.copy('fiona/ogrext2.pyx', 'fiona/ogrext.pyx')
- shutil.copy('fiona/ograpi2.pxd', 'fiona/ograpi.pxd')
-
--if '--gdalversion' in sys.argv:
-+if '--gdalversion' in sys.argv and "clean" not in sys.argv:
- index = sys.argv.index('--gdalversion')
- sys.argv.pop(index)
- gdalversion = sys.argv.pop(index)
-@@ -91,57 +91,58 @@ libraries = []
- extra_link_args = []
- gdal_output = [None] * 4
-
--try:
-- gdal_config = os.environ.get('GDAL_CONFIG', 'gdal-config')
-- for i, flag in enumerate(("--cflags", "--libs", "--datadir", "--version")):
-- gdal_output[i] = check_output([gdal_config, flag]).strip()
--
-- for item in gdal_output[0].split():
-- if item.startswith("-I"):
-- include_dirs.extend(item[2:].split(":"))
-- for item in gdal_output[1].split():
-- if item.startswith("-L"):
-- library_dirs.extend(item[2:].split(":"))
-- elif item.startswith("-l"):
-- libraries.append(item[2:])
-+if "clean" not in sys.argv:
-+ try:
-+ gdal_config = os.environ.get('GDAL_CONFIG', 'gdal-config')
-+ for i, flag in enumerate(("--cflags", "--libs", "--datadir", "--version")):
-+ gdal_output[i] = check_output([gdal_config, flag]).strip()
-+
-+ for item in gdal_output[0].split():
-+ if item.startswith("-I"):
-+ include_dirs.extend(item[2:].split(":"))
-+ for item in gdal_output[1].split():
-+ if item.startswith("-L"):
-+ library_dirs.extend(item[2:].split(":"))
-+ elif item.startswith("-l"):
-+ libraries.append(item[2:])
-+ else:
-+ # e.g. -framework GDAL
-+ extra_link_args.append(item)
-+
-+ copy_gdalapi(gdal_output[3])
-+
-+ except Exception as e:
-+ if os.name == "nt":
-+ log.info(("Building on Windows requires extra options to setup.py to locate needed GDAL files.\n"
-+ "More information is available in the README."))
- else:
-- # e.g. -framework GDAL
-- extra_link_args.append(item)
-+ log.warning("Failed to get options via gdal-config: %s", str(e))
-
-- copy_gdalapi(gdal_output[3])
--
--except Exception as e:
-- if os.name == "nt":
-- log.info(("Building on Windows requires extra options to setup.py to locate needed GDAL files.\n"
-- "More information is available in the README."))
-- else:
-- log.warning("Failed to get options via gdal-config: %s", str(e))
--
-- # Conditionally copy the GDAL data. To be used in conjunction with
-- # the bdist_wheel command to make self-contained binary wheels.
-+ # Conditionally copy the GDAL data. To be used in conjunction with
-+ # the bdist_wheel command to make self-contained binary wheels.
-+ if os.environ.get('PACKAGE_DATA'):
-+ try:
-+ shutil.rmtree('fiona/gdal_data')
-+ except OSError:
-+ pass
-+ shutil.copytree(datadir, 'fiona/gdal_data')
- if os.environ.get('PACKAGE_DATA'):
-- try:
-- shutil.rmtree('fiona/gdal_data')
-- except OSError:
-- pass
-- shutil.copytree(datadir, 'fiona/gdal_data')
--if os.environ.get('PACKAGE_DATA'):
-- destdir = 'fiona/gdal_data'
-- if gdal_output[2]:
-- log.info("Copying gdal data from %s" % gdal_output[2])
-- copy_data_tree(gdal_output[2], destdir)
-- else:
-- # check to see if GDAL_DATA is defined
-- gdal_data = os.environ.get('GDAL_DATA', None)
-- if gdal_data:
-- log.info("Copying gdal data from %s" % gdal_data)
-- copy_data_tree(gdal_data, destdir)
--
-- # Conditionally copy PROJ.4 data.
-- projdatadir = os.environ.get('PROJ_LIB', '/usr/local/share/proj')
-- if os.path.exists(projdatadir):
-- log.info("Copying proj data from %s" % projdatadir)
-- copy_data_tree(projdatadir, 'fiona/proj_data')
-+ destdir = 'fiona/gdal_data'
-+ if gdal_output[2]:
-+ log.info("Copying gdal data from %s" % gdal_output[2])
-+ copy_data_tree(gdal_output[2], destdir)
-+ else:
-+ # check to see if GDAL_DATA is defined
-+ gdal_data = os.environ.get('GDAL_DATA', None)
-+ if gdal_data:
-+ log.info("Copying gdal data from %s" % gdal_data)
-+ copy_data_tree(gdal_data, destdir)
-+
-+ # Conditionally copy PROJ.4 data.
-+ projdatadir = os.environ.get('PROJ_LIB', '/usr/local/share/proj')
-+ if os.path.exists(projdatadir):
-+ log.info("Copying proj data from %s" % projdatadir)
-+ copy_data_tree(projdatadir, 'fiona/proj_data')
-
- ext_options = dict(
- include_dirs=include_dirs,
diff --git a/debian/patches/0008-Disable-GDAL-2-ImportError.patch b/debian/patches/0008-Disable-GDAL-2-ImportError.patch
deleted file mode 100644
index 4d6aec6..0000000
--- a/debian/patches/0008-Disable-GDAL-2-ImportError.patch
+++ /dev/null
@@ -1,20 +0,0 @@
-Description: Disable ImportError for GDAL 2.x.
- GDAL 2.x changes backported from Fiona 1.7.
-Author: Bas Couwenberg <sebastic at debian.org>
-Forwarded: not-needed
-
---- a/fiona/__init__.py
-+++ b/fiona/__init__.py
-@@ -84,12 +84,6 @@ __all__ = ['bounds', 'listlayers', 'open
- __version__ = "1.6.4"
- __gdal_version__ = get_gdal_release_name().decode('utf-8')
-
--# Warn user that they use fiona 1.x with gdal 2.0
--if get_gdal_version_num() >= calc_gdal_version_num(2, 0, 0):
-- raise ImportError(
-- "Fiona {0} is only compatible with GDAL 1.x (installed: {1})".format(
-- __version__, __gdal_version__))
--
- log = logging.getLogger('Fiona')
- class NullHandler(logging.Handler):
- def emit(self, record):
diff --git a/debian/patches/series b/debian/patches/series
index 3b6d427..780dd7b 100644
--- a/debian/patches/series
+++ b/debian/patches/series
@@ -1,8 +1,3 @@
0001-Rename-fio-command-to-fiona-to-avoid-name-clash.patch
0002-Remove-outside-reference-possible-privacy-breach.patch
-0003-GDAL-2.0.patch
-0004-Just-use-int-as-a-plain-old-builtin.patch
-0005-Initial-attempt-at-fiona.remove-for-deleting-data-sources.patch
0006-Remove-unknown-distribution-options.patch
-0007-clean.patch
-0008-Disable-GDAL-2-ImportError.patch
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-grass/fiona.git
More information about the Pkg-grass-devel
mailing list