From f60c843199adeca37e627b19b49f38104fff0673 Mon Sep 17 00:00:00 2001 From: Jared Erickson Date: Wed, 3 Jun 2020 16:27:12 -0700 Subject: [PATCH] Add Geobuf Workspace --- geoscript/util/data.py | 19 +++++++++++++++++++ geoscript/workspace/__init__.py | 1 + geoscript/workspace/geobuf.py | 24 ++++++++++++++++++++++++ geoscript/workspace/workspace.py | 7 +++++-- pom.xml | 5 +++++ tests/workspace/test_geobuf.py | 13 +++++++++++++ 6 files changed, 67 insertions(+), 2 deletions(-) create mode 100644 geoscript/workspace/geobuf.py create mode 100644 tests/workspace/test_geobuf.py diff --git a/geoscript/util/data.py b/geoscript/util/data.py index acf1cf6..242ba9c 100644 --- a/geoscript/util/data.py +++ b/geoscript/util/data.py @@ -1,4 +1,6 @@ from org.geotools.data.collection import ListFeatureCollection +from org.geotools.feature.simple import SimpleFeatureBuilder + def readFeatures(it, type, chunk): i = 0 features = ListFeatureCollection(type) @@ -7,3 +9,20 @@ def readFeatures(it, type, chunk): i = i+1 return features + +def readFeaturesWithChangedGeometry(it, sourceType, targetType, chunk): + i = 0 + features = ListFeatureCollection(targetType) + builder = SimpleFeatureBuilder(targetType) + while it.hasNext() and i < chunk: + f = it.next() + for x in range(0, f.getAttributeCount()): + name = f.getFeatureType().getDescriptor(x).getLocalName() + value = f.getAttribute(x) + if (name == sourceType.getGeometryDescriptor().getLocalName()): + name = targetType.getGeometryDescriptor().getLocalName() + builder.set(name, value) + features.add(builder.buildFeature(f.getID())) + i = i+1 + + return features \ No newline at end of file diff --git a/geoscript/workspace/__init__.py b/geoscript/workspace/__init__.py index 2b4a88e..e212c1b 100644 --- a/geoscript/workspace/__init__.py +++ b/geoscript/workspace/__init__.py @@ -17,4 +17,5 @@ def _import(mod, clas): Property = _import('property', 'Property') Oracle = _import('oracle', 'Oracle') GeoPackage = _import('geopackage', 'GeoPackage') +Geobuf = _import('geobuf', 'Geobuf') diff --git a/geoscript/workspace/geobuf.py b/geoscript/workspace/geobuf.py new file mode 100644 index 0000000..9e14b43 --- /dev/null +++ b/geoscript/workspace/geobuf.py @@ -0,0 +1,24 @@ +""" +the :mod:`workspace.property` module provides a workspace implemntation based on a directory of java style property files. +""" + +import os +from java import io, net +from geoscript import util +from geoscript.workspace import Workspace +from org.geotools.data.geobuf import GeobufDataStoreFactory + +class Geobuf(Workspace): + """ + A subclass of :class:`Workspace ` that provides layers that correspond to geobuf files in a directory. + + *dir* is the optional path as a ``str`` to a directory. If not specified it defaults to ``os.getcwd()``. + """ + + def __init__(self, dir=None, precision=6, dimension=2): + dir = dir or os.getcwd() + params = {'file': util.toFile(dir), 'precision': precision, 'dimension': dimension} + Workspace.__init__(self, GeobufDataStoreFactory(), params) + + def __repr__(self): + return 'Geobuf[%s]' % str(self._store.info.source.path) diff --git a/geoscript/workspace/workspace.py b/geoscript/workspace/workspace.py index c802e91..542e69c 100644 --- a/geoscript/workspace/workspace.py +++ b/geoscript/workspace/workspace.py @@ -5,7 +5,7 @@ from org.geotools.data import DataStore from geoscript.layer import Layer from geoscript.filter import Filter -from geoscript.util.data import readFeatures +from geoscript.util.data import readFeatures, readFeaturesWithChangedGeometry from geoscript import core, geom, feature class Workspace: @@ -168,7 +168,10 @@ def add(self, layer, name=None, chunk=1000): if features.isEmpty(): break - l._source.addFeatures(features) + if (l.schema.geom.name != layer.schema.geom.name): + l._source.addFeatures(readFeaturesWithChangedGeometry(features.features(), layer._source.getSchema(), l._source.getSchema(), chunk)) + else: + l._source.addFeatures(features) return l finally: diff --git a/pom.xml b/pom.xml index 71f4cda..ff1a5ad 100644 --- a/pom.xml +++ b/pom.xml @@ -160,6 +160,11 @@ gt-geopkg ${gt.version} + + org.geotools + gt-geobuf + ${gt.version} + org.python jython-standalone diff --git a/tests/workspace/test_geobuf.py b/tests/workspace/test_geobuf.py new file mode 100644 index 0000000..c2047b9 --- /dev/null +++ b/tests/workspace/test_geobuf.py @@ -0,0 +1,13 @@ +import os +import shutil +from tests.workspace.workspacetest import WorkspaceTest +from geoscript.workspace import Geobuf + +class GeobufWorkspace_Test(WorkspaceTest): + + def setUp(self): + self.path = 'work/geobufs' + if os.path.isdir(self.path): + shutil.rmtree(self.path) + os.mkdir(self.path) + self.ws = Geobuf(self.path)