Skip to content

Instantly share code, notes, and snippets.

@phargogh
Created February 5, 2020 03:13
Show Gist options
  • Save phargogh/f654a8de747544272f356fb34024dc87 to your computer and use it in GitHub Desktop.
Save phargogh/f654a8de747544272f356fb34024dc87 to your computer and use it in GitHub Desktop.
Create an aspatial geopackage table
In the latest version of watershed delineation, a single watershed
seed may be associated with many features of interest. For this reason,
we need to be able to associate the attributes of the features of interest
with each of the seeds derived from the features.
The GeoPackage driver (https://www.gdal.org/drv_geopackage.html) supports
'aspatial' tables in GDAL>2.0, and 'attribute' data types in GDAL>2.2.
The two prototypes needed are:
* How do we make an aspatial table in GDAL 2?
* How do we use the 'attribute' data type in GDAL 2.2?
Solution
--------
The way to specify which style of non-spatial table to use is to use the
ASPATIAL_VARIANT option. Tested against GDAL 2.2.4, the older one
(OGR_ASPATIAL) does what I expect, and the GDAL source code appears to treat
the two aspatial options (OGR_ASPATIAL, GPKG_ATTRIBUTES) as identical.
When a non-spatial layer is added, features are created as normal. The only
exception to this is that the features do not have a spatial reference or
geometry. They have fields as normal.
from osgeo import gdal
from osgeo import ogr
from osgeo import osr
SRS = osr.SpatialReference()
SRS.ImportFromEPSG(32631)
def make_vector(path):
driver = gdal.GetDriverByName('GPKG')
vector = driver.Create(path, 0, 0, 0, gdal.GDT_Unknown)
spatial_layer = vector.CreateLayer('spatial', SRS, ogr.wkbPoint)
# This snippet was taken from the gdal autotests. See
# https://github.com/OSGeo/gdal/blob/3dca475ef2334e2c1386718d03149428df774281/autotest/ogr/ogr_gpkg.py#L787
# ASPATIAL_VARIANT=OGR_ASPATIAL is present since GDAL 2.0
# ASPATIAL_VARIANT=GPKG_ATTRIBUTES is present since GDAL 2.2. I last tested
# this code against GDAL 2.2.4, and first-supported version (OGR_ASPATIAL)
# works as expected.
aspatial_layer= vector.CreateLayer('aspatial', geom_type=ogr.wkbNone,
options=['ASPATIAL_VARIANT=OGR_ASPATIAL'])
aspatial_layer.CreateField(
ogr.FieldDefn('intfield', ogr.OFTInteger))
feature = ogr.Feature(aspatial_layer.GetLayerDefn())
feature.SetField('intfield', 1)
aspatial_layer.CreateFeature(feature)
aspatial_layer = None
spatial_layer = None
vector = None
if __name__ == '__main__':
make_vector('test.gpkg')
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment