This is an automated email from the ASF dual-hosted git repository.
bchapuis pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/incubator-baremaps.git
The following commit(s) were added to refs/heads/main by this push:
new c3791173 Improve the transformation workflow (#620)
c3791173 is described below
commit c37911738bc14c30986e00d68a9d1edefc19666f
Author: Bertil Chapuis <[email protected]>
AuthorDate: Sun Apr 9 21:46:33 2023 +0200
Improve the transformation workflow (#620)
* Improve support for geometries in collections
* Fix index out of bounds exception
* Improve flatgeobuf serialization
* Import empty geometry instead of null
---
.../{GeometryDataType.java => WKBDataType.java} | 5 +-
.../type/geometry/CoordinateArrayDataType.java | 73 ++++++++
.../type/geometry/GeometryCollectionDataType.java | 110 ++++++++++++
.../collection/type/geometry/GeometryDataType.java | 197 +++++++++++++++++++++
.../type/geometry/LineStringDataType.java | 78 ++++++++
.../type/geometry/MultiLineStringDataType.java | 97 ++++++++++
.../type/geometry/MultiPointDataType.java | 77 ++++++++
.../type/geometry/MultiPolygonDataType.java | 95 ++++++++++
.../collection/type/geometry/PointDataType.java | 87 +++++++++
.../collection/type/geometry/PolygonDataType.java | 124 +++++++++++++
.../function/RelationGeometryBuilder.java | 1 +
.../openstreetmap/function/WayGeometryBuilder.java | 1 +
.../main/java/org/apache/baremaps/storage/Row.java | 2 +-
.../storage/flatgeobuf/FlatGeoBufStore.java | 8 +-
.../storage/flatgeobuf/FlatGeoBufTable.java | 53 +++---
.../flatgeobuf/internal/TableConversions.java | 4 +-
.../baremaps/workflow/tasks/EntityDataType.java | 4 +-
.../baremaps/collection/AppendOnlyBufferTest.java | 4 +-
.../baremaps/collection/type/DataTypeProvider.java | 145 +++++++++++++--
.../workflow.json | 6 +-
20 files changed, 1122 insertions(+), 49 deletions(-)
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/GeometryDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/WKBDataType.java
similarity index 91%
rename from
baremaps-core/src/main/java/org/apache/baremaps/collection/type/GeometryDataType.java
rename to
baremaps-core/src/main/java/org/apache/baremaps/collection/type/WKBDataType.java
index 395a74cf..4bf89729 100644
---
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/GeometryDataType.java
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/WKBDataType.java
@@ -19,12 +19,13 @@ import
org.apache.baremaps.openstreetmap.utils.GeometryUtils;
import org.locationtech.jts.geom.Geometry;
/** A {@link DataType} for reading and writing {@link Geometry} in {@link
ByteBuffer}s. */
-public class GeometryDataType implements DataType<Geometry> {
+public class WKBDataType implements DataType<Geometry> {
/** {@inheritDoc} */
@Override
public int size(Geometry value) {
- return Integer.BYTES + GeometryUtils.serialize(value).length;
+ byte[] bytes = GeometryUtils.serialize(value);
+ return Integer.BYTES + bytes.length;
}
/** {@inheritDoc} */
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/CoordinateArrayDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/CoordinateArrayDataType.java
new file mode 100644
index 00000000..1bc483c8
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/CoordinateArrayDataType.java
@@ -0,0 +1,73 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.Coordinate;
+
+/**
+ * A data type for {@link Coordinate} arrays.
+ */
+public class CoordinateArrayDataType implements DataType<Coordinate[]> {
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(Coordinate[] value) {
+ return Integer.BYTES + Double.BYTES * 2 * value.length;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return buffer.getInt(position);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, Coordinate[] value) {
+ buffer.putInt(position, size(value));
+ position += Integer.BYTES;
+ for (int i = 0; i < value.length; i++) {
+ Coordinate coordinate = value[i];
+ buffer.putDouble(position, coordinate.x);
+ position += Double.BYTES;
+ buffer.putDouble(position, coordinate.y);
+ position += Double.BYTES;
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public Coordinate[] read(ByteBuffer buffer, int position) {
+ int size = buffer.getInt(position);
+ int numPoints = (size - Integer.BYTES) / (Double.BYTES * 2);
+ position += Integer.BYTES;
+ Coordinate[] coordinates = new Coordinate[numPoints];
+ for (int i = 0; i < numPoints; i++) {
+ double x = buffer.getDouble(position);
+ double y = buffer.getDouble(position + Double.BYTES);
+ coordinates[i] = new Coordinate(x, y);
+ position += Double.BYTES * 2;
+ }
+ return coordinates;
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/GeometryCollectionDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/GeometryCollectionDataType.java
new file mode 100644
index 00000000..256c75e7
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/GeometryCollectionDataType.java
@@ -0,0 +1,110 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.Geometry;
+import org.locationtech.jts.geom.GeometryCollection;
+import org.locationtech.jts.geom.GeometryFactory;
+
+/**
+ * A data type for {@link GeometryCollection} objects.
+ */
+public class GeometryCollectionDataType implements
DataType<GeometryCollection> {
+
+ private final GeometryFactory geometryFactory;
+
+ private GeometryDataType geometryDataType;
+
+ /**
+ * Constructs a {@code GeometryCollectionDataType} with a default {@code
GeometryFactory}.
+ */
+ public GeometryCollectionDataType() {
+ this(new GeometryFactory(), new GeometryDataType());
+ }
+
+ /**
+ * Constructs a {@code GeometryCollectionDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory the geometry factory
+ */
+ public GeometryCollectionDataType(GeometryFactory geometryFactory) {
+ this(geometryFactory, new GeometryDataType());
+ }
+
+ /**
+ * Constructs a {@code GeometryCollectionDataType} with a specified {@code
GeometryFactory} and
+ * {@code GeometryDataType}.
+ *
+ * @param geometryFactory the geometry factory
+ * @param geometryDataType the geometry data type
+ */
+ public GeometryCollectionDataType(GeometryFactory geometryFactory,
+ GeometryDataType geometryDataType) {
+ this.geometryFactory = geometryFactory;
+ this.geometryDataType = geometryDataType;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(GeometryCollection value) {
+ int size = Integer.BYTES;
+ for (int i = 0; i < value.getNumGeometries(); i++) {
+ size += geometryDataType.size(value.getGeometryN(i));
+ }
+ return size;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return buffer.getInt(position);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, GeometryCollection value)
{
+ buffer.putInt(position, size(value));
+ position += Integer.BYTES;
+ for (int i = 0; i < value.getNumGeometries(); i++) {
+ var geometry = value.getGeometryN(i);
+ geometryDataType.write(buffer, position, geometry);
+ position += geometryDataType.size(buffer, position);
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public GeometryCollection read(ByteBuffer buffer, int position) {
+ var size = size(buffer, position);
+ var limit = position + size;
+ position += Integer.BYTES;
+ var geometries = new ArrayList<Geometry>();
+ while (position < limit) {
+ var geometry = geometryDataType.read(buffer, position);
+ geometries.add(geometry);
+ position += geometryDataType.size(geometry);
+ }
+ return
geometryFactory.createGeometryCollection(geometries.toArray(Geometry[]::new));
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/GeometryDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/GeometryDataType.java
new file mode 100644
index 00000000..376e82de
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/GeometryDataType.java
@@ -0,0 +1,197 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+
+import java.nio.ByteBuffer;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.*;
+
+/**
+ * A {@code DataType} for {@code MultiPolygon} objects.
+ */
+public class GeometryDataType implements DataType<Geometry> {
+
+ private final PointDataType pointDataType;
+
+ private final LineStringDataType lineStringDataType;
+
+ private final PolygonDataType polygonDataType;
+
+ private final MultiPointDataType multiPointDataType;
+
+ private final MultiLineStringDataType multiLineStringDataType;
+
+ private final MultiPolygonDataType multiPolygonDataType;
+
+ private final GeometryCollectionDataType geometryCollectionDataType;
+
+ /**
+ * Constructs a {@code GeometryDataType} with a default {@code
GeometryFactory}.
+ */
+ public GeometryDataType() {
+ this(new GeometryFactory());
+ }
+
+ /**
+ * Constructs a {@code GeometryDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory
+ */
+ public GeometryDataType(GeometryFactory geometryFactory) {
+ this.pointDataType = new PointDataType(geometryFactory);
+ this.lineStringDataType = new LineStringDataType(geometryFactory);
+ this.polygonDataType = new PolygonDataType(geometryFactory);
+ this.multiPointDataType = new MultiPointDataType(geometryFactory);
+ this.multiLineStringDataType = new
MultiLineStringDataType(geometryFactory);
+ this.multiPolygonDataType = new MultiPolygonDataType(geometryFactory);
+ this.geometryCollectionDataType = new
GeometryCollectionDataType(geometryFactory, this);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(Geometry value) {
+ var size = 0;
+
+ // Geometry type
+ size += Byte.BYTES;
+
+ // Size of the geometry
+ if (value instanceof Point point) {
+ size += pointDataType.size(point);
+ } else if (value instanceof LineString lineString) {
+ size += lineStringDataType.size(lineString);
+ } else if (value instanceof Polygon polygon) {
+ size += polygonDataType.size(polygon);
+ } else if (value instanceof MultiPoint multiPoint) {
+ size += multiPointDataType.size(multiPoint);
+ } else if (value instanceof MultiLineString multiLineString) {
+ size += multiLineStringDataType.size(multiLineString);
+ } else if (value instanceof MultiPolygon multiPolygon) {
+ size += multiPolygonDataType.size(multiPolygon);
+ } else if (value instanceof GeometryCollection geometryCollection) {
+ size += geometryCollectionDataType.size(geometryCollection);
+ } else {
+ throw new IllegalArgumentException("Unsupported geometry type: " +
value.getClass());
+ }
+
+ return size;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ var size = 0;
+
+ // Geometry type
+ var type = buffer.get(position);
+ size += Byte.BYTES;
+
+ // Size of the geometry
+ if (type == 1) {
+ size += pointDataType.size(buffer, position + Byte.BYTES);
+ } else if (type == 2) {
+ size += lineStringDataType.size(buffer, position + Byte.BYTES);
+ } else if (type == 3) {
+ size += polygonDataType.size(buffer, position + Byte.BYTES);
+ } else if (type == 4) {
+ size += multiPointDataType.size(buffer, position + Byte.BYTES);
+ } else if (type == 5) {
+ size += multiLineStringDataType.size(buffer, position + Byte.BYTES);
+ } else if (type == 6) {
+ size += multiPolygonDataType.size(buffer, position + Byte.BYTES);
+ } else if (type == 7) {
+ size += geometryCollectionDataType.size(buffer, position + Byte.BYTES);
+ } else {
+ throw new IllegalArgumentException("Unsupported geometry type: " + type);
+ }
+
+ return size;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, Geometry value) {
+ // Write the geometry
+ if (value == null) {
+ buffer.put(position, (byte) 0);
+ } else if (value instanceof Point point) {
+ buffer.put(position, (byte) 1);
+ position += Byte.BYTES;
+ pointDataType.write(buffer, position, point);
+ } else if (value instanceof LineString lineString) {
+ buffer.put(position, (byte) 2);
+ position += Byte.BYTES;
+ lineStringDataType.write(buffer, position, lineString);
+ } else if (value instanceof Polygon polygon) {
+ buffer.put(position, (byte) 3);
+ position += Byte.BYTES;
+ polygonDataType.write(buffer, position, polygon);
+ } else if (value instanceof MultiPoint multiPoint) {
+ buffer.put(position, (byte) 4);
+ position += Byte.BYTES;
+ multiPointDataType.write(buffer, position, multiPoint);
+ } else if (value instanceof MultiLineString multiLineString) {
+ buffer.put(position, (byte) 5);
+ position += Byte.BYTES;
+ multiLineStringDataType.write(buffer, position, multiLineString);
+ } else if (value instanceof MultiPolygon multiPolygon) {
+ buffer.put(position, (byte) 6);
+ position += Byte.BYTES;
+ multiPolygonDataType.write(buffer, position, multiPolygon);
+ } else if (value instanceof GeometryCollection geometryCollection) {
+ buffer.put(position, (byte) 7);
+ position += Byte.BYTES;
+ geometryCollectionDataType.write(buffer, position, geometryCollection);
+ } else {
+ throw new IllegalArgumentException("Unsupported geometry type: " +
value.getClass());
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public Geometry read(ByteBuffer buffer, int position) {
+ // Read the geometry type
+ var type = buffer.get(position);
+ position += Byte.BYTES;
+
+ // Read the geometry
+ if (type == 0) {
+ return null;
+ } else if (type == 1) {
+ return pointDataType.read(buffer, position);
+ } else if (type == 2) {
+ return lineStringDataType.read(buffer, position);
+ } else if (type == 3) {
+ return polygonDataType.read(buffer, position);
+ } else if (type == 4) {
+ return multiPointDataType.read(buffer, position);
+ } else if (type == 5) {
+ return multiLineStringDataType.read(buffer, position);
+ } else if (type == 6) {
+ return multiPolygonDataType.read(buffer, position);
+ } else if (type == 7) {
+ return geometryCollectionDataType.read(buffer, position);
+ } else {
+ throw new IllegalArgumentException("Unsupported geometry type: " + type);
+ }
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/LineStringDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/LineStringDataType.java
new file mode 100644
index 00000000..9e3f397b
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/LineStringDataType.java
@@ -0,0 +1,78 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.GeometryFactory;
+import org.locationtech.jts.geom.LineString;
+
+/**
+ * A data type for {@link LineString} objects.
+ */
+public class LineStringDataType implements DataType<LineString> {
+
+ private final GeometryFactory geometryFactory;
+
+ private final CoordinateArrayDataType coordinateArrayDataType;
+
+ /**
+ * Constructs a {@code LineStringDataType} with a default {@code
GeometryFactory}.
+ */
+ public LineStringDataType() {
+ this(new GeometryFactory());
+ }
+
+ /**
+ * Constructs a {@code LineStringDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory the geometry factory
+ */
+ public LineStringDataType(GeometryFactory geometryFactory) {
+ this.geometryFactory = geometryFactory;
+ this.coordinateArrayDataType = new CoordinateArrayDataType();
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(LineString value) {
+ return coordinateArrayDataType.size(value.getCoordinates());
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return coordinateArrayDataType.size(buffer, position);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, LineString value) {
+ coordinateArrayDataType.write(buffer, position, value.getCoordinates());
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public LineString read(ByteBuffer buffer, int position) {
+ var coordinates = coordinateArrayDataType.read(buffer, position);
+ return geometryFactory.createLineString(coordinates);
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiLineStringDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiLineStringDataType.java
new file mode 100644
index 00000000..f78e4f45
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiLineStringDataType.java
@@ -0,0 +1,97 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.GeometryFactory;
+import org.locationtech.jts.geom.LineString;
+import org.locationtech.jts.geom.MultiLineString;
+
+/**
+ * A data type for {@link MultiLineString} objects.
+ */
+public class MultiLineStringDataType implements DataType<MultiLineString> {
+
+ private final LineStringDataType lineStringDataType;
+
+ private final GeometryFactory geometryFactory;
+
+ /**
+ * Constructs a {@code MultiLineStringDataType} with a default {@code
GeometryFactory}.
+ */
+ public MultiLineStringDataType() {
+ this(new GeometryFactory());
+ }
+
+ /**
+ * Constructs a {@code MultiLineStringDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory the geometry factory
+ */
+ public MultiLineStringDataType(GeometryFactory geometryFactory) {
+ this.geometryFactory = geometryFactory;
+ this.lineStringDataType = new LineStringDataType(geometryFactory);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(MultiLineString value) {
+ int size = Integer.BYTES;
+ for (int i = 0; i < value.getNumGeometries(); i++) {
+ size += lineStringDataType.size((LineString) value.getGeometryN(i));
+ }
+ return size;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return buffer.getInt(position);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, MultiLineString value) {
+ buffer.putInt(position, size(value));
+ position += Integer.BYTES;
+ for (int i = 0; i < value.getNumGeometries(); i++) {
+ lineStringDataType.write(buffer, position, (LineString)
value.getGeometryN(i));
+ position += buffer.getInt(position);
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public MultiLineString read(ByteBuffer buffer, int position) {
+ var size = size(buffer, position);
+ var limit = position + size;
+ position += Integer.BYTES;
+ var lineStrings = new ArrayList<LineString>();
+ while (position < limit) {
+ var lineString = lineStringDataType.read(buffer, position);
+ lineStrings.add(lineString);
+ position += lineStringDataType.size(buffer, position);
+ }
+ return
geometryFactory.createMultiLineString(lineStrings.toArray(LineString[]::new));
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiPointDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiPointDataType.java
new file mode 100644
index 00000000..0e41c101
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiPointDataType.java
@@ -0,0 +1,77 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.GeometryFactory;
+import org.locationtech.jts.geom.MultiPoint;
+
+/**
+ * A data type for {@link MultiPoint} objects.
+ */
+public class MultiPointDataType implements DataType<MultiPoint> {
+
+ private final CoordinateArrayDataType coordinateArrayDataType = new
CoordinateArrayDataType();
+
+ private final GeometryFactory geometryFactory;
+
+ /**
+ * Constructs a {@code MultiPointDataType} with a default {@code
GeometryFactory}.
+ */
+ public MultiPointDataType() {
+ this(new GeometryFactory());
+ }
+
+ /**
+ * Constructs a {@code MultiPointDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory the geometry factory
+ */
+ public MultiPointDataType(GeometryFactory geometryFactory) {
+ this.geometryFactory = geometryFactory;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(MultiPoint value) {
+ return coordinateArrayDataType.size(value.getCoordinates());
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return coordinateArrayDataType.size(buffer, position);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, MultiPoint value) {
+ coordinateArrayDataType.write(buffer, position, value.getCoordinates());
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public MultiPoint read(ByteBuffer buffer, int position) {
+ var coordinates = coordinateArrayDataType.read(buffer, position);
+ return geometryFactory.createMultiPoint(coordinates);
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiPolygonDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiPolygonDataType.java
new file mode 100644
index 00000000..f8b84cdc
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/MultiPolygonDataType.java
@@ -0,0 +1,95 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.*;
+
+/**
+ * A data type for {@link GeometryCollection} objects.
+ */
+public class MultiPolygonDataType implements DataType<MultiPolygon> {
+
+ private final GeometryFactory geometryFactory;
+
+ private final PolygonDataType polygonDataType;
+
+ /**
+ * Constructs a {@code MultiPolygonDataType} with a default {@code
GeometryFactory}.
+ */
+ public MultiPolygonDataType() {
+ this(new GeometryFactory());
+ }
+
+ /**
+ * Constructs a {@code MultiPolygonDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory the geometry factory
+ */
+ public MultiPolygonDataType(GeometryFactory geometryFactory) {
+ this.geometryFactory = geometryFactory;
+ this.polygonDataType = new PolygonDataType(geometryFactory);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(MultiPolygon value) {
+ int size = Integer.BYTES;
+ for (int i = 0; i < value.getNumGeometries(); i++) {
+ size += polygonDataType.size((Polygon) value.getGeometryN(i));
+ }
+ return size;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return buffer.getInt(position);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, MultiPolygon value) {
+ buffer.putInt(position, size(value));
+ position += Integer.BYTES;
+ for (int i = 0; i < value.getNumGeometries(); i++) {
+ polygonDataType.write(buffer, position, (Polygon) value.getGeometryN(i));
+ position += buffer.getInt(position);
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public MultiPolygon read(ByteBuffer buffer, int position) {
+ var size = size(buffer, position);
+ var limit = position + size;
+ position += Integer.BYTES;
+ var polygons = new ArrayList<Polygon>();
+ while (position < limit) {
+ var polygon = polygonDataType.read(buffer, position);
+ polygons.add(polygon);
+ position += polygonDataType.size(buffer, position);
+ }
+ return
geometryFactory.createMultiPolygon(polygons.toArray(Polygon[]::new));
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/PointDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/PointDataType.java
new file mode 100644
index 00000000..3059340f
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/PointDataType.java
@@ -0,0 +1,87 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.Coordinate;
+import org.locationtech.jts.geom.GeometryFactory;
+import org.locationtech.jts.geom.Point;
+
+/**
+ * A data type for {@link Point} objects.
+ */
+public class PointDataType implements DataType<Point> {
+
+ private final GeometryFactory geometryFactory;
+
+ /**
+ * Constructs a {@code PointDataType} with a default {@code GeometryFactory}.
+ */
+ public PointDataType() {
+ this(new GeometryFactory());
+ }
+
+ /**
+ * Constructs a {@code PointDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory the geometry factory
+ */
+ public PointDataType(GeometryFactory geometryFactory) {
+ this.geometryFactory = geometryFactory;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(Point value) {
+ return Double.BYTES * 2;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return Double.BYTES * 2;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, Point value) {
+ if (value.isEmpty()) {
+ buffer.putDouble(position, Double.NaN);
+ buffer.putDouble(position + Double.BYTES, Double.NaN);
+ } else {
+ buffer.putDouble(position, value.getX());
+ buffer.putDouble(position + Double.BYTES, value.getY());
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public Point read(ByteBuffer buffer, int position) {
+ double x = buffer.getDouble(position);
+ double y = buffer.getDouble(position + Double.BYTES);
+ if (Double.isNaN(x) || Double.isNaN(y)) {
+ return geometryFactory.createPoint();
+ } else {
+ return geometryFactory.createPoint(new Coordinate(x, y));
+ }
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/PolygonDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/PolygonDataType.java
new file mode 100644
index 00000000..8497dc04
--- /dev/null
+++
b/baremaps-core/src/main/java/org/apache/baremaps/collection/type/geometry/PolygonDataType.java
@@ -0,0 +1,124 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
use this file except
+ * in compliance with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express
+ * or implied. See the License for the specific language governing permissions
and limitations under
+ * the License.
+ */
+
+package org.apache.baremaps.collection.type.geometry;
+
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+import org.apache.baremaps.collection.type.DataType;
+import org.locationtech.jts.geom.GeometryFactory;
+import org.locationtech.jts.geom.LineString;
+import org.locationtech.jts.geom.LinearRing;
+import org.locationtech.jts.geom.Polygon;
+
+/**
+ * A data type for {@link Polygon} objects.
+ */
+public class PolygonDataType implements DataType<Polygon> {
+
+ private final CoordinateArrayDataType coordinateArrayDataType = new
CoordinateArrayDataType();
+
+ private final GeometryFactory geometryFactory;
+
+ /**
+ * Constructs a {@code PolygonDataType} with a default {@code
GeometryFactory}.
+ */
+ public PolygonDataType() {
+ this(new GeometryFactory());
+ }
+
+ /**
+ * Constructs a {@code PolygonDataType} with a specified {@code
GeometryFactory}.
+ *
+ * @param geometryFactory the geometry factory
+ */
+ public PolygonDataType(GeometryFactory geometryFactory) {
+ this.geometryFactory = geometryFactory;
+ }
+
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(Polygon value) {
+ int size = Integer.BYTES;
+
+ // Add the size of the exterior ring
+ var exteriorRing = value.getExteriorRing();
+ size += coordinateArrayDataType.size(exteriorRing.getCoordinates());
+
+ // Add the size of the interior rings
+ for (int i = 0; i < value.getNumInteriorRing(); i++) {
+ var interiorRing = value.getInteriorRingN(i);
+ size += coordinateArrayDataType.size(interiorRing.getCoordinates());
+ }
+
+ return size;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public int size(ByteBuffer buffer, int position) {
+ return coordinateArrayDataType.size(buffer, position);
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void write(ByteBuffer buffer, int position, Polygon value) {
+ buffer.putInt(position, size(value));
+ position += Integer.BYTES;
+
+ // Write the exterior ring
+ var exteriorRing = value.getExteriorRing();
+ coordinateArrayDataType.write(buffer, position,
exteriorRing.getCoordinates());
+ position += coordinateArrayDataType.size(exteriorRing.getCoordinates());
+
+ // Write the interior rings
+ for (int i = 0; i < value.getNumInteriorRing(); i++) {
+ var interiorRing = value.getInteriorRingN(i);
+ coordinateArrayDataType.write(buffer, position,
interiorRing.getCoordinates());
+ position += coordinateArrayDataType.size(interiorRing.getCoordinates());
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public Polygon read(ByteBuffer buffer, int position) {
+ var size = size(buffer, position);
+ var limit = position + size;
+ position += Integer.BYTES;
+
+
+ // Read the exterior ring
+ var exteriorRingCoordinates = coordinateArrayDataType.read(buffer,
position);
+ var exteriorRing =
geometryFactory.createLinearRing(exteriorRingCoordinates);
+ position += coordinateArrayDataType.size(buffer, position);
+
+ // Read the interior rings
+ var interiorRings = new ArrayList<LineString>();
+ while (position < limit) {
+ var interiorRingCoordinates = coordinateArrayDataType.read(buffer,
position);
+ var interiorRing =
geometryFactory.createLinearRing(interiorRingCoordinates);
+ interiorRings.add(interiorRing);
+ position += coordinateArrayDataType.size(buffer, position);
+ }
+
+ return geometryFactory.createPolygon(exteriorRing,
interiorRings.toArray(LinearRing[]::new));
+ }
+}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/RelationGeometryBuilder.java
b/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/RelationGeometryBuilder.java
index 35867faa..35370f09 100644
---
a/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/RelationGeometryBuilder.java
+++
b/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/RelationGeometryBuilder.java
@@ -96,6 +96,7 @@ public class RelationGeometryBuilder implements
Consumer<Relation> {
}
} catch (Exception e) {
logger.warn("Unable to build the geometry for relation #" +
relation.id(), e);
+ relation.setGeometry(GEOMETRY_FACTORY_WGS84.createEmpty(0));
}
}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/WayGeometryBuilder.java
b/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/WayGeometryBuilder.java
index 4ffeec3a..9a57fcbf 100644
---
a/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/WayGeometryBuilder.java
+++
b/baremaps-core/src/main/java/org/apache/baremaps/openstreetmap/function/WayGeometryBuilder.java
@@ -62,6 +62,7 @@ public class WayGeometryBuilder implements Consumer<Way> {
}
} catch (Exception e) {
logger.warn("Unable to build the geometry for way #" + way.id(), e);
+ way.setGeometry(GEOMETRY_FACTORY_WGS84.createEmpty(0));
}
}
}
diff --git a/baremaps-core/src/main/java/org/apache/baremaps/storage/Row.java
b/baremaps-core/src/main/java/org/apache/baremaps/storage/Row.java
index 2af38e3f..3de90fbf 100644
--- a/baremaps-core/src/main/java/org/apache/baremaps/storage/Row.java
+++ b/baremaps-core/src/main/java/org/apache/baremaps/storage/Row.java
@@ -31,7 +31,7 @@ public interface Row {
*
* @return the values of the columns in the row
*/
- List values();
+ List<?> values();
/**
* Returns the value of the specified column.
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufStore.java
b/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufStore.java
index 2b0459ec..950597bd 100644
---
a/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufStore.java
+++
b/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufStore.java
@@ -60,12 +60,14 @@ public class FlatGeoBufStore implements Store {
*/
@Override
public void add(Table table) throws TableException {
- var path = directory.resolve(table.schema().name());
+ var filename = table.schema().name();
+ filename = filename.endsWith(".fgb") ? filename : filename + ".fgb";
+ var path = directory.resolve(filename);
try {
- Files.delete(path);
+ Files.deleteIfExists(path);
Files.createFile(path);
var flatGeoBufTable = new FlatGeoBufTable(path, table.schema());
- table.forEach(flatGeoBufTable::add);
+ flatGeoBufTable.write(table);
} catch (IOException e) {
throw new TableException(e);
}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufTable.java
b/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufTable.java
index 5a13eeef..dedae110 100644
---
a/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufTable.java
+++
b/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/FlatGeoBufTable.java
@@ -27,7 +27,7 @@ import org.apache.baremaps.storage.AbstractTable;
import org.apache.baremaps.storage.Row;
import org.apache.baremaps.storage.Schema;
import org.apache.baremaps.storage.flatgeobuf.internal.TableConversions;
-import org.locationtech.jts.geom.Geometry;
+import org.locationtech.jts.geom.*;
import org.wololo.flatgeobuf.Constants;
import org.wololo.flatgeobuf.GeometryConversions;
import org.wololo.flatgeobuf.HeaderMeta;
@@ -160,6 +160,7 @@ public class FlatGeoBufTable extends AbstractTable {
var headerMeta = new HeaderMeta();
headerMeta.geometryType = GeometryType.Unknown;
headerMeta.indexNodeSize = 16;
+ headerMeta.srid = 3857;
headerMeta.featuresCount =
features instanceof AbstractDataCollection<Row>c ? c.sizeAsLong() :
features.size();
headerMeta.name = schema.name();
@@ -175,38 +176,44 @@ public class FlatGeoBufTable extends AbstractTable {
var iterator = features.iterator();
while (iterator.hasNext()) {
+ var featureBuilder = new FlatBufferBuilder(4096);
+
var row = iterator.next();
- var featureBuilder = new FlatBufferBuilder();
- var geometryOffset = 0;
- var propertiesOffset = 0;
+
var propertiesBuffer = ByteBuffer.allocate(1 <<
20).order(ByteOrder.LITTLE_ENDIAN);
- var i = 0;
- for (Object value : row.values()) {
- if (value instanceof Geometry geometry) {
- try {
- geometryOffset =
- GeometryConversions.serialize(featureBuilder, geometry,
headerMeta.geometryType);
- } catch (IOException e) {
- throw new RuntimeException(e);
- }
- } else {
- var column = headerMeta.columns.get(i);
- propertiesBuffer.putShort((short) i);
- TableConversions.writeValue(propertiesBuffer, column, value);
- i++;
- }
+ var properties = row.values().stream()
+ .filter(v -> !(v instanceof Geometry))
+ .toList();
+ for (int i = 0; i < properties.size(); i++) {
+ var column = headerMeta.columns.get(i);
+ var value = properties.get(i);
+ propertiesBuffer.putShort((short) i);
+ TableConversions.writeValue(propertiesBuffer, column, value);
}
- propertiesBuffer.flip();
- propertiesOffset = org.wololo.flatgeobuf.generated.Feature
+ if (propertiesBuffer.position() > 0) {
+ propertiesBuffer.flip();
+ }
+ var propertiesOffset = org.wololo.flatgeobuf.generated.Feature
.createPropertiesVector(featureBuilder, propertiesBuffer);
+ var geometry = row.values().stream()
+ .filter(v -> v instanceof Geometry)
+ .map(Geometry.class::cast)
+ .findFirst();
+
+ var geometryOffset = geometry.isPresent()
+ ? GeometryConversions.serialize(featureBuilder, geometry.get(),
headerMeta.geometryType)
+ : 0;
+
var featureOffset =
org.wololo.flatgeobuf.generated.Feature.createFeature(featureBuilder,
geometryOffset,
propertiesOffset, 0);
-
featureBuilder.finishSizePrefixed(featureOffset);
- channel.write(featureBuilder.dataBuffer());
+ ByteBuffer data = featureBuilder.dataBuffer();
+ while (data.hasRemaining()) {
+ channel.write(data);
+ }
}
}
}
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/internal/TableConversions.java
b/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/internal/TableConversions.java
index 817dc6d0..5bc3fff9 100644
---
a/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/internal/TableConversions.java
+++
b/baremaps-core/src/main/java/org/apache/baremaps/storage/flatgeobuf/internal/TableConversions.java
@@ -21,6 +21,7 @@ import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
+import java.util.Objects;
import java.util.stream.Collectors;
import org.apache.baremaps.storage.*;
import org.wololo.flatgeobuf.ColumnMeta;
@@ -191,13 +192,14 @@ public class TableConversions {
public static List<ColumnMeta> asColumns(List<Column> columns) {
return columns.stream()
.map(TableConversions::asColumn)
+ .filter(Objects::nonNull)
.collect(Collectors.toList());
}
public static ColumnMeta asColumn(Column column) {
var type = types.get(column.type());
if (type == null) {
- throw new IllegalArgumentException("Unsupported type " + type);
+ return null;
}
var columnMeta = new ColumnMeta();
columnMeta.name = column.name();
diff --git
a/baremaps-core/src/main/java/org/apache/baremaps/workflow/tasks/EntityDataType.java
b/baremaps-core/src/main/java/org/apache/baremaps/workflow/tasks/EntityDataType.java
index f9c9a2de..027762d3 100644
---
a/baremaps-core/src/main/java/org/apache/baremaps/workflow/tasks/EntityDataType.java
+++
b/baremaps-core/src/main/java/org/apache/baremaps/workflow/tasks/EntityDataType.java
@@ -15,6 +15,7 @@ package org.apache.baremaps.workflow.tasks;
import java.nio.ByteBuffer;
import java.util.Map;
import org.apache.baremaps.collection.type.*;
+import org.apache.baremaps.collection.type.geometry.GeometryDataType;
import org.locationtech.jts.geom.Geometry;
public class EntityDataType implements DataType<Entity> {
@@ -29,7 +30,8 @@ public class EntityDataType implements DataType<Entity> {
@Override
public int size(Entity value) {
int size = 0;
- size += idType.size();
+ size += Integer.BYTES;
+ size += idType.size(value.getId());
size += tagsType.size(value.getTags());
size += geometryType.size(value.getGeometry());
return size;
diff --git
a/baremaps-core/src/test/java/org/apache/baremaps/collection/AppendOnlyBufferTest.java
b/baremaps-core/src/test/java/org/apache/baremaps/collection/AppendOnlyBufferTest.java
index 5340fd3b..d1e6bebc 100644
---
a/baremaps-core/src/test/java/org/apache/baremaps/collection/AppendOnlyBufferTest.java
+++
b/baremaps-core/src/test/java/org/apache/baremaps/collection/AppendOnlyBufferTest.java
@@ -61,8 +61,8 @@ class AppendOnlyBufferTest {
@ParameterizedTest
@MethodSource("org.apache.baremaps.collection.type.DataTypeProvider#dataTypes")
void testAllDataTypes(DataType dataType, Object value) {
- var num = 1 << 10;
- var collection = new AppendOnlyBuffer<>(dataType, new OffHeapMemory(1 <<
8));
+ var num = 1000;
+ var collection = new AppendOnlyBuffer<>(dataType, new OffHeapMemory(1 <<
22));
// write values
for (int i = 0; i < num; i++) {
diff --git
a/baremaps-core/src/test/java/org/apache/baremaps/collection/type/DataTypeProvider.java
b/baremaps-core/src/test/java/org/apache/baremaps/collection/type/DataTypeProvider.java
index 76d32457..0b8d15f8 100644
---
a/baremaps-core/src/test/java/org/apache/baremaps/collection/type/DataTypeProvider.java
+++
b/baremaps-core/src/test/java/org/apache/baremaps/collection/type/DataTypeProvider.java
@@ -13,13 +13,12 @@
package org.apache.baremaps.collection.type;
-
import java.util.List;
import java.util.Map;
import java.util.stream.Stream;
+import org.apache.baremaps.collection.type.geometry.*;
import org.junit.jupiter.params.provider.Arguments;
-import org.locationtech.jts.geom.Coordinate;
-import org.locationtech.jts.geom.GeometryFactory;
+import org.locationtech.jts.geom.*;
public class DataTypeProvider {
@@ -62,15 +61,6 @@ public class DataTypeProvider {
Arguments.of(new FloatListDataType(), List.of()),
Arguments.of(new FloatListDataType(), List.of((float) 1, (float) 2,
(float) 3)),
- // Geometry
- Arguments.of(new GeometryDataType(),
- new GeometryFactory().createEmpty(0)),
- Arguments.of(new GeometryDataType(),
- new GeometryFactory().createPoint(new Coordinate(1, 1))),
- Arguments.of(new GeometryDataType(),
- new GeometryFactory()
- .createLineString(new Coordinate[] {new Coordinate(1, 1), new
Coordinate(2, 2)})),
-
// Integer
Arguments.of(new IntegerDataType(), Integer.MIN_VALUE),
Arguments.of(new IntegerDataType(), Integer.MAX_VALUE),
@@ -147,6 +137,135 @@ public class DataTypeProvider {
Arguments.of(new SmallLongDataType(8), Long.MIN_VALUE),
Arguments.of(
new PairDataType<>(new LongDataType(), new LongDataType()),
- new PairDataType.Pair<>(1l, 2l)));
+ new PairDataType.Pair<>(1l, 2l)),
+
+ // WKB (Well Known Binary)
+ Arguments.of(new WKBDataType(),
+ new GeometryFactory().createEmpty(0)),
+ Arguments.of(new WKBDataType(),
+ new GeometryFactory().createPoint(new Coordinate(1, 1))),
+ Arguments.of(new WKBDataType(),
+ new GeometryFactory()
+ .createLineString(new Coordinate[] {new Coordinate(1, 1), new
Coordinate(2, 2)})),
+
+ // Point
+ Arguments.of(new PointDataType(),
+ new GeometryFactory().createPoint()),
+ Arguments.of(new PointDataType(),
+ new GeometryFactory()
+ .createPoint(new Coordinate(1, 1))),
+
+ // MultiPoint
+ Arguments.of(new MultiPointDataType(),
+ new GeometryFactory().createMultiPoint()),
+ Arguments.of(new MultiPointDataType(),
+ new GeometryFactory()
+ .createMultiPoint(new Coordinate[] {new Coordinate(1, 1), new
Coordinate(2, 2)})),
+
+ // LineString
+ Arguments.of(new LineStringDataType(),
+ new GeometryFactory().createLineString()),
+ Arguments.of(new LineStringDataType(),
+ new GeometryFactory()
+ .createLineString(new Coordinate[] {new Coordinate(1, 1), new
Coordinate(2, 2)})),
+
+ // MultiLineString
+ Arguments.of(new MultiLineStringDataType(),
+ new GeometryFactory().createMultiLineString()),
+ Arguments.of(new MultiLineStringDataType(),
+ new GeometryFactory()
+ .createMultiLineString(
+ new LineString[] {
+ new GeometryFactory()
+ .createLineString(
+ new Coordinate[] {new Coordinate(1, 1), new
Coordinate(2, 2)}),
+ new GeometryFactory()
+ .createLineString(
+ new Coordinate[] {new Coordinate(3, 3), new
Coordinate(4, 4)})})),
+
+ // Polygon
+ Arguments.of(new PolygonDataType(),
+ new GeometryFactory().createPolygon()),
+ Arguments.of(new PolygonDataType(),
+ new GeometryFactory()
+ .createPolygon(
+ new GeometryFactory()
+ .createLinearRing(
+ new Coordinate[] {new Coordinate(0, 0), new
Coordinate(0, 3),
+ new Coordinate(5, 3), new Coordinate(5, 0),
new Coordinate(0, 0)}),
+ new LinearRing[] {
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[] {new
Coordinate(1, 1),
+ new Coordinate(1, 2), new Coordinate(2, 2),
new Coordinate(2, 1),
+ new Coordinate(1, 1)}),
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[] {new
Coordinate(3, 1),
+ new Coordinate(3, 2), new Coordinate(4, 2),
new Coordinate(4, 1),
+ new Coordinate(3, 1)})})),
+
+ // MultiPolygon
+ Arguments.of(new MultiPolygonDataType(),
+ new GeometryFactory().createMultiPolygon()),
+ Arguments.of(new MultiPolygonDataType(),
+ new GeometryFactory()
+ .createMultiPolygon(
+ new Polygon[] {
+ new GeometryFactory()
+ .createPolygon(
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[] {new
Coordinate(0, 0),
+ new Coordinate(0, 3), new
Coordinate(5, 3),
+ new Coordinate(5, 0), new
Coordinate(0, 0)}),
+ new LinearRing[] {
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[]
{new Coordinate(1, 1),
+ new Coordinate(1, 2), new
Coordinate(2, 2),
+ new Coordinate(2, 1), new
Coordinate(1, 1)}),
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[]
{new Coordinate(3, 1),
+ new Coordinate(3, 2), new
Coordinate(4, 2),
+ new Coordinate(4, 1), new
Coordinate(3, 1)})}),
+ new GeometryFactory()
+ .createPolygon(
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[] {new
Coordinate(1, 4),
+ new Coordinate(1, 5), new
Coordinate(2, 5),
+ new Coordinate(2, 4), new
Coordinate(1, 4)}))})),
+
+ // GeometryCollection
+ Arguments.of(new GeometryCollectionDataType(),
+ new GeometryFactory().createGeometryCollection()),
+ Arguments.of(new GeometryCollectionDataType(),
+ new GeometryFactory()
+ .createGeometryCollection(
+ new Geometry[] {
+ new GeometryFactory()
+ .createPoint(new Coordinate(1, 1)),
+ new GeometryFactory()
+ .createLineString(
+ new Coordinate[] {new Coordinate(1, 1), new
Coordinate(2, 2)}),
+ new GeometryFactory()
+ .createPolygon(
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[] {new
Coordinate(0, 0),
+ new Coordinate(0, 3), new
Coordinate(5, 3),
+ new Coordinate(5, 0), new
Coordinate(0, 0)}),
+ new LinearRing[] {
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[]
{new Coordinate(1, 1),
+ new Coordinate(1, 2), new
Coordinate(2, 2),
+ new Coordinate(2, 1), new
Coordinate(1, 1)}),
+ new GeometryFactory()
+ .createLinearRing(new Coordinate[]
{new Coordinate(3, 1),
+ new Coordinate(3, 2), new
Coordinate(4, 2),
+ new Coordinate(4, 1), new
Coordinate(3, 1)})})})),
+
+ // Geometry
+ Arguments.of(new GeometryDataType(),
+ new GeometryFactory().createEmpty(0)),
+ Arguments.of(new GeometryDataType(),
+ new GeometryFactory()
+ .createPoint(new Coordinate(1, 1))));
+
}
}
diff --git a/examples/simplification/workflow.json
b/examples/transformation/workflow.json
similarity index 91%
rename from examples/simplification/workflow.json
rename to examples/transformation/workflow.json
index d1028ce9..a89c4560 100644
--- a/examples/simplification/workflow.json
+++ b/examples/transformation/workflow.json
@@ -6,8 +6,8 @@
"tasks": [
{
"type": "DownloadUrl",
- "url":
"https://download.geofabrik.de/europe/liechtenstein-latest.osm.pbf",
- "path": "liechtenstein-latest.osm.pbf"
+ "url":
"https://download.geofabrik.de/europe/switzerland-latest.osm.pbf",
+ "path": "data.osm.pbf"
}
]
},
@@ -19,7 +19,7 @@
"tasks": [
{
"type": "CreateEntityCollection",
- "file": "liechtenstein-latest.osm.pbf",
+ "file": "data.osm.pbf",
"collection": "collection",
"srid": 3857
}