You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@lucene.apache.org by rm...@apache.org on 2016/03/24 17:58:32 UTC

lucene-solr:branch_6x: LUCENE-7137: consolidate many tests across Points and GeoPoint queries/fields

Repository: lucene-solr
Updated Branches:
  refs/heads/branch_6x 521ff41c8 -> 139aa0bec


LUCENE-7137: consolidate many tests across Points and GeoPoint queries/fields


Project: http://git-wip-us.apache.org/repos/asf/lucene-solr/repo
Commit: http://git-wip-us.apache.org/repos/asf/lucene-solr/commit/139aa0be
Tree: http://git-wip-us.apache.org/repos/asf/lucene-solr/tree/139aa0be
Diff: http://git-wip-us.apache.org/repos/asf/lucene-solr/diff/139aa0be

Branch: refs/heads/branch_6x
Commit: 139aa0bec5683acbc6c3a00898aad9572853ea91
Parents: 521ff41
Author: Robert Muir <rm...@apache.org>
Authored: Thu Mar 24 12:18:40 2016 -0400
Committer: Robert Muir <rm...@apache.org>
Committed: Thu Mar 24 12:42:04 2016 -0400

----------------------------------------------------------------------
 .../apache/lucene/document/TestLatLonPoint.java | 126 +------
 .../document/TestLatLonPointDistanceQuery.java  |  82 -----
 .../document/TestLatLonPointInPolygonQuery.java |  49 ---
 .../lucene/search/TestLatLonPointQueries.java   |   5 +-
 .../geopoint/document/GeoPointField.java        |  32 +-
 .../geopoint/search/GeoPointDistanceQuery.java  |  49 ++-
 .../geopoint/search/GeoPointInBBoxQuery.java    |  18 +
 .../lucene/spatial/util/GeoDistanceUtils.java   |  61 ----
 .../geopoint/search/TestGeoPointField.java      | 255 --------------
 .../geopoint/search/TestGeoPointQuery.java      |  12 +-
 .../search/TestLegacyGeoPointField.java         | 242 -------------
 .../search/TestLegacyGeoPointQuery.java         |  12 +-
 .../spatial/util/BaseGeoPointTestCase.java      | 352 ++++++++++++++++++-
 .../lucene/spatial/util/TestGeoUtils.java       |  23 ++
 14 files changed, 426 insertions(+), 892 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPoint.java
----------------------------------------------------------------------
diff --git a/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPoint.java b/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPoint.java
index 1b6a6d2..55c8062 100644
--- a/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPoint.java
+++ b/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPoint.java
@@ -16,37 +16,11 @@
  */
 package org.apache.lucene.document;
 
-import org.apache.lucene.index.IndexReader;
-import org.apache.lucene.index.RandomIndexWriter;
-import org.apache.lucene.search.IndexSearcher;
-import org.apache.lucene.search.Query;
-import org.apache.lucene.store.Directory;
 import org.apache.lucene.util.LuceneTestCase;
 
 /** Simple tests for {@link LatLonPoint} */
 public class TestLatLonPoint extends LuceneTestCase {
 
-  /** Add a single point and search for it in a box */
-  // NOTE: we don't currently supply an exact search, only ranges, because of the lossiness...
-  public void testBoxQuery() throws Exception {
-    Directory dir = newDirectory();
-    RandomIndexWriter writer = new RandomIndexWriter(random(), dir);
-
-    // add a doc with a point
-    Document document = new Document();
-    document.add(new LatLonPoint("field", 18.313694, -65.227444));
-    writer.addDocument(document);
-    
-    // search and verify we found our doc
-    IndexReader reader = writer.getReader();
-    IndexSearcher searcher = newSearcher(reader);
-    assertEquals(1, searcher.count(LatLonPoint.newBoxQuery("field", 18, 19, -66, -65)));
-
-    reader.close();
-    writer.close();
-    dir.close();
-  }
-    
   public void testToString() throws Exception {
     // looks crazy due to lossiness
     assertEquals("LatLonPoint <field:18.313693958334625,-65.22744392976165>",(new LatLonPoint("field", 18.313694, -65.227444)).toString());
@@ -60,79 +34,6 @@ public class TestLatLonPoint extends LuceneTestCase {
     // sort field
     assertEquals("<distance:\"field\" latitude=18.0 longitude=19.0>", LatLonPoint.newDistanceSort("field", 18.0, 19.0).toString());
   }
-  
-  /** Valid values that should not cause exception */
-  public void testExtremeValues() {
-    new LatLonPoint("foo", 90.0, 180.0);
-    new LatLonPoint("foo", 90.0, -180.0);
-    new LatLonPoint("foo", -90.0, 180.0);
-    new LatLonPoint("foo", -90.0, -180.0);
-  }
-  
-  /** Invalid values */
-  public void testOutOfRangeValues() {
-    IllegalArgumentException expected;
-
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", Math.nextUp(90.0), 50.0);
-    });
-    assertTrue(expected.getMessage().contains("invalid latitude"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", Math.nextDown(-90.0), 50.0);
-    });
-    assertTrue(expected.getMessage().contains("invalid latitude"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", 90.0, Math.nextUp(180.0));
-    });
-    assertTrue(expected.getMessage().contains("invalid longitude"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", 90.0, Math.nextDown(-180.0));
-    });
-    assertTrue(expected.getMessage().contains("invalid longitude"));
-  }
-  
-  /** NaN: illegal */
-  public void testNaNValues() {
-    IllegalArgumentException expected;
-
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", Double.NaN, 50.0);
-    });
-    assertTrue(expected.getMessage().contains("invalid latitude"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", 50.0, Double.NaN);
-    });
-    assertTrue(expected.getMessage().contains("invalid longitude"));
-  }
-  
-  /** Inf: illegal */
-  public void testInfValues() {
-    IllegalArgumentException expected;
-
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", Double.POSITIVE_INFINITY, 50.0);
-    });
-    assertTrue(expected.getMessage().contains("invalid latitude"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", Double.NEGATIVE_INFINITY, 50.0);
-    });
-    assertTrue(expected.getMessage().contains("invalid latitude"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", 50.0, Double.POSITIVE_INFINITY);
-    });
-    assertTrue(expected.getMessage().contains("invalid longitude"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      new LatLonPoint("foo", 50.0, Double.NEGATIVE_INFINITY);
-    });
-    assertTrue(expected.getMessage().contains("invalid longitude"));
-  }
    
   public void testEncodeDecode() throws Exception {
     // just for testing quantization error
@@ -183,30 +84,5 @@ public class TestLatLonPoint extends LuceneTestCase {
       assertEquals(latEnc, latEnc2, 0.0);
       assertEquals(lonEnc, lonEnc2, 0.0);
     }
-  }
-
-  public void testQueryEquals() throws Exception {
-    Query q1 = LatLonPoint.newBoxQuery("field", 50, 70, -40, 20);
-    Query q2 = LatLonPoint.newBoxQuery("field", 50, 70, -40, 20);
-    assertEquals(q1, q2);
-    assertEquals(q1.hashCode(), q2.hashCode());
-    assertFalse(q1.equals(LatLonPoint.newBoxQuery("field", 50, 70, -40, 10)));
-
-    q1 = LatLonPoint.newDistanceQuery("field", 50, 70, 10000);
-    q2 = LatLonPoint.newDistanceQuery("field", 50, 70, 10000);
-    assertEquals(q1, q2);
-    assertEquals(q1.hashCode(), q2.hashCode());
-    assertFalse(q1.equals(LatLonPoint.newDistanceQuery("field", 50, 70, 11000)));
-    assertFalse(q1.equals(LatLonPoint.newDistanceQuery("field", 50, 60, 10000)));
-
-                
-    double[] polyLats1 = new double[] {30, 40, 40, 30, 30};
-    double[] polyLons1 = new double[] {90, 90, -40, -40, 90};
-    double[] polyLats2 = new double[] {20, 40, 40, 20, 20};
-    q1 = LatLonPoint.newPolygonQuery("field", polyLats1, polyLons1);
-    q2 = LatLonPoint.newPolygonQuery("field", polyLats1, polyLons1);
-    assertEquals(q1, q2);
-    assertEquals(q1.hashCode(), q2.hashCode());
-    assertFalse(q1.equals(LatLonPoint.newPolygonQuery("field", polyLats2, polyLons1)));
-  }     
+  }   
 }

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointDistanceQuery.java
----------------------------------------------------------------------
diff --git a/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointDistanceQuery.java b/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointDistanceQuery.java
deleted file mode 100644
index f015780..0000000
--- a/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointDistanceQuery.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You 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.lucene.document;
-
-import org.apache.lucene.index.IndexReader;
-import org.apache.lucene.index.RandomIndexWriter;
-import org.apache.lucene.search.IndexSearcher;
-import org.apache.lucene.store.Directory;
-import org.apache.lucene.util.LuceneTestCase;
-
-/** Simple tests for {@link LatLonPoint#newDistanceQuery} */
-public class TestLatLonPointDistanceQuery extends LuceneTestCase {
-
-  /** test we can search for a point */
-  public void testBasics() throws Exception {
-    Directory dir = newDirectory();
-    RandomIndexWriter writer = new RandomIndexWriter(random(), dir);
-
-    // add a doc with a location
-    Document document = new Document();
-    document.add(new LatLonPoint("field", 18.313694, -65.227444));
-    writer.addDocument(document);
-    
-    // search within 50km and verify we found our doc
-    IndexReader reader = writer.getReader();
-    IndexSearcher searcher = newSearcher(reader);
-    assertEquals(1, searcher.count(LatLonPoint.newDistanceQuery("field", 18, -65, 50_000)));
-
-    reader.close();
-    writer.close();
-    dir.close();
-  }
-  
-  /** negative distance queries are not allowed */
-  public void testNegativeRadius() {
-    IllegalArgumentException expected = expectThrows(IllegalArgumentException.class, () -> {
-      LatLonPoint.newDistanceQuery("field", 18, 19, -1);
-    });
-    assertTrue(expected.getMessage().contains("radiusMeters"));
-    assertTrue(expected.getMessage().contains("is invalid"));
-  }
-  
-  /** NaN distance queries are not allowed */
-  public void testNaNRadius() {
-    IllegalArgumentException expected = expectThrows(IllegalArgumentException.class, () -> {
-      LatLonPoint.newDistanceQuery("field", 18, 19, Double.NaN);
-    });
-    assertTrue(expected.getMessage().contains("radiusMeters"));
-    assertTrue(expected.getMessage().contains("is invalid"));
-  }
-  
-  /** Inf distance queries are not allowed */
-  public void testInfRadius() {
-    IllegalArgumentException expected;
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      LatLonPoint.newDistanceQuery("field", 18, 19, Double.POSITIVE_INFINITY);
-    });
-    assertTrue(expected.getMessage().contains("radiusMeters"));
-    assertTrue(expected.getMessage().contains("is invalid"));
-    
-    expected = expectThrows(IllegalArgumentException.class, () -> {
-      LatLonPoint.newDistanceQuery("field", 18, 19, Double.NEGATIVE_INFINITY);
-    });
-    assertTrue(expected.getMessage().contains("radiusMeters"));
-    assertTrue(expected.getMessage().contains("is invalid"));
-  }
-}

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointInPolygonQuery.java
----------------------------------------------------------------------
diff --git a/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointInPolygonQuery.java b/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointInPolygonQuery.java
deleted file mode 100644
index de87027..0000000
--- a/lucene/sandbox/src/test/org/apache/lucene/document/TestLatLonPointInPolygonQuery.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You 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.lucene.document;
-
-import org.apache.lucene.index.IndexReader;
-import org.apache.lucene.index.RandomIndexWriter;
-import org.apache.lucene.search.IndexSearcher;
-import org.apache.lucene.store.Directory;
-import org.apache.lucene.util.LuceneTestCase;
-
-/** Simple tests for {@link LatLonPoint#newPolygonQuery} */
-public class TestLatLonPointInPolygonQuery extends LuceneTestCase {
-
-  /** test we can search for a polygon */
-  public void testBasics() throws Exception {
-    Directory dir = newDirectory();
-    RandomIndexWriter writer = new RandomIndexWriter(random(), dir);
-
-    // add a doc with a point
-    Document document = new Document();
-    document.add(new LatLonPoint("field", 18.313694, -65.227444));
-    writer.addDocument(document);
-    
-    // search and verify we found our doc
-    IndexReader reader = writer.getReader();
-    IndexSearcher searcher = newSearcher(reader);
-    assertEquals(1, searcher.count(LatLonPoint.newPolygonQuery("field",
-                                                               new double[] { 18, 18, 19, 19, 18 },
-                                                               new double[] { -66, -65, -65, -66, -66 })));
-
-    reader.close();
-    writer.close();
-    dir.close();
-  }
-}

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/sandbox/src/test/org/apache/lucene/search/TestLatLonPointQueries.java
----------------------------------------------------------------------
diff --git a/lucene/sandbox/src/test/org/apache/lucene/search/TestLatLonPointQueries.java b/lucene/sandbox/src/test/org/apache/lucene/search/TestLatLonPointQueries.java
index b136776..4f2c2d7 100644
--- a/lucene/sandbox/src/test/org/apache/lucene/search/TestLatLonPointQueries.java
+++ b/lucene/sandbox/src/test/org/apache/lucene/search/TestLatLonPointQueries.java
@@ -19,7 +19,6 @@ package org.apache.lucene.search;
 import org.apache.lucene.document.Document;
 import org.apache.lucene.document.LatLonPoint;
 import org.apache.lucene.spatial.util.BaseGeoPointTestCase;
-import org.apache.lucene.spatial.util.GeoRect;
 
 public class TestLatLonPointQueries extends BaseGeoPointTestCase {
 
@@ -29,8 +28,8 @@ public class TestLatLonPointQueries extends BaseGeoPointTestCase {
   }
 
   @Override
-  protected Query newRectQuery(String field, GeoRect rect) {
-    return LatLonPoint.newBoxQuery(field, rect.minLat, rect.maxLat, rect.minLon, rect.maxLon);
+  protected Query newRectQuery(String field, double minLat, double maxLat, double minLon, double maxLon) {
+    return LatLonPoint.newBoxQuery(field, minLat, maxLat, minLon, maxLon);
   }
 
   @Override

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/document/GeoPointField.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/document/GeoPointField.java b/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/document/GeoPointField.java
index 00db23a..a477fa9 100644
--- a/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/document/GeoPointField.java
+++ b/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/document/GeoPointField.java
@@ -128,47 +128,47 @@ public final class GeoPointField extends Field {
 
   /** Creates a stored or un-stored GeoPointField
    *  @param name field name
-   *  @param lat latitude double value [-90.0 : 90.0]
-   *  @param lon longitude double value [-180.0 : 180.0]
+   *  @param latitude latitude double value [-90.0 : 90.0]
+   *  @param longitude longitude double value [-180.0 : 180.0]
    *  @param stored Store.YES if the content should also be stored
    *  @throws IllegalArgumentException if the field name is null.
    */
-  public GeoPointField(String name, double lat, double lon, Store stored) {
-    this(name, lat, lon, getFieldType(stored));
+  public GeoPointField(String name, double latitude, double longitude, Store stored) {
+    this(name, latitude, longitude, getFieldType(stored));
   }
 
   /** Creates a stored or un-stored GeoPointField using the specified {@link TermEncoding} method
    *  @param name field name
-   *  @param lat latitude double value [-90.0 : 90.0]
-   *  @param lon longitude double value [-180.0 : 180.0]
+   *  @param latitude latitude double value [-90.0 : 90.0]
+   *  @param longitude longitude double value [-180.0 : 180.0]
    *  @param termEncoding encoding type to use ({@link TermEncoding#NUMERIC} Terms, or {@link TermEncoding#PREFIX} only Terms)
    *  @param stored Store.YES if the content should also be stored
    *  @throws IllegalArgumentException if the field name is null.
    */
   @Deprecated
-  public GeoPointField(String name, double lat, double lon, TermEncoding termEncoding, Store stored) {
-    this(name, lat, lon, getFieldType(termEncoding, stored));
+  public GeoPointField(String name, double latitude, double longitude, TermEncoding termEncoding, Store stored) {
+    this(name, latitude, longitude, getFieldType(termEncoding, stored));
   }
 
   /** Expert: allows you to customize the {@link
    *  FieldType}.
    *  @param name field name
-   *  @param lat latitude double value [-90.0 : 90.0]
-   *  @param lon longitude double value [-180.0 : 180.0]
+   *  @param latitude latitude double value [-90.0 : 90.0]
+   *  @param longitude longitude double value [-180.0 : 180.0]
    *  @param type customized field type: must have {@link FieldType#numericType()}
    *         of {@link org.apache.lucene.document.FieldType.LegacyNumericType#LONG}.
    *  @throws IllegalArgumentException if the field name or type is null, or
    *          if the field type does not have a LONG numericType()
    */
-  public GeoPointField(String name, double lat, double lon, FieldType type) {
+  public GeoPointField(String name, double latitude, double longitude, FieldType type) {
     super(name, type);
 
-    if (GeoUtils.isValidLat(lat) == false) {
-      throw new IllegalArgumentException("invalid lat=" + lat + " for field \"" + name + "\"");
+    if (GeoUtils.isValidLat(latitude) == false) {
+      throw new IllegalArgumentException("invalid latitude=" + latitude + " for field \"" + name + "\"");
     }
 
-    if (GeoUtils.isValidLon(lon) == false) {
-      throw new IllegalArgumentException("invalid lon=" + lon + " for field \"" + name + "\"");
+    if (GeoUtils.isValidLon(longitude) == false) {
+      throw new IllegalArgumentException("invalid longitude=" + longitude + " for field \"" + name + "\"");
     }
 
     // field must be indexed
@@ -190,7 +190,7 @@ public final class GeoPointField extends Field {
     }
 
     // set field data
-    fieldsData = GeoEncodingUtils.mortonHash(lat, lon);
+    fieldsData = GeoEncodingUtils.mortonHash(latitude, longitude);
   }
 
   private static FieldType getFieldType(Store stored) {

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointDistanceQuery.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointDistanceQuery.java b/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointDistanceQuery.java
index 2486852..98bb2ca 100644
--- a/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointDistanceQuery.java
+++ b/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointDistanceQuery.java
@@ -21,7 +21,6 @@ import org.apache.lucene.search.BooleanClause;
 import org.apache.lucene.search.BooleanQuery;
 import org.apache.lucene.search.Query;
 import org.apache.lucene.spatial.geopoint.document.GeoPointField.TermEncoding;
-import org.apache.lucene.spatial.util.GeoDistanceUtils;
 import org.apache.lucene.spatial.util.GeoRect;
 import org.apache.lucene.spatial.util.GeoUtils;
 
@@ -49,12 +48,34 @@ public class GeoPointDistanceQuery extends GeoPointInBBoxQuery {
   /** distance (in meters) from lat, lon center location */
   protected final double radiusMeters;
 
+  // we must check these before passing to superclass or circleToBBox, or users can get a strange exception!
+  private static double checkRadius(double radiusMeters) {
+    if (Double.isFinite(radiusMeters) == false || radiusMeters < 0) {
+      throw new IllegalArgumentException("invalid radiusMeters " + radiusMeters);
+    }
+    return radiusMeters;
+  }
+  
+  private static double checkLatitude(double centerLat) {
+    if (GeoUtils.isValidLat(centerLat) == false) {
+      throw new IllegalArgumentException("invalid centerLat " + centerLat);
+    }
+    return centerLat;
+  }
+  
+  private static double checkLongitude(double centerLon) {
+    if (GeoUtils.isValidLon(centerLon) == false) {
+      throw new IllegalArgumentException("invalid centerLon " + centerLon);
+    }
+    return centerLon;
+  }
+  
   /**
    * Constructs a Query for all {@link org.apache.lucene.spatial.geopoint.document.GeoPointField} types within a
    * distance (in meters) from a given point
    **/
   public GeoPointDistanceQuery(final String field, final double centerLat, final double centerLon, final double radiusMeters) {
-    this(field, TermEncoding.PREFIX, centerLat, centerLon, radiusMeters);
+    this(field, TermEncoding.PREFIX, checkLatitude(centerLat), checkLongitude(centerLon), checkRadius(radiusMeters));
   }
 
   /**
@@ -63,34 +84,12 @@ public class GeoPointDistanceQuery extends GeoPointInBBoxQuery {
    * {@link org.apache.lucene.spatial.geopoint.document.GeoPointField.TermEncoding} parameter
    **/
   public GeoPointDistanceQuery(final String field, final TermEncoding termEncoding, final double centerLat, final double centerLon, final double radiusMeters) {
-    this(field, termEncoding, GeoUtils.circleToBBox(centerLat, centerLon, radiusMeters), centerLat, centerLon, radiusMeters);
+    this(field, termEncoding, GeoUtils.circleToBBox(checkLatitude(centerLat), checkLongitude(centerLon), checkRadius(radiusMeters)), centerLat, centerLon, radiusMeters);
   }
 
   private GeoPointDistanceQuery(final String field, final TermEncoding termEncoding, final GeoRect bbox,
                                  final double centerLat, final double centerLon, final double radiusMeters) {
     super(field, termEncoding, bbox.minLat, bbox.maxLat, bbox.minLon, bbox.maxLon);
-    {
-      // check longitudinal overlap (restrict distance to maximum longitudinal radius)
-      // todo this restriction technically shouldn't be needed,
-      // its only purpose is to ensure the bounding box doesn't self overlap.
-      final double maxRadius = GeoDistanceUtils.maxRadialDistanceMeters(centerLat, centerLon);
-      if (radiusMeters > maxRadius) {
-        throw new IllegalArgumentException("radiusMeters " + radiusMeters + " exceeds maxRadius [" + maxRadius
-            + "] at location [" + centerLat + " " + centerLon + "]");
-      }
-    }
-
-    if (GeoUtils.isValidLat(centerLat) == false) {
-      throw new IllegalArgumentException("invalid centerLat " + centerLat);
-    }
-
-    if (GeoUtils.isValidLon(centerLon) == false) {
-      throw new IllegalArgumentException("invalid centerLon " + centerLon);
-    }
-
-    if (radiusMeters <= 0.0) {
-      throw new IllegalArgumentException("invalid radiusMeters " + radiusMeters);
-    }
 
     this.centerLat = centerLat;
     this.centerLon = centerLon;

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointInBBoxQuery.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointInBBoxQuery.java b/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointInBBoxQuery.java
index f81f37e..e9486d3 100644
--- a/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointInBBoxQuery.java
+++ b/lucene/spatial/src/java/org/apache/lucene/spatial/geopoint/search/GeoPointInBBoxQuery.java
@@ -71,6 +71,24 @@ public class GeoPointInBBoxQuery extends Query {
    * defined bounding box. Accepts optional {@link org.apache.lucene.spatial.geopoint.document.GeoPointField.TermEncoding} parameter
    */
   public GeoPointInBBoxQuery(final String field, final TermEncoding termEncoding, final double minLat, final double maxLat, final double minLon, final double maxLon) {
+    if (field == null) {
+      throw new IllegalArgumentException("field cannot be null");
+    }
+    if (termEncoding == null) {
+      throw new IllegalArgumentException("termEncoding cannot be null");
+    }
+    if (GeoUtils.isValidLat(minLat) == false) {
+      throw new IllegalArgumentException("invalid minimum latitude: " + minLat + ", must be -90 to 90");
+    }
+    if (GeoUtils.isValidLat(maxLat) == false) {
+      throw new IllegalArgumentException("invalid maximum latitude: " + maxLat + ", must be -90 to 90");
+    }
+    if (GeoUtils.isValidLon(minLon) == false) {
+      throw new IllegalArgumentException("invalid minimum longitude: " + minLon + ", must be -180 to 180");
+    }
+    if (GeoUtils.isValidLon(maxLon) == false) {
+      throw new IllegalArgumentException("invalid maximum longitude: " + maxLon + ", must be -180 to 180");
+    }
     this.field = field;
     this.minLat = minLat;
     this.maxLat = maxLat;

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/java/org/apache/lucene/spatial/util/GeoDistanceUtils.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/java/org/apache/lucene/spatial/util/GeoDistanceUtils.java b/lucene/spatial/src/java/org/apache/lucene/spatial/util/GeoDistanceUtils.java
deleted file mode 100644
index 1a412ac..0000000
--- a/lucene/spatial/src/java/org/apache/lucene/spatial/util/GeoDistanceUtils.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You 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.lucene.spatial.util;
-
-import org.apache.lucene.util.SloppyMath;
-
-/**
- * Reusable geo-spatial distance utility methods.
- *
- * @lucene.experimental
- */
-public class GeoDistanceUtils {
-
-  // No instance:
-  private GeoDistanceUtils() {
-  }
-
-  /**
-   * Compute the inverse haversine to determine distance in degrees longitude for provided distance in meters
-   * @param lat latitude to compute delta degrees lon
-   * @param distance distance in meters to convert to degrees lon
-   * @return Sloppy distance in degrees longitude for provided distance in meters
-   */
-  public static double distanceToDegreesLon(double lat, double distance) {
-    // convert latitude to radians
-    lat = StrictMath.toRadians(lat);
-
-    // get the diameter at the latitude
-    final double diameter = 2 * GeoUtils.SEMIMAJOR_AXIS;
-
-    // compute inverse haversine
-    double a = StrictMath.sin(distance/diameter);
-    double h = StrictMath.min(1, a);
-    h *= h;
-    double cLat = StrictMath.cos(lat);
-
-    return StrictMath.toDegrees(StrictMath.acos(1-((2d*h)/(cLat*cLat))));
-  }
-
-  /** Returns the maximum distance/radius (in meters) from the point 'center' before overlapping */
-  public static double maxRadialDistanceMeters(final double centerLat, final double centerLon) {
-    if (Math.abs(centerLat) == GeoUtils.MAX_LAT_INCL) {
-      return SloppyMath.haversinMeters(centerLat, centerLon, 0, centerLon);
-    }
-    return SloppyMath.haversinMeters(centerLat, centerLon, centerLat, (GeoUtils.MAX_LON_INCL + centerLon) % 360);
-  }
-}

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointField.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointField.java b/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointField.java
deleted file mode 100644
index 123769e..0000000
--- a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointField.java
+++ /dev/null
@@ -1,255 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You 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.lucene.spatial.geopoint.search;
-
-import org.apache.lucene.analysis.MockAnalyzer;
-import org.apache.lucene.document.Document;
-import org.apache.lucene.document.Field;
-import org.apache.lucene.document.StringField;
-import org.apache.lucene.index.IndexReader;
-import org.apache.lucene.index.RandomIndexWriter;
-import org.apache.lucene.search.IndexSearcher;
-import org.apache.lucene.search.TopDocs;
-import org.apache.lucene.spatial.geopoint.document.GeoPointField;
-import org.apache.lucene.spatial.geopoint.document.GeoPointField.TermEncoding;
-import org.apache.lucene.spatial.util.GeoRelationUtils;
-import org.apache.lucene.spatial.util.GeoUtils;
-import org.apache.lucene.store.Directory;
-import org.apache.lucene.util.LuceneTestCase;
-import org.apache.lucene.util.TestUtil;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-
-/** Simple tests for GeoPoint */
-public class TestGeoPointField extends LuceneTestCase {
-  
-  private static Directory directory = null;
-  private static IndexReader reader = null;
-  private static IndexSearcher searcher = null;
-  private static final String FIELD_NAME = "point";
-
-  @BeforeClass
-  public static void beforeClass() throws Exception {
-    directory = newDirectory();
-
-    RandomIndexWriter writer = new RandomIndexWriter(random(), directory,
-            newIndexWriterConfig(new MockAnalyzer(random()))
-                    .setMaxBufferedDocs(TestUtil.nextInt(random(), 100, 1000))
-                    .setMergePolicy(newLogMergePolicy()));
-
-    // this is a simple systematic test
-    GeoPointField[] pts = new GeoPointField[] {
-        new GeoPointField(FIELD_NAME, 32.763420, -96.774, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.7559529921407, -96.7759895324707, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.77866942010977, -96.77701950073242, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.7756745755423, -96.7706036567688, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 27.703618681345585, -139.73458170890808, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.94823588839368, -96.4538113027811, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 33.06047141970814, -96.65084838867188, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.778650, -96.7772, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, -88.56029371730983, -177.23537676036358, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 33.541429799076354, -26.779373834241003, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 26.774024500421728, -77.35379276106497, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, -90.0, -14.796283808944777, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.94823588839368, -178.8538113027811, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.94823588839368, 178.8538113027811, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 40.720611, -73.998776, GeoPointField.PREFIX_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, -44.5, -179.5, GeoPointField.PREFIX_TYPE_NOT_STORED)};
-
-    for (GeoPointField p : pts) {
-        Document doc = new Document();
-        doc.add(p);
-        writer.addDocument(doc);
-    }
-
-    // add explicit multi-valued docs
-    for (int i=0; i<pts.length; i+=2) {
-      Document doc = new Document();
-      doc.add(pts[i]);
-      doc.add(pts[i+1]);
-      writer.addDocument(doc);
-    }
-
-    // index random string documents
-    for (int i=0; i<random().nextInt(10); ++i) {
-      Document doc = new Document();
-      doc.add(new StringField("string", Integer.toString(i), Field.Store.NO));
-      writer.addDocument(doc);
-    }
-
-    reader = writer.getReader();
-    searcher = newSearcher(reader);
-    writer.close();
-  }
-
-  @AfterClass
-  public static void afterClass() throws Exception {
-    searcher = null;
-    reader.close();
-    reader = null;
-    directory.close();
-    directory = null;
-  }
-
-  private TopDocs bboxQuery(double minLat, double maxLat, double minLon, double maxLon, int limit) throws Exception {
-    GeoPointInBBoxQuery q = new GeoPointInBBoxQuery(FIELD_NAME, TermEncoding.PREFIX, minLat, maxLat, minLon, maxLon);
-    return searcher.search(q, limit);
-  }
-
-  private TopDocs polygonQuery(double[] polyLats, double[] polyLons, int limit) throws Exception {
-    GeoPointInPolygonQuery q = new GeoPointInPolygonQuery(FIELD_NAME, TermEncoding.PREFIX, polyLats, polyLons);
-    return searcher.search(q, limit);
-  }
-
-  private TopDocs geoDistanceQuery(double lat, double lon, double radius, int limit) throws Exception {
-    GeoPointDistanceQuery q = new GeoPointDistanceQuery(FIELD_NAME, TermEncoding.PREFIX, lat, lon, radius);
-    return searcher.search(q, limit);
-  }
-
-  private TopDocs geoDistanceRangeQuery(double lat, double lon, double minRadius, double maxRadius, int limit)
-      throws Exception {
-    GeoPointDistanceRangeQuery q = new GeoPointDistanceRangeQuery(FIELD_NAME, TermEncoding.PREFIX, lat, lon, minRadius, maxRadius);
-    return searcher.search(q, limit);
-  }
-
-  public void testBBoxQuery() throws Exception {
-    TopDocs td = bboxQuery(32.778650, 32.778950, -96.7772, -96.77690000, 5);
-    assertEquals("GeoBoundingBoxQuery failed", 4, td.totalHits);
-  }
-
-  public void testPolyQuery() throws Exception {
-        TopDocs td = polygonQuery(
-            new double[]{33.073130, 32.9942669, 32.938386, 33.0374494,
-                33.1369762, 33.1162747, 33.073130, 33.073130},
-            new double[]{-96.7682647, -96.8280029, -96.6288757, -96.4929199,
-                         -96.6041564, -96.7449188, -96.76826477, -96.7682647},
-            5);
-    assertEquals("GeoPolygonQuery failed", 2, td.totalHits);
-  }
-
-  public void testPacManPolyQuery() throws Exception {
-    // pacman
-    double[] px = {0, 10, 10, 0, -8, -10, -8, 0, 10, 10, 0};
-    double[] py = {0, 5, 9, 10, 9, 0, -9, -10, -9, -5, 0};
-
-    // shape bbox
-    double xMinA = -10;
-    double xMaxA = 10;
-    double yMinA = -10;
-    double yMaxA = 10;
-
-    // candidate crosses cell
-    double xMin = 2;//-5;
-    double xMax = 11;//0.000001;
-    double yMin = -1;//0;
-    double yMax = 1;//5;
-
-    // test cell crossing poly
-    assertTrue(GeoRelationUtils.rectCrossesPolyApprox(yMin, yMax, xMin, yMax, py, px, yMinA, yMaxA, xMinA, xMaxA));
-    assertFalse(GeoRelationUtils.rectCrossesPolyApprox(0, 5, -5, 0.000001, py, px, yMin, yMax, xMin, xMax));
-    assertTrue(GeoRelationUtils.rectWithinPolyApprox(0, 5, -5, -2, py, px, yMin, yMax, xMin, xMax));
-  }
-
-  public void testBBoxCrossDateline() throws Exception {
-    TopDocs td = bboxQuery(-45.0, -44.0, 179.0, -179.0, 20);
-    assertEquals("BBoxCrossDateline query failed", 2, td.totalHits);
-  }
-
-  public void testWholeMap() throws Exception {
-    TopDocs td = bboxQuery(GeoUtils.MIN_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MIN_LON_INCL, GeoUtils.MAX_LON_INCL, 20);
-    assertEquals("testWholeMap failed", 24, td.totalHits);
-    td = polygonQuery(new double[] {GeoUtils.MIN_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MIN_LAT_INCL, GeoUtils.MIN_LAT_INCL},
-                      new double[] {GeoUtils.MIN_LON_INCL, GeoUtils.MIN_LON_INCL, GeoUtils.MAX_LON_INCL, GeoUtils.MAX_LON_INCL, GeoUtils.MIN_LON_INCL},
-                      20);    assertEquals("testWholeMap failed", 24, td.totalHits);
-  }
-
-  public void smallTest() throws Exception {
-    TopDocs td = geoDistanceQuery(40.720611, -73.998776, 1, 20);
-    assertEquals("smallTest failed", 2, td.totalHits);
-  }
-
-  // GeoBoundingBox should not accept invalid lat/lon
-  public void testInvalidBBox() throws Exception {
-    expectThrows(Exception.class, () -> {
-      bboxQuery(-92.0, -91.0, 179.0, 181.0, 20);
-    });
-  }
-
-  public void testGeoDistanceQuery() throws Exception {
-    TopDocs td = geoDistanceQuery(32.94823588839368, -96.4538113027811, 6000, 20);
-    assertEquals("GeoDistanceQuery failed", 2, td.totalHits);
-  }
-
-  /** see https://issues.apache.org/jira/browse/LUCENE-6905 */
-  public void testNonEmptyTermsEnum() throws Exception {
-    TopDocs td = geoDistanceQuery(-88.56029371730983, -177.23537676036358, 7757.999232959935, 20);
-    assertEquals("GeoDistanceQuery failed", 2, td.totalHits);
-  }
-
-  public void testMultiValuedQuery() throws Exception {
-    TopDocs td = bboxQuery(32.7559529921407, 32.7756745755423, -96.4538113027811, -96.7706036567688, 20);
-    // 3 single valued docs + 2 multi-valued docs
-    assertEquals("testMultiValuedQuery failed", 5, td.totalHits);
-  }
-
-  public void testTooBigRadius() throws Exception {
-    IllegalArgumentException expected = expectThrows(IllegalArgumentException.class, () -> {
-      geoDistanceQuery(85.0, 0.0, 4000000, 20);
-    });
-    assertTrue(expected.getMessage().contains("exceeds maxRadius"));
-  }
-
-  /**
-   * Explicitly large
-   */
-  public void testGeoDistanceQueryHuge() throws Exception {
-    TopDocs td = geoDistanceQuery(32.94823588839368, -96.4538113027811, 6000000, 20);
-    assertEquals("GeoDistanceQuery failed", 16, td.totalHits);
-  }
-
-  public void testGeoDistanceQueryCrossDateline() throws Exception {
-    TopDocs td = geoDistanceQuery(32.94823588839368, -179.9538113027811, 120000, 20);
-    assertEquals("GeoDistanceQuery failed", 3, td.totalHits);
-  }
-
-  // GeoDistanceQuery should not accept invalid lat/lon as origin
-  public void testInvalidGeoDistanceQuery() throws Exception {
-    expectThrows(Exception.class, () -> {
-      geoDistanceQuery(92.0, 181.0, 120000, 20);
-    });
-  }
-
-  public void testMaxDistanceRangeQuery() throws Exception {
-    TopDocs td = geoDistanceRangeQuery(0.0, 0.0, 10, 20000000, 20);
-    assertEquals("GeoDistanceRangeQuery failed", 24, td.totalHits);
-  }
-
-  public void testInvalidLatLon() throws Exception {
-    IllegalArgumentException e;
-    e= expectThrows(IllegalArgumentException.class,
-                    () -> {
-                      new GeoPointField("field", 180.0, 0.0, Field.Store.NO);
-                    });
-    assertEquals("invalid lat=180.0 for field \"field\"", e.getMessage());
-
-    e = expectThrows(IllegalArgumentException.class,
-                     () -> {
-                       new GeoPointField("field", 0.0, 190.0, Field.Store.NO);
-                     });
-    assertEquals("invalid lon=190.0 for field \"field\"", e.getMessage());
-  }
-}

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointQuery.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointQuery.java b/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointQuery.java
index 747cd1f..1a739a3 100644
--- a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointQuery.java
+++ b/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestGeoPointQuery.java
@@ -22,8 +22,6 @@ import org.apache.lucene.spatial.util.GeoEncodingUtils;
 import org.apache.lucene.spatial.geopoint.document.GeoPointField;
 import org.apache.lucene.spatial.geopoint.document.GeoPointField.TermEncoding;
 import org.apache.lucene.spatial.util.BaseGeoPointTestCase;
-import org.apache.lucene.spatial.util.GeoDistanceUtils;
-import org.apache.lucene.spatial.util.GeoRect;
 
 /**
  * random testing for GeoPoint query logic
@@ -31,12 +29,6 @@ import org.apache.lucene.spatial.util.GeoRect;
  * @lucene.experimental
  */
 public class TestGeoPointQuery extends BaseGeoPointTestCase {
-
-  @Override
-  protected double maxRadius(double latitude, double longitude) {
-    // TODO: clean this up
-    return GeoDistanceUtils.maxRadialDistanceMeters(latitude, longitude);
-  }
   
   @Override
   protected double quantizeLat(double lat) {
@@ -54,8 +46,8 @@ public class TestGeoPointQuery extends BaseGeoPointTestCase {
   }
 
   @Override
-  protected Query newRectQuery(String field, GeoRect rect) {
-    return new GeoPointInBBoxQuery(field, TermEncoding.PREFIX, rect.minLat, rect.maxLat, rect.minLon, rect.maxLon);
+  protected Query newRectQuery(String field, double minLat, double maxLat, double minLon, double maxLon) {
+    return new GeoPointInBBoxQuery(field, TermEncoding.PREFIX, minLat, maxLat, minLon, maxLon);
   }
 
   @Override

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointField.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointField.java b/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointField.java
deleted file mode 100644
index beab5b9..0000000
--- a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointField.java
+++ /dev/null
@@ -1,242 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You 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.lucene.spatial.geopoint.search;
-
-import org.apache.lucene.analysis.MockAnalyzer;
-import org.apache.lucene.document.Document;
-import org.apache.lucene.document.Field;
-import org.apache.lucene.document.StringField;
-import org.apache.lucene.index.IndexReader;
-import org.apache.lucene.index.RandomIndexWriter;
-import org.apache.lucene.search.IndexSearcher;
-import org.apache.lucene.search.TopDocs;
-import org.apache.lucene.spatial.geopoint.document.GeoPointField;
-import org.apache.lucene.spatial.geopoint.document.GeoPointField.TermEncoding;
-import org.apache.lucene.spatial.util.GeoRelationUtils;
-import org.apache.lucene.spatial.util.GeoUtils;
-import org.apache.lucene.store.Directory;
-import org.apache.lucene.util.LuceneTestCase;
-import org.apache.lucene.util.TestUtil;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-
-/** Simple tests for GeoPoint with legacy numeric encoding 
- * @deprecated remove this when TermEncoding.NUMERIC is removed */
-@Deprecated
-public class TestLegacyGeoPointField extends LuceneTestCase {
-  
-  private static Directory directory = null;
-  private static IndexReader reader = null;
-  private static IndexSearcher searcher = null;
-  private static final String FIELD_NAME = "point";
-
-  @BeforeClass
-  public static void beforeClass() throws Exception {
-    directory = newDirectory();
-
-    RandomIndexWriter writer = new RandomIndexWriter(random(), directory,
-            newIndexWriterConfig(new MockAnalyzer(random()))
-                    .setMaxBufferedDocs(TestUtil.nextInt(random(), 100, 1000))
-                    .setMergePolicy(newLogMergePolicy()));
-
-    // this is a simple systematic test
-    GeoPointField[] pts = new GeoPointField[] {
-        new GeoPointField(FIELD_NAME, 32.763420, -96.774, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.7559529921407, -96.7759895324707, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.77866942010977, -96.77701950073242, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.7756745755423, -96.7706036567688, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 27.703618681345585, -139.73458170890808, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.94823588839368, -96.4538113027811, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 33.06047141970814, -96.65084838867188, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.778650, -96.7772, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, -88.56029371730983, -177.23537676036358, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 33.541429799076354, -26.779373834241003, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 26.774024500421728, -77.35379276106497, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, -90.0, -14.796283808944777, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.94823588839368, -178.8538113027811, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 32.94823588839368, 178.8538113027811, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, 40.720611, -73.998776, GeoPointField.NUMERIC_TYPE_NOT_STORED),
-        new GeoPointField(FIELD_NAME, -44.5, -179.5, GeoPointField.NUMERIC_TYPE_NOT_STORED)};
-
-    for (GeoPointField p : pts) {
-        Document doc = new Document();
-        doc.add(p);
-        writer.addDocument(doc);
-    }
-
-    // add explicit multi-valued docs
-    for (int i=0; i<pts.length; i+=2) {
-      Document doc = new Document();
-      doc.add(pts[i]);
-      doc.add(pts[i+1]);
-      writer.addDocument(doc);
-    }
-
-    // index random string documents
-    for (int i=0; i<random().nextInt(10); ++i) {
-      Document doc = new Document();
-      doc.add(new StringField("string", Integer.toString(i), Field.Store.NO));
-      writer.addDocument(doc);
-    }
-
-    reader = writer.getReader();
-    searcher = newSearcher(reader);
-    writer.close();
-  }
-
-  @AfterClass
-  public static void afterClass() throws Exception {
-    searcher = null;
-    reader.close();
-    reader = null;
-    directory.close();
-    directory = null;
-  }
-
-  private TopDocs bboxQuery(double minLat, double maxLat, double minLon, double maxLon, int limit) throws Exception {
-    GeoPointInBBoxQuery q = new GeoPointInBBoxQuery(FIELD_NAME, TermEncoding.NUMERIC, minLat, maxLat, minLon, maxLon);
-    return searcher.search(q, limit);
-  }
-
-  private TopDocs polygonQuery(double[] polyLats, double[] polyLons, int limit) throws Exception {
-    GeoPointInPolygonQuery q = new GeoPointInPolygonQuery(FIELD_NAME, TermEncoding.NUMERIC, polyLats, polyLons);
-    return searcher.search(q, limit);
-  }
-
-  private TopDocs geoDistanceQuery(double lat, double lon, double radius, int limit) throws Exception {
-    GeoPointDistanceQuery q = new GeoPointDistanceQuery(FIELD_NAME, TermEncoding.NUMERIC, lat, lon, radius);
-    return searcher.search(q, limit);
-  }
-
-  private TopDocs geoDistanceRangeQuery(double lat, double lon, double minRadius, double maxRadius, int limit)
-      throws Exception {
-    GeoPointDistanceRangeQuery q = new GeoPointDistanceRangeQuery(FIELD_NAME, TermEncoding.NUMERIC, lat, lon, minRadius, maxRadius);
-    return searcher.search(q, limit);
-  }
-
-  public void testBBoxQuery() throws Exception {
-    TopDocs td = bboxQuery(32.778650, 32.778950, -96.7772, -96.77690000, 5);
-    assertEquals("GeoBoundingBoxQuery failed", 4, td.totalHits);
-  }
-
-  public void testPolyQuery() throws Exception {
-    TopDocs td = polygonQuery(
-        new double[]{33.073130, 32.9942669, 32.938386, 33.0374494,
-            33.1369762, 33.1162747, 33.073130, 33.073130},
-        new double[]{-96.7682647, -96.8280029, -96.6288757, -96.4929199,
-                     -96.6041564, -96.7449188, -96.76826477, -96.7682647},
-        5);
-    assertEquals("GeoPolygonQuery failed", 2, td.totalHits);
-  }
-
-  public void testPacManPolyQuery() throws Exception {
-    // pacman
-    double[] px = {0, 10, 10, 0, -8, -10, -8, 0, 10, 10, 0};
-    double[] py = {0, 5, 9, 10, 9, 0, -9, -10, -9, -5, 0};
-
-    // shape bbox
-    double xMinA = -10;
-    double xMaxA = 10;
-    double yMinA = -10;
-    double yMaxA = 10;
-
-    // candidate crosses cell
-    double xMin = 2;//-5;
-    double xMax = 11;//0.000001;
-    double yMin = -1;//0;
-    double yMax = 1;//5;
-
-    // test cell crossing poly
-    assertTrue(GeoRelationUtils.rectCrossesPolyApprox(yMin, yMax, xMin, yMax, py, px, yMinA, yMaxA, xMinA, xMaxA));
-    assertFalse(GeoRelationUtils.rectCrossesPolyApprox(0, 5, -5, 0.000001, py, px, yMin, yMax, xMin, xMax));
-    assertTrue(GeoRelationUtils.rectWithinPolyApprox(0, 5, -5, -2, py, px, yMin, yMax, xMin, xMax));
-  }
-
-  public void testBBoxCrossDateline() throws Exception {
-    TopDocs td = bboxQuery(-45.0, -44.0, 179.0, -179.0, 20);
-    assertEquals("BBoxCrossDateline query failed", 2, td.totalHits);
-  }
-
-  public void testWholeMap() throws Exception {
-    TopDocs td = bboxQuery(GeoUtils.MIN_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MIN_LON_INCL, GeoUtils.MAX_LON_INCL, 20);
-    assertEquals("testWholeMap failed", 24, td.totalHits);
-    td = polygonQuery(new double[] {GeoUtils.MIN_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MIN_LAT_INCL, GeoUtils.MIN_LAT_INCL},
-                      new double[] {GeoUtils.MIN_LON_INCL, GeoUtils.MIN_LON_INCL, GeoUtils.MAX_LON_INCL, GeoUtils.MAX_LON_INCL, GeoUtils.MIN_LON_INCL},
-                      20);    assertEquals("testWholeMap failed", 24, td.totalHits);
-  }
-
-  public void smallTest() throws Exception {
-    TopDocs td = geoDistanceQuery(40.720611, -73.998776, 1, 20);
-    assertEquals("smallTest failed", 2, td.totalHits);
-  }
-
-  // GeoBoundingBox should not accept invalid lat/lon
-  public void testInvalidBBox() throws Exception {
-    expectThrows(Exception.class, () -> {
-      bboxQuery(-92.0, -91.0, 179.0, 181.0, 20);
-    });
-  }
-
-  public void testGeoDistanceQuery() throws Exception {
-    TopDocs td = geoDistanceQuery(32.94823588839368, -96.4538113027811, 6000, 20);
-    assertEquals("GeoDistanceQuery failed", 2, td.totalHits);
-  }
-
-  /** see https://issues.apache.org/jira/browse/LUCENE-6905 */
-  public void testNonEmptyTermsEnum() throws Exception {
-    TopDocs td = geoDistanceQuery(-88.56029371730983, -177.23537676036358, 7757.999232959935, 20);
-    assertEquals("GeoDistanceQuery failed", 2, td.totalHits);
-  }
-
-  public void testMultiValuedQuery() throws Exception {
-    TopDocs td = bboxQuery(32.7559529921407, 32.7756745755423, -96.4538113027811, -96.7706036567688, 20);
-    // 3 single valued docs + 2 multi-valued docs
-    assertEquals("testMultiValuedQuery failed", 5, td.totalHits);
-  }
-
-  public void testTooBigRadius() throws Exception {
-    IllegalArgumentException expected = expectThrows(IllegalArgumentException.class, () -> {
-      geoDistanceQuery(85.0, 0.0, 4000000, 20);
-    });
-    assertTrue(expected.getMessage().contains("exceeds maxRadius"));
-  }
-
-  /**
-   * Explicitly large
-   */
-  public void testGeoDistanceQueryHuge() throws Exception {
-    TopDocs td = geoDistanceQuery(32.94823588839368, -96.4538113027811, 6000000, 20);
-    assertEquals("GeoDistanceQuery failed", 16, td.totalHits);
-  }
-
-  public void testGeoDistanceQueryCrossDateline() throws Exception {
-    TopDocs td = geoDistanceQuery(32.94823588839368, -179.9538113027811, 120000, 20);
-    assertEquals("GeoDistanceQuery failed", 3, td.totalHits);
-  }
-
-  // GeoDistanceQuery should not accept invalid lat/lon as origin
-  public void testInvalidGeoDistanceQuery() throws Exception {
-    expectThrows(Exception.class, () -> {
-      geoDistanceQuery(92.0, 181.0, 120000, 20);
-    });
-  }
-
-  public void testMaxDistanceRangeQuery() throws Exception {
-    TopDocs td = geoDistanceRangeQuery(0.0, 0.0, 10, 20000000, 20);
-    assertEquals("GeoDistanceRangeQuery failed", 24, td.totalHits);
-  }
-}

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointQuery.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointQuery.java b/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointQuery.java
index 73b3082..c2f74f16 100644
--- a/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointQuery.java
+++ b/lucene/spatial/src/test/org/apache/lucene/spatial/geopoint/search/TestLegacyGeoPointQuery.java
@@ -22,8 +22,6 @@ import org.apache.lucene.spatial.util.GeoEncodingUtils;
 import org.apache.lucene.spatial.geopoint.document.GeoPointField;
 import org.apache.lucene.spatial.geopoint.document.GeoPointField.TermEncoding;
 import org.apache.lucene.spatial.util.BaseGeoPointTestCase;
-import org.apache.lucene.spatial.util.GeoDistanceUtils;
-import org.apache.lucene.spatial.util.GeoRect;
 
 /**
  * random testing for GeoPoint query logic (with deprecated numeric encoding)
@@ -31,12 +29,6 @@ import org.apache.lucene.spatial.util.GeoRect;
  */
 @Deprecated
 public class TestLegacyGeoPointQuery extends BaseGeoPointTestCase {
-
-  @Override
-  protected double maxRadius(double latitude, double longitude) {
-    // TODO: clean this up
-    return GeoDistanceUtils.maxRadialDistanceMeters(latitude, longitude);
-  }
   
   @Override
   protected double quantizeLat(double lat) {
@@ -54,8 +46,8 @@ public class TestLegacyGeoPointQuery extends BaseGeoPointTestCase {
   }
 
   @Override
-  protected Query newRectQuery(String field, GeoRect rect) {
-    return new GeoPointInBBoxQuery(field, TermEncoding.NUMERIC, rect.minLat, rect.maxLat, rect.minLon, rect.maxLon);
+  protected Query newRectQuery(String field, double minLat, double maxLat, double minLon, double maxLon) {
+    return new GeoPointInBBoxQuery(field, TermEncoding.NUMERIC, minLat, maxLat, minLon, maxLon);
   }
 
   @Override

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/test/org/apache/lucene/spatial/util/BaseGeoPointTestCase.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/test/org/apache/lucene/spatial/util/BaseGeoPointTestCase.java b/lucene/spatial/src/test/org/apache/lucene/spatial/util/BaseGeoPointTestCase.java
index 3943a92..4d25451 100644
--- a/lucene/spatial/src/test/org/apache/lucene/spatial/util/BaseGeoPointTestCase.java
+++ b/lucene/spatial/src/test/org/apache/lucene/spatial/util/BaseGeoPointTestCase.java
@@ -29,6 +29,7 @@ import java.util.Set;
 import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.atomic.AtomicBoolean;
 
+import org.apache.lucene.analysis.MockAnalyzer;
 import org.apache.lucene.codecs.FilterCodec;
 import org.apache.lucene.codecs.PointsFormat;
 import org.apache.lucene.codecs.PointsReader;
@@ -39,6 +40,7 @@ import org.apache.lucene.document.Document;
 import org.apache.lucene.document.Field;
 import org.apache.lucene.document.NumericDocValuesField;
 import org.apache.lucene.document.StoredField;
+import org.apache.lucene.document.StringField;
 import org.apache.lucene.index.DirectoryReader;
 import org.apache.lucene.index.IndexReader;
 import org.apache.lucene.index.IndexWriter;
@@ -65,8 +67,17 @@ import org.apache.lucene.util.TestUtil;
 import org.apache.lucene.util.bkd.BKDWriter;
 import org.junit.BeforeClass;
 
-// TODO: cutover TestGeoUtils too?
-
+/**
+ * Abstract class to do basic tests for a geospatial impl (high level
+ * fields and queries)
+ * NOTE: This test focuses on geospatial (distance queries, polygon
+ * queries, etc) indexing and search, not any underlying storage
+ * format or encoding: it merely supplies two hooks for the encoding
+ * so that tests can be exact. The [stretch] goal is for this test to be
+ * so thorough in testing a new geo impl that if this
+ * test passes, then all Lucene/Solr tests should also pass.  Ie,
+ * if there is some bug in a given geo impl that this
+ * test fails to catch then this test needs to be improved! */
 public abstract class BaseGeoPointTestCase extends LuceneTestCase {
 
   protected static final String FIELD_NAME = "point";
@@ -109,6 +120,195 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
     double off = Math.abs((lat_deg + 90) % 360);
     return (off <= 180 ? off : 360-off) - 90;
   }
+  
+  /** Valid values that should not cause exception */
+  public void testIndexExtremeValues() {
+    Document document = new Document();
+    addPointToDoc("foo", document, 90.0, 180.0);
+    addPointToDoc("foo", document, 90.0, -180.0);
+    addPointToDoc("foo", document, -90.0, 180.0);
+    addPointToDoc("foo", document, -90.0, -180.0);
+  }
+  
+  /** Invalid values */
+  public void testIndexOutOfRangeValues() {
+    Document document = new Document();
+    IllegalArgumentException expected;
+
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, Math.nextUp(90.0), 50.0);
+    });
+    assertTrue(expected.getMessage().contains("invalid latitude"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, Math.nextDown(-90.0), 50.0);
+    });
+    assertTrue(expected.getMessage().contains("invalid latitude"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, 90.0, Math.nextUp(180.0));
+    });
+    assertTrue(expected.getMessage().contains("invalid longitude"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, 90.0, Math.nextDown(-180.0));
+    });
+    assertTrue(expected.getMessage().contains("invalid longitude"));
+  }
+  
+  /** NaN: illegal */
+  public void testIndexNaNValues() {
+    Document document = new Document();
+    IllegalArgumentException expected;
+
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, Double.NaN, 50.0);
+    });
+    assertTrue(expected.getMessage().contains("invalid latitude"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, 50.0, Double.NaN);
+    });
+    assertTrue(expected.getMessage().contains("invalid longitude"));
+  }
+  
+  /** Inf: illegal */
+  public void testIndexInfValues() {
+    Document document = new Document();
+    IllegalArgumentException expected;
+
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, Double.POSITIVE_INFINITY, 50.0);
+    });
+    assertTrue(expected.getMessage().contains("invalid latitude"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, Double.NEGATIVE_INFINITY, 50.0);
+    });
+    assertTrue(expected.getMessage().contains("invalid latitude"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, 50.0, Double.POSITIVE_INFINITY);
+    });
+    assertTrue(expected.getMessage().contains("invalid longitude"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      addPointToDoc("foo", document, 50.0, Double.NEGATIVE_INFINITY);
+    });
+    assertTrue(expected.getMessage().contains("invalid longitude"));
+  }
+  
+  /** Add a single point and search for it in a box */
+  // NOTE: we don't currently supply an exact search, only ranges, because of the lossiness...
+  public void testBoxBasics() throws Exception {
+    Directory dir = newDirectory();
+    RandomIndexWriter writer = new RandomIndexWriter(random(), dir);
+
+    // add a doc with a point
+    Document document = new Document();
+    addPointToDoc("field", document, 18.313694, -65.227444);
+    writer.addDocument(document);
+    
+    // search and verify we found our doc
+    IndexReader reader = writer.getReader();
+    IndexSearcher searcher = newSearcher(reader);
+    assertEquals(1, searcher.count(newRectQuery("field", 18, 19, -66, -65)));
+
+    reader.close();
+    writer.close();
+    dir.close();
+  }
+  
+
+  // box should not accept invalid lat/lon
+  public void testBoxInvalidCoordinates() throws Exception {
+    expectThrows(Exception.class, () -> {
+      newRectQuery("field", -92.0, -91.0, 179.0, 181.0);
+    });
+  }
+
+  /** test we can search for a point */
+  public void testDistanceBasics() throws Exception {
+    Directory dir = newDirectory();
+    RandomIndexWriter writer = new RandomIndexWriter(random(), dir);
+
+    // add a doc with a location
+    Document document = new Document();
+    addPointToDoc("field", document, 18.313694, -65.227444);
+    writer.addDocument(document);
+    
+    // search within 50km and verify we found our doc
+    IndexReader reader = writer.getReader();
+    IndexSearcher searcher = newSearcher(reader);
+    assertEquals(1, searcher.count(newDistanceQuery("field", 18, -65, 50_000)));
+
+    reader.close();
+    writer.close();
+    dir.close();
+  }
+  
+  /** distance query should not accept invalid lat/lon as origin */
+  public void testDistanceIllegal() throws Exception {
+    expectThrows(Exception.class, () -> {
+      newDistanceQuery("field", 92.0, 181.0, 120000);
+    });
+  }
+  /** negative distance queries are not allowed */
+  public void testDistanceNegative() {
+    IllegalArgumentException expected = expectThrows(IllegalArgumentException.class, () -> {
+      newDistanceQuery("field", 18, 19, -1);
+    });
+    assertTrue(expected.getMessage().contains("radiusMeters"));
+    assertTrue(expected.getMessage().contains("invalid"));
+  }
+  
+  /** NaN distance queries are not allowed */
+  public void testDistanceNaN() {
+    IllegalArgumentException expected = expectThrows(IllegalArgumentException.class, () -> {
+      newDistanceQuery("field", 18, 19, Double.NaN);
+    });
+    assertTrue(expected.getMessage().contains("radiusMeters"));
+    assertTrue(expected.getMessage().contains("invalid"));
+  }
+  
+  /** Inf distance queries are not allowed */
+  public void testDistanceInf() {
+    IllegalArgumentException expected;
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      newDistanceQuery("field", 18, 19, Double.POSITIVE_INFINITY);
+    });
+    assertTrue(expected.getMessage().contains("radiusMeters"));
+    assertTrue(expected.getMessage().contains("invalid"));
+    
+    expected = expectThrows(IllegalArgumentException.class, () -> {
+      newDistanceQuery("field", 18, 19, Double.NEGATIVE_INFINITY);
+    });
+    assertTrue(expected.getMessage(), expected.getMessage().contains("radiusMeters"));
+    assertTrue(expected.getMessage().contains("invalid"));
+  }
+  
+  /** test we can search for a polygon */
+  public void testPolygonBasics() throws Exception {
+    Directory dir = newDirectory();
+    RandomIndexWriter writer = new RandomIndexWriter(random(), dir);
+
+    // add a doc with a point
+    Document document = new Document();
+    addPointToDoc("field", document, 18.313694, -65.227444);
+    writer.addDocument(document);
+    
+    // search and verify we found our doc
+    IndexReader reader = writer.getReader();
+    IndexSearcher searcher = newSearcher(reader);
+    assertEquals(1, searcher.count(newPolygonQuery("field",
+                                                   new double[] { 18, 18, 19, 19, 18 },
+                                                   new double[] { -66, -65, -65, -66, -66 })));
+
+    reader.close();
+    writer.close();
+    dir.close();
+  }
 
   // A particularly tricky adversary for BKD tree:
   public void testSamePointManyTimes() throws Exception {
@@ -275,7 +475,7 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
         System.out.println("\nTEST: iter=" + iter + " rect=" + rect);
       }
 
-      Query query = newRectQuery(FIELD_NAME, rect);
+      Query query = newRectQuery(FIELD_NAME, rect.minLat, rect.maxLat, rect.minLon, rect.maxLon);
 
       final FixedBitSet hits = new FixedBitSet(r.maxDoc());
       s.search(query, new SimpleCollector() {
@@ -455,10 +655,6 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
   protected double quantizeLon(double lon) {
     return lon;
   }
-  
-  protected double maxRadius(double latitude, double longitude) {
-    return 50000000D; // bigger than earth, shouldnt matter
-  }
 
   protected GeoRect randomRect(boolean small, boolean canCrossDateLine) {
     double lat0 = randomLat(small);
@@ -486,7 +682,7 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
 
   protected abstract void addPointToDoc(String field, Document doc, double lat, double lon);
 
-  protected abstract Query newRectQuery(String field, GeoRect bbox);
+  protected abstract Query newRectQuery(String field, double minLat, double maxLat, double minLon, double maxLon);
 
   protected abstract Query newDistanceQuery(String field, double centerLat, double centerLon, double radiusMeters);
 
@@ -708,7 +904,7 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
                 // Rect: don't allow dateline crossing when testing small:
                 final GeoRect rect = randomRect(small, small == false);
 
-                query = newRectQuery(FIELD_NAME, rect);
+                query = newRectQuery(FIELD_NAME, rect.minLat, rect.maxLat, rect.minLon, rect.maxLon);
 
                 verifyHits = new VerifyHits() {
                     @Override
@@ -875,7 +1071,7 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
     }
     IndexReader r = w.getReader();
     IndexSearcher s = newSearcher(r, false);
-    assertEquals(8, s.count(newRectQuery(FIELD_NAME, rect)));
+    assertEquals(8, s.count(newRectQuery(FIELD_NAME, rect.minLat, rect.maxLat, rect.minLon, rect.maxLon)));
     r.close();
     w.close();
     dir.close();
@@ -936,7 +1132,7 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
     for (int i = 0; i < numQueries; i++) {
       double lat = -90 + 180.0 * random().nextDouble();
       double lon = -180 + 360.0 * random().nextDouble();
-      double radius = maxRadius(lat, lon) * random().nextDouble();
+      double radius = 50000000D * random().nextDouble();
   
       BitSet expected = new BitSet();
       for (int doc = 0; doc < reader.maxDoc(); doc++) {
@@ -977,10 +1173,10 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
 
     GeoRect rect = randomRect(false, true);
 
-    q1 = newRectQuery("field", rect);
-    q2 = newRectQuery("field", rect);
+    q1 = newRectQuery("field", rect.minLat, rect.maxLat, rect.minLon, rect.maxLon);
+    q2 = newRectQuery("field", rect.minLat, rect.maxLat, rect.minLon, rect.maxLon);
     assertEquals(q1, q2);
-    assertFalse(q1.equals(newRectQuery("field2", rect)));
+    assertFalse(q1.equals(newRectQuery("field2", rect.minLat, rect.maxLat, rect.minLon, rect.maxLon)));
 
     double lat = randomLat(false);
     double lon = randomLon(false);
@@ -1014,4 +1210,132 @@ public abstract class BaseGeoPointTestCase extends LuceneTestCase {
     assertEquals(q1, q2);
     assertFalse(q1.equals(newPolygonQuery("field2", lats, lons)));
   }
+  
+  /** return topdocs over a small set of points in field "point" */
+  private TopDocs searchSmallSet(Query query, int size) throws Exception {
+    // this is a simple systematic test, indexing these points
+    double[][] pts = new double[][] {
+        { 32.763420,          -96.774             },
+        { 32.7559529921407,   -96.7759895324707   },
+        { 32.77866942010977,  -96.77701950073242  },
+        { 32.7756745755423,   -96.7706036567688   },
+        { 27.703618681345585, -139.73458170890808 },
+        { 32.94823588839368,  -96.4538113027811   },
+        { 33.06047141970814,  -96.65084838867188  },
+        { 32.778650,          -96.7772            },
+        { -88.56029371730983, -177.23537676036358 },
+        { 33.541429799076354, -26.779373834241003 },
+        { 26.774024500421728, -77.35379276106497  },
+        { -90.0,              -14.796283808944777 },
+        { 32.94823588839368,  -178.8538113027811  },
+        { 32.94823588839368,  178.8538113027811   },
+        { 40.720611,          -73.998776          },
+        { -44.5,              -179.5              }
+    };
+    
+    Directory directory = newDirectory();
+
+    RandomIndexWriter writer = new RandomIndexWriter(random(), directory,
+            newIndexWriterConfig(new MockAnalyzer(random()))
+                    .setMaxBufferedDocs(TestUtil.nextInt(random(), 100, 1000))
+                    .setMergePolicy(newLogMergePolicy()));
+
+    for (double p[] : pts) {
+        Document doc = new Document();
+        addPointToDoc("point", doc, p[0], p[1]);
+        writer.addDocument(doc);
+    }
+
+    // add explicit multi-valued docs
+    for (int i=0; i<pts.length; i+=2) {
+      Document doc = new Document();
+      addPointToDoc("point", doc, pts[i][0], pts[i][1]);
+      addPointToDoc("point", doc, pts[i+1][0], pts[i+1][1]);
+      writer.addDocument(doc);
+    }
+
+    // index random string documents
+    for (int i=0; i<random().nextInt(10); ++i) {
+      Document doc = new Document();
+      doc.add(new StringField("string", Integer.toString(i), Field.Store.NO));
+      writer.addDocument(doc);
+    }
+
+    IndexReader reader = writer.getReader();
+    writer.close();
+
+    IndexSearcher searcher = newSearcher(reader);
+    TopDocs topDocs = searcher.search(query, size);
+    reader.close();
+    directory.close();
+    return topDocs;
+  }
+  
+  public void testSmallSetRect() throws Exception {
+    TopDocs td = searchSmallSet(newRectQuery("point", 32.778650, 32.778950, -96.7772, -96.77690000), 5);
+    assertEquals(4, td.totalHits);
+  }
+
+  public void testSmallSetDateline() throws Exception {
+    TopDocs td = searchSmallSet(newRectQuery("point", -45.0, -44.0, 179.0, -179.0), 20);
+    assertEquals(2, td.totalHits);
+  }
+
+  public void testSmallSetMultiValued() throws Exception {
+    TopDocs td = searchSmallSet(newRectQuery("point", 32.7559529921407, 32.7756745755423, -96.4538113027811, -96.7706036567688), 20);
+    // 3 single valued docs + 2 multi-valued docs
+    assertEquals(5, td.totalHits);
+  }
+  
+  public void testSmallSetWholeMap() throws Exception {
+    TopDocs td = searchSmallSet(newRectQuery("point", GeoUtils.MIN_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MIN_LON_INCL, GeoUtils.MAX_LON_INCL), 20);
+    assertEquals(24, td.totalHits);
+  }
+  
+  public void testSmallSetPoly() throws Exception {
+    TopDocs td = searchSmallSet(newPolygonQuery("point",
+        new double[]{33.073130, 32.9942669, 32.938386, 33.0374494,
+            33.1369762, 33.1162747, 33.073130, 33.073130},
+        new double[]{-96.7682647, -96.8280029, -96.6288757, -96.4929199,
+                     -96.6041564, -96.7449188, -96.76826477, -96.7682647}),
+        5);
+    assertEquals(2, td.totalHits);
+  }
+
+  public void testSmallSetPolyWholeMap() throws Exception {
+    TopDocs td = searchSmallSet(newPolygonQuery("point",
+                      new double[] {GeoUtils.MIN_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MAX_LAT_INCL, GeoUtils.MIN_LAT_INCL, GeoUtils.MIN_LAT_INCL},
+                      new double[] {GeoUtils.MIN_LON_INCL, GeoUtils.MIN_LON_INCL, GeoUtils.MAX_LON_INCL, GeoUtils.MAX_LON_INCL, GeoUtils.MIN_LON_INCL}),
+                      20);    
+    assertEquals("testWholeMap failed", 24, td.totalHits);
+  }
+
+  public void testSmallSetDistance() throws Exception {
+    TopDocs td = searchSmallSet(newDistanceQuery("point", 32.94823588839368, -96.4538113027811, 6000), 20);
+    assertEquals(2, td.totalHits);
+  }
+  
+  public void testSmallSetTinyDistance() throws Exception {
+    TopDocs td = searchSmallSet(newDistanceQuery("point", 40.720611, -73.998776, 1), 20);
+    assertEquals(2, td.totalHits);
+  }
+
+  /** see https://issues.apache.org/jira/browse/LUCENE-6905 */
+  public void testSmallSetDistanceNotEmpty() throws Exception {
+    TopDocs td = searchSmallSet(newDistanceQuery("point", -88.56029371730983, -177.23537676036358, 7757.999232959935), 20);
+    assertEquals(2, td.totalHits);
+  }
+
+  /**
+   * Explicitly large
+   */
+  public void testSmallSetHugeDistance() throws Exception {
+    TopDocs td = searchSmallSet(newDistanceQuery("point", 32.94823588839368, -96.4538113027811, 6000000), 20);
+    assertEquals(16, td.totalHits);
+  }
+
+  public void testSmallSetDistanceDateline() throws Exception {
+    TopDocs td = searchSmallSet(newDistanceQuery("point", 32.94823588839368, -179.9538113027811, 120000), 20);
+    assertEquals(3, td.totalHits);
+  }
 }

http://git-wip-us.apache.org/repos/asf/lucene-solr/blob/139aa0be/lucene/spatial/src/test/org/apache/lucene/spatial/util/TestGeoUtils.java
----------------------------------------------------------------------
diff --git a/lucene/spatial/src/test/org/apache/lucene/spatial/util/TestGeoUtils.java b/lucene/spatial/src/test/org/apache/lucene/spatial/util/TestGeoUtils.java
index 49a6411..15fa29c 100644
--- a/lucene/spatial/src/test/org/apache/lucene/spatial/util/TestGeoUtils.java
+++ b/lucene/spatial/src/test/org/apache/lucene/spatial/util/TestGeoUtils.java
@@ -298,4 +298,27 @@ public class TestGeoUtils extends LuceneTestCase {
       assertFalse(rect.crossesDateline());
     }
   }
+  
+  public void testPacManPolyQuery() throws Exception {
+    // pacman
+    double[] px = {0, 10, 10, 0, -8, -10, -8, 0, 10, 10, 0};
+    double[] py = {0, 5, 9, 10, 9, 0, -9, -10, -9, -5, 0};
+
+    // shape bbox
+    double xMinA = -10;
+    double xMaxA = 10;
+    double yMinA = -10;
+    double yMaxA = 10;
+
+    // candidate crosses cell
+    double xMin = 2;//-5;
+    double xMax = 11;//0.000001;
+    double yMin = -1;//0;
+    double yMax = 1;//5;
+
+    // test cell crossing poly
+    assertTrue(GeoRelationUtils.rectCrossesPolyApprox(yMin, yMax, xMin, yMax, py, px, yMinA, yMaxA, xMinA, xMaxA));
+    assertFalse(GeoRelationUtils.rectCrossesPolyApprox(0, 5, -5, 0.000001, py, px, yMin, yMax, xMin, xMax));
+    assertTrue(GeoRelationUtils.rectWithinPolyApprox(0, 5, -5, -2, py, px, yMin, yMax, xMin, xMax));
+  }
 }