提交 01e9b9d4 authored 作者: Evgenij Ryazanov's avatar Evgenij Ryazanov

Add h2.mixedGeometries system property for compatibility

上级 68cb892e
......@@ -565,6 +565,18 @@ public class SysProperties {
public static final String AUTH_CONFIG_FILE =
Utils.getProperty("h2.authConfigFile", null);
/**
* System property {@code h2.mixedGeometries}, {@code false} by default.
* <p>
* If {@code true} illegal geometries with mixed XY/XYZ dimensionality like
* {@code 'LINESTRING (1 2, 3 4 5)'} are accepted.
* </p>
* <p>
* If {@code false} such geometries are rejected with data conversion error.
* </p>
*/
public static final boolean MIXED_GEOMETRIES = Utils.getProperty("h2.mixedGeometries", false);
private static final String H2_BASE_DIR = "h2.baseDir";
private SysProperties() {
......
......@@ -20,6 +20,7 @@ import static org.h2.util.geometry.GeometryUtils.toCanonicalDouble;
import java.io.ByteArrayOutputStream;
import org.h2.engine.SysProperties;
import org.h2.util.Bits;
import org.h2.util.StringUtils;
import org.h2.util.geometry.GeometryUtils.DimensionSystemTarget;
......@@ -141,7 +142,7 @@ public final class EWKBUtils {
writeDouble(x);
writeDouble(y);
if ((dimensionSystem & DIMENSION_SYSTEM_XYZ) != 0) {
writeDouble(check ? checkFinite(z) : z);
writeDouble(!SysProperties.MIXED_GEOMETRIES && check ? checkFinite(z) : z);
}
if ((dimensionSystem & DIMENSION_SYSTEM_XYM) != 0) {
writeDouble(check ? checkFinite(m) : m);
......
......@@ -23,6 +23,7 @@ import static org.h2.util.geometry.GeometryUtils.Z;
import java.io.ByteArrayOutputStream;
import java.util.ArrayList;
import org.h2.engine.SysProperties;
import org.h2.util.StringUtils;
import org.h2.util.geometry.EWKBUtils.EWKBTarget;
import org.h2.util.geometry.GeometryUtils.DimensionSystemTarget;
......@@ -198,7 +199,15 @@ public final class EWKTUtils {
writeDouble(x);
output.append(' ');
writeDouble(y);
if ((dimensionSystem & DIMENSION_SYSTEM_XYZ) != 0) {
dimensionZ: if ((dimensionSystem & DIMENSION_SYSTEM_XYZ) != 0) {
if (SysProperties.MIXED_GEOMETRIES) {
if (Double.isNaN(z)) {
if ((dimensionSystem & DIMENSION_SYSTEM_XYM) != 0) {
throw new IllegalArgumentException();
}
break dimensionZ;
}
}
output.append(' ');
writeDouble(z);
}
......
......@@ -23,6 +23,7 @@ import static org.h2.util.geometry.GeometryUtils.toCanonicalDouble;
import java.io.ByteArrayOutputStream;
import org.h2.engine.SysProperties;
import org.h2.util.geometry.EWKBUtils.EWKBTarget;
import org.h2.util.geometry.GeometryUtils.DimensionSystemTarget;
import org.h2.util.geometry.GeometryUtils.Target;
......@@ -164,7 +165,9 @@ public final class JTSUtils {
coordinates.setOrdinate(index, X, checkFinite(x));
coordinates.setOrdinate(index, Y, checkFinite(y));
coordinates.setOrdinate(index, Z,
(dimensionSystem & DIMENSION_SYSTEM_XYZ) != 0 ? checkFinite(z) : Double.NaN);
(dimensionSystem & DIMENSION_SYSTEM_XYZ) != 0
? SysProperties.MIXED_GEOMETRIES ? z : checkFinite(z)
: Double.NaN);
if ((dimensionSystem & DIMENSION_SYSTEM_XYM) != 0) {
coordinates.setOrdinate(index, M, checkFinite(m));
}
......
......@@ -18,6 +18,7 @@ import static org.h2.util.geometry.GeometryUtils.Y;
import static org.h2.util.geometry.GeometryUtils.Z;
import java.io.ByteArrayOutputStream;
import java.lang.ProcessBuilder.Redirect;
import java.util.Random;
import org.h2.test.TestBase;
......@@ -37,6 +38,7 @@ import org.locationtech.jts.geom.Envelope;
import org.locationtech.jts.geom.Geometry;
import org.locationtech.jts.geom.GeometryCollection;
import org.locationtech.jts.geom.GeometryFactory;
import org.locationtech.jts.geom.LineString;
import org.locationtech.jts.geom.Point;
import org.locationtech.jts.io.WKBWriter;
import org.locationtech.jts.io.WKTReader;
......@@ -73,14 +75,44 @@ public class TestGeometryUtils extends TestBase {
DIMENSION_SYSTEM_XYZ, //
DIMENSION_SYSTEM_XYM };
private static final String MIXED_WKT = "LINESTRING (1 2, 3 4 5)";
private static final String MIXED_WKT_Z = "LINESTRING Z (1 2, 3 4 5)";
private static final byte[] MIXED_WKB = StringUtils.convertHexToBytes(""
// BOM (BigEndian)
+ "00"
// Z | LINESTRING
+ "80000002"
// 2 items
+ "00000002"
// 1.0
+ "3ff0000000000000"
// 2.0
+ "4000000000000000"
// NaN
+ "7ff8000000000000"
// 3.0
+ "4008000000000000"
// 4.0
+ "4010000000000000"
// 5.0
+ "4014000000000000");
/**
* Run just this test.
* May be used to run only this test and may be launched by this test in a
* subprocess.
*
* @param a
* ignored
* if empty run this test only
*/
public static void main(String... a) throws Exception {
TestBase.createCaller().init().test();
TestGeometryUtils test = (TestGeometryUtils) TestBase.createCaller().init();
if (a.length == 0) {
test.test();
} else {
test.testMixedGeometriesAcceptImpl();
}
}
@Override
......@@ -98,6 +130,8 @@ public class TestGeometryUtils extends TestBase {
testFiniteOnly();
testSRID();
testIntersectionAndUnion();
testMixedGeometries();
testMixedGeometriesAccept();
}
private void testPoint() throws Exception {
......@@ -360,4 +394,55 @@ public class TestGeometryUtils extends TestBase {
return new double[] { minX, maxX, minY, maxY };
}
private void testMixedGeometries() throws Exception {
try {
EWKTUtils.ewkt2ewkb(MIXED_WKT);
fail();
} catch (IllegalArgumentException ex) {
// Expected
}
try {
EWKTUtils.ewkb2ewkt(MIXED_WKB);
fail();
} catch (IllegalArgumentException ex) {
// Expected
}
try {
JTSUtils.ewkb2geometry(MIXED_WKB);
fail();
} catch (IllegalArgumentException ex) {
// Expected
}
Geometry g = new WKTReader().read(MIXED_WKT);
try {
JTSUtils.geometry2ewkb(g);
fail();
} catch (IllegalArgumentException ex) {
// Expected
}
}
private void testMixedGeometriesAccept() throws Exception {
ProcessBuilder pb = new ProcessBuilder().redirectError(Redirect.INHERIT);
pb.command(getJVM(), "-cp", getClassPath(), "-ea", "-Dh2.mixedGeometries=true", getClass().getName(), "dummy");
assertEquals(0, pb.start().waitFor());
}
private void testMixedGeometriesAcceptImpl() throws Exception {
assertEquals(MIXED_WKB, EWKTUtils.ewkt2ewkb(MIXED_WKT));
assertEquals(MIXED_WKT_Z, EWKTUtils.ewkb2ewkt(MIXED_WKB));
Geometry g = new WKTReader().read(MIXED_WKT);
assertEquals(MIXED_WKB, JTSUtils.geometry2ewkb(g));
LineString ls = (LineString) JTSUtils.ewkb2geometry(MIXED_WKB);
CoordinateSequence cs = ls.getCoordinateSequence();
assertEquals(2, cs.size());
assertEquals(3, cs.getDimension());
assertEquals(1, cs.getOrdinate(0, X));
assertEquals(2, cs.getOrdinate(0, Y));
assertEquals(Double.NaN, cs.getOrdinate(0, Z));
assertEquals(3, cs.getOrdinate(1, X));
assertEquals(4, cs.getOrdinate(1, Y));
assertEquals(5, cs.getOrdinate(1, Z));
}
}
......@@ -794,4 +794,4 @@ minxf maxxf minyf maxyf bminxf bmaxxf bminyf bmaxyf
minxd maxxd minyd maxyd bminxd bmaxxd bminyd bmaxyd
interior envelopes multilinestring multipoint packed exterior normalization awkward determination subgeometries
xym normalizes coord setz xyzm geometrycollection multipolygon mixup rings polygons rejection finite
pointzm pointz pointm
pointzm pointz pointm dimensionality
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论