Geo search across anti-meridian doesn't work, closes #363.
This commit is contained in:
parent
b31b0e979c
commit
4e661c165a
|
@ -75,6 +75,7 @@ public class GeoBoundingBoxFilter extends Filter {
|
|||
final NumericFieldData latFieldData = (NumericFieldData) fieldDataCache.cache(fieldDataType, reader, latFieldName);
|
||||
final NumericFieldData lonFieldData = (NumericFieldData) fieldDataCache.cache(fieldDataType, reader, lonFieldName);
|
||||
|
||||
//checks to see if bounding box crosses 180 degrees
|
||||
if (topLeft.lon > bottomRight.lon) {
|
||||
return new GetDocSet(reader.maxDoc()) {
|
||||
@Override public boolean get(int doc) throws IOException {
|
||||
|
@ -86,17 +87,33 @@ public class GeoBoundingBoxFilter extends Filter {
|
|||
double[] lats = latFieldData.doubleValues(doc);
|
||||
double[] lons = latFieldData.doubleValues(doc);
|
||||
for (int i = 0; i < lats.length; i++) {
|
||||
if (topLeft.lon >= lons[i] && bottomRight.lon <= lons[i]
|
||||
&& topLeft.lat >= lats[i] && bottomRight.lat <= lats[i]) {
|
||||
return true;
|
||||
double lat = lats[i];
|
||||
double lon = lons[i];
|
||||
if (lon < 0) {
|
||||
if (-180.0 <= lon && bottomRight.lon >= lon
|
||||
&& topLeft.lat >= lat && bottomRight.lat <= lat) {
|
||||
return true;
|
||||
}
|
||||
} else {
|
||||
if (topLeft.lon <= lon && 180 >= lon
|
||||
&& topLeft.lat >= lat && bottomRight.lat <= lat) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
double lat = latFieldData.doubleValue(doc);
|
||||
double lon = lonFieldData.doubleValue(doc);
|
||||
if (topLeft.lon >= lon && bottomRight.lon <= lon
|
||||
&& topLeft.lat >= lat && bottomRight.lat <= lat) {
|
||||
return true;
|
||||
if (lon < 0) {
|
||||
if (-180.0 <= lon && bottomRight.lon >= lon
|
||||
&& topLeft.lat >= lat && bottomRight.lat <= lat) {
|
||||
return true;
|
||||
}
|
||||
} else {
|
||||
if (topLeft.lon <= lon && 180 >= lon
|
||||
&& topLeft.lat >= lat && bottomRight.lat <= lat) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
|
|
|
@ -27,6 +27,7 @@ import org.testng.annotations.AfterClass;
|
|||
import org.testng.annotations.BeforeClass;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
import static org.elasticsearch.common.settings.ImmutableSettings.*;
|
||||
import static org.elasticsearch.common.xcontent.XContentFactory.*;
|
||||
import static org.elasticsearch.index.query.xcontent.FilterBuilders.*;
|
||||
import static org.elasticsearch.index.query.xcontent.QueryBuilders.*;
|
||||
|
@ -117,5 +118,85 @@ public class GeoBoundingBoxTests extends AbstractNodesTests {
|
|||
assertThat(hit.id(), anyOf(equalTo("1"), equalTo("3"), equalTo("5")));
|
||||
}
|
||||
}
|
||||
|
||||
@Test public void limitsBoundingBoxTest() throws Exception {
|
||||
try {
|
||||
client.admin().indices().prepareDelete("test").execute().actionGet();
|
||||
} catch (Exception e) {
|
||||
// ignore
|
||||
}
|
||||
client.admin().indices().prepareCreate("test").setSettings(settingsBuilder().put("number_of_shards", "1")).execute().actionGet();
|
||||
client.admin().cluster().prepareHealth().setWaitForGreenStatus().execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "1").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 40).field("lon", -20).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "2").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 40).field("lon", -10).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "3").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 40).field("lon", 10).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "4").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 40).field("lon", 20).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "5").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 10).field("lon", -170).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "6").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 0).field("lon", -170).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "7").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", -10).field("lon", -170).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "8").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 10).field("lon", 170).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "9").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", 0).field("lon", 170).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.prepareIndex("test", "type1", "10").setSource(jsonBuilder().startObject()
|
||||
.startObject("location").field("lat", -10).field("lon", 170).endObject()
|
||||
.endObject()).execute().actionGet();
|
||||
|
||||
client.admin().indices().prepareRefresh().execute().actionGet();
|
||||
|
||||
SearchResponse searchResponse = client.prepareSearch()
|
||||
.setQuery(filtered(matchAllQuery(), geoBoundingBoxFilter("location").topLeft(41, -11).bottomRight(40, 9)))
|
||||
.execute().actionGet();
|
||||
assertThat(searchResponse.hits().getTotalHits(), equalTo(1l));
|
||||
assertThat(searchResponse.hits().hits().length, equalTo(1));
|
||||
assertThat(searchResponse.hits().getAt(0).id(), equalTo("2"));
|
||||
|
||||
searchResponse = client.prepareSearch()
|
||||
.setQuery(filtered(matchAllQuery(), geoBoundingBoxFilter("location").topLeft(41, -9).bottomRight(40, 11)))
|
||||
.execute().actionGet();
|
||||
assertThat(searchResponse.hits().getTotalHits(), equalTo(1l));
|
||||
assertThat(searchResponse.hits().hits().length, equalTo(1));
|
||||
assertThat(searchResponse.hits().getAt(0).id(), equalTo("3"));
|
||||
|
||||
searchResponse = client.prepareSearch()
|
||||
.setQuery(filtered(matchAllQuery(), geoBoundingBoxFilter("location").topLeft(11, 171).bottomRight(1, -169)))
|
||||
.execute().actionGet();
|
||||
assertThat(searchResponse.hits().getTotalHits(), equalTo(1l));
|
||||
assertThat(searchResponse.hits().hits().length, equalTo(1));
|
||||
assertThat(searchResponse.hits().getAt(0).id(), equalTo("5"));
|
||||
|
||||
searchResponse = client.prepareSearch()
|
||||
.setQuery(filtered(matchAllQuery(), geoBoundingBoxFilter("location").topLeft(9, 169).bottomRight(-1, -171)))
|
||||
.execute().actionGet();
|
||||
assertThat(searchResponse.hits().getTotalHits(), equalTo(1l));
|
||||
assertThat(searchResponse.hits().hits().length, equalTo(1));
|
||||
assertThat(searchResponse.hits().getAt(0).id(), equalTo("9"));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue