@@ -85,6 +85,8 @@ public static class Names {
8585 public static final String LON_SUFFIX = "." + LON ;
8686 public static final String GEOHASH = "geohash" ;
8787 public static final String GEOHASH_SUFFIX = "." + GEOHASH ;
88+ public static final String IGNORE_MALFORMED = "ignore_malformed" ;
89+ public static final String COERCE = "coerce" ;
8890 }
8991
9092 public static class Defaults {
@@ -93,10 +95,9 @@ public static class Defaults {
9395 public static final boolean ENABLE_GEOHASH = false ;
9496 public static final boolean ENABLE_GEOHASH_PREFIX = false ;
9597 public static final int GEO_HASH_PRECISION = GeoHashUtils .PRECISION ;
96- public static final boolean NORMALIZE_LAT = true ;
97- public static final boolean NORMALIZE_LON = true ;
98- public static final boolean VALIDATE_LAT = true ;
99- public static final boolean VALIDATE_LON = true ;
98+
99+ public static final boolean IGNORE_MALFORMED = false ;
100+ public static final boolean COERCE = false ;
100101
101102 public static final MappedFieldType FIELD_TYPE = new GeoPointFieldType ();
102103
@@ -215,6 +216,7 @@ public static class TypeParser implements Mapper.TypeParser {
215216 @ Override
216217 public Mapper .Builder <?, ?> parse (String name , Map <String , Object > node , ParserContext parserContext ) throws MapperParsingException {
217218 Builder builder = geoPointField (name );
219+ final boolean indexCreatedBeforeV2_0 = parserContext .indexVersionCreated ().before (Version .V_2_0_0 );
218220 parseField (builder , name , node , parserContext );
219221 for (Iterator <Map .Entry <String , Object >> iterator = node .entrySet ().iterator (); iterator .hasNext ();) {
220222 Map .Entry <String , Object > entry = iterator .next ();
@@ -245,25 +247,42 @@ public static class TypeParser implements Mapper.TypeParser {
245247 builder .geoHashPrecision (GeoUtils .geoHashLevelsForPrecision (fieldNode .toString ()));
246248 }
247249 iterator .remove ();
248- } else if (fieldName .equals ("validate" )) {
249- builder .fieldType ().setValidateLat (XContentMapValues .nodeBooleanValue (fieldNode ));
250- builder .fieldType ().setValidateLon (XContentMapValues .nodeBooleanValue (fieldNode ));
250+ } else if (fieldName .equals (Names .IGNORE_MALFORMED )) {
251+ if (builder .fieldType ().coerce == false ) {
252+ builder .fieldType ().ignoreMalformed = XContentMapValues .nodeBooleanValue (fieldNode );
253+ }
251254 iterator .remove ();
252- } else if (fieldName .equals ("validate_lon" )) {
253- builder .fieldType ().setValidateLon (XContentMapValues .nodeBooleanValue (fieldNode ));
255+ } else if (indexCreatedBeforeV2_0 && fieldName .equals ("validate" )) {
256+ if (builder .fieldType ().ignoreMalformed == false ) {
257+ builder .fieldType ().ignoreMalformed = !XContentMapValues .nodeBooleanValue (fieldNode );
258+ }
259+ iterator .remove ();
260+ } else if (indexCreatedBeforeV2_0 && fieldName .equals ("validate_lon" )) {
261+ if (builder .fieldType ().ignoreMalformed () == false ) {
262+ builder .fieldType ().ignoreMalformed = !XContentMapValues .nodeBooleanValue (fieldNode );
263+ }
254264 iterator .remove ();
255- } else if (fieldName .equals ("validate_lat" )) {
256- builder .fieldType ().setValidateLat (XContentMapValues .nodeBooleanValue (fieldNode ));
265+ } else if (indexCreatedBeforeV2_0 && fieldName .equals ("validate_lat" )) {
266+ if (builder .fieldType ().ignoreMalformed == false ) {
267+ builder .fieldType ().ignoreMalformed = !XContentMapValues .nodeBooleanValue (fieldNode );
268+ }
257269 iterator .remove ();
258- } else if (fieldName .equals ("normalize" )) {
259- builder .fieldType ().setNormalizeLat (XContentMapValues .nodeBooleanValue (fieldNode ));
260- builder .fieldType ().setNormalizeLon (XContentMapValues .nodeBooleanValue (fieldNode ));
270+ } else if (fieldName .equals (Names .COERCE )) {
271+ builder .fieldType ().coerce = XContentMapValues .nodeBooleanValue (fieldNode );
272+ if (builder .fieldType ().coerce == true ) {
273+ builder .fieldType ().ignoreMalformed = true ;
274+ }
275+ iterator .remove ();
276+ } else if (indexCreatedBeforeV2_0 && fieldName .equals ("normalize" )) {
277+ builder .fieldType ().coerce = XContentMapValues .nodeBooleanValue (fieldNode );
261278 iterator .remove ();
262- } else if (fieldName .equals ("normalize_lat" )) {
263- builder .fieldType ().setNormalizeLat ( XContentMapValues .nodeBooleanValue (fieldNode ) );
279+ } else if (indexCreatedBeforeV2_0 && fieldName .equals ("normalize_lat" )) {
280+ builder .fieldType ().coerce = XContentMapValues .nodeBooleanValue (fieldNode );
264281 iterator .remove ();
265- } else if (fieldName .equals ("normalize_lon" )) {
266- builder .fieldType ().setNormalizeLon (XContentMapValues .nodeBooleanValue (fieldNode ));
282+ } else if (indexCreatedBeforeV2_0 && fieldName .equals ("normalize_lon" )) {
283+ if (builder .fieldType ().coerce == false ) {
284+ builder .fieldType ().coerce = XContentMapValues .nodeBooleanValue (fieldNode );
285+ }
267286 iterator .remove ();
268287 } else if (parseMultiField (builder , name , parserContext , fieldName , fieldNode )) {
269288 iterator .remove ();
@@ -281,10 +300,8 @@ public static final class GeoPointFieldType extends MappedFieldType {
281300
282301 private MappedFieldType latFieldType ;
283302 private MappedFieldType lonFieldType ;
284- private boolean validateLon = true ;
285- private boolean validateLat = true ;
286- private boolean normalizeLon = true ;
287- private boolean normalizeLat = true ;
303+ private boolean ignoreMalformed = false ;
304+ private boolean coerce = false ;
288305
289306 public GeoPointFieldType () {}
290307
@@ -295,10 +312,8 @@ protected GeoPointFieldType(GeoPointFieldType ref) {
295312 this .geohashPrefixEnabled = ref .geohashPrefixEnabled ;
296313 this .latFieldType = ref .latFieldType ; // copying ref is ok, this can never be modified
297314 this .lonFieldType = ref .lonFieldType ; // copying ref is ok, this can never be modified
298- this .validateLon = ref .validateLon ;
299- this .validateLat = ref .validateLat ;
300- this .normalizeLon = ref .normalizeLon ;
301- this .normalizeLat = ref .normalizeLat ;
315+ this .coerce = ref .coerce ;
316+ this .ignoreMalformed = ref .ignoreMalformed ;
302317 }
303318
304319 @ Override
@@ -312,18 +327,17 @@ public boolean equals(Object o) {
312327 GeoPointFieldType that = (GeoPointFieldType ) o ;
313328 return geohashPrecision == that .geohashPrecision &&
314329 geohashPrefixEnabled == that .geohashPrefixEnabled &&
315- validateLon == that .validateLon &&
316- validateLat == that .validateLat &&
317- normalizeLon == that .normalizeLon &&
318- normalizeLat == that .normalizeLat &&
330+ coerce == that .coerce &&
331+ ignoreMalformed == that .ignoreMalformed &&
319332 java .util .Objects .equals (geohashFieldType , that .geohashFieldType ) &&
320333 java .util .Objects .equals (latFieldType , that .latFieldType ) &&
321334 java .util .Objects .equals (lonFieldType , that .lonFieldType );
322335 }
323336
324337 @ Override
325338 public int hashCode () {
326- return java .util .Objects .hash (super .hashCode (), geohashFieldType , geohashPrecision , geohashPrefixEnabled , latFieldType , lonFieldType , validateLon , validateLat , normalizeLon , normalizeLat );
339+ return java .util .Objects .hash (super .hashCode (), geohashFieldType , geohashPrecision , geohashPrefixEnabled , latFieldType ,
340+ lonFieldType , coerce , ignoreMalformed );
327341 }
328342
329343 @ Override
@@ -347,22 +361,10 @@ public void checkCompatibility(MappedFieldType fieldType, List<String> conflicts
347361 if (isGeohashPrefixEnabled () != other .isGeohashPrefixEnabled ()) {
348362 conflicts .add ("mapper [" + names ().fullName () + "] has different geohash_prefix" );
349363 }
350- if (normalizeLat () != other .normalizeLat ()) {
351- conflicts .add ("mapper [" + names ().fullName () + "] has different normalize_lat" );
352- }
353- if (normalizeLon () != other .normalizeLon ()) {
354- conflicts .add ("mapper [" + names ().fullName () + "] has different normalize_lon" );
355- }
356- if (isLatLonEnabled () &&
364+ if (isLatLonEnabled () && other .isLatLonEnabled () &&
357365 latFieldType ().numericPrecisionStep () != other .latFieldType ().numericPrecisionStep ()) {
358366 conflicts .add ("mapper [" + names ().fullName () + "] has different precision_step" );
359367 }
360- if (validateLat () != other .validateLat ()) {
361- conflicts .add ("mapper [" + names ().fullName () + "] has different validate_lat" );
362- }
363- if (validateLon () != other .validateLon ()) {
364- conflicts .add ("mapper [" + names ().fullName () + "] has different validate_lon" );
365- }
366368 }
367369
368370 public boolean isGeohashEnabled () {
@@ -406,40 +408,22 @@ public void setLatLonEnabled(MappedFieldType latFieldType, MappedFieldType lonFi
406408 this .lonFieldType = lonFieldType ;
407409 }
408410
409- public boolean validateLon () {
410- return validateLon ;
411- }
412-
413- public void setValidateLon (boolean validateLon ) {
414- checkIfFrozen ();
415- this .validateLon = validateLon ;
416- }
417-
418- public boolean validateLat () {
419- return validateLat ;
420- }
421-
422- public void setValidateLat (boolean validateLat ) {
423- checkIfFrozen ();
424- this .validateLat = validateLat ;
411+ public boolean coerce () {
412+ return this .coerce ;
425413 }
426414
427- public boolean normalizeLon () {
428- return normalizeLon ;
429- }
430-
431- public void setNormalizeLon (boolean normalizeLon ) {
415+ public void setCoerce (boolean coerce ) {
432416 checkIfFrozen ();
433- this .normalizeLon = normalizeLon ;
417+ this .coerce = coerce ;
434418 }
435419
436- public boolean normalizeLat () {
437- return normalizeLat ;
420+ public boolean ignoreMalformed () {
421+ return this . ignoreMalformed ;
438422 }
439423
440- public void setNormalizeLat (boolean normalizeLat ) {
424+ public void setIgnoreMalformed (boolean ignoreMalformed ) {
441425 checkIfFrozen ();
442- this .normalizeLat = normalizeLat ;
426+ this .ignoreMalformed = ignoreMalformed ;
443427 }
444428
445429 @ Override
@@ -586,7 +570,8 @@ public GeoPoint decode(long latBits, long lonBits, GeoPoint out) {
586570 private final StringFieldMapper geohashMapper ;
587571
588572 public GeoPointFieldMapper (String simpleName , MappedFieldType fieldType , MappedFieldType defaultFieldType , Settings indexSettings ,
589- ContentPath .Type pathType , DoubleFieldMapper latMapper , DoubleFieldMapper lonMapper , StringFieldMapper geohashMapper ,MultiFields multiFields ) {
573+ ContentPath .Type pathType , DoubleFieldMapper latMapper , DoubleFieldMapper lonMapper , StringFieldMapper geohashMapper ,
574+ MultiFields multiFields ) {
590575 super (simpleName , fieldType , defaultFieldType , indexSettings , multiFields , null );
591576 this .pathType = pathType ;
592577 this .latMapper = latMapper ;
@@ -680,21 +665,22 @@ private void parsePointFromString(ParseContext context, GeoPoint sparse, String
680665 }
681666
682667 private void parse (ParseContext context , GeoPoint point , String geohash ) throws IOException {
683- if (fieldType ().normalizeLat () || fieldType ().normalizeLon ()) {
684- GeoUtils .normalizePoint (point , fieldType ().normalizeLat (), fieldType ().normalizeLon ());
685- }
686-
687- if (fieldType ().validateLat ()) {
668+ if (fieldType ().ignoreMalformed == false ) {
688669 if (point .lat () > 90.0 || point .lat () < -90.0 ) {
689670 throw new IllegalArgumentException ("illegal latitude value [" + point .lat () + "] for " + name ());
690671 }
691- }
692- if (fieldType ().validateLon ()) {
693672 if (point .lon () > 180.0 || point .lon () < -180 ) {
694673 throw new IllegalArgumentException ("illegal longitude value [" + point .lon () + "] for " + name ());
695674 }
696675 }
697676
677+ if (fieldType ().coerce ) {
678+ // by setting coerce to false we are assuming all geopoints are already in a valid coordinate system
679+ // thus this extra step can be skipped
680+ // LUCENE WATCH: This will be folded back into Lucene's GeoPointField
681+ GeoUtils .normalizePoint (point , true , true );
682+ }
683+
698684 if (fieldType ().indexOptions () != IndexOptions .NONE || fieldType ().stored ()) {
699685 Field field = new Field (fieldType ().names ().indexName (), Double .toString (point .lat ()) + ',' + Double .toString (point .lon ()), fieldType ());
700686 context .doc ().add (field );
@@ -755,33 +741,11 @@ protected void doXContentBody(XContentBuilder builder, boolean includeDefaults,
755741 if (fieldType ().isLatLonEnabled () && (includeDefaults || fieldType ().latFieldType ().numericPrecisionStep () != NumericUtils .PRECISION_STEP_DEFAULT )) {
756742 builder .field ("precision_step" , fieldType ().latFieldType ().numericPrecisionStep ());
757743 }
758- if (includeDefaults || fieldType ().validateLat () != Defaults .VALIDATE_LAT || fieldType ().validateLon () != Defaults .VALIDATE_LON ) {
759- if (fieldType ().validateLat () && fieldType ().validateLon ()) {
760- builder .field ("validate" , true );
761- } else if (!fieldType ().validateLat () && !fieldType ().validateLon ()) {
762- builder .field ("validate" , false );
763- } else {
764- if (includeDefaults || fieldType ().validateLat () != Defaults .VALIDATE_LAT ) {
765- builder .field ("validate_lat" , fieldType ().validateLat ());
766- }
767- if (includeDefaults || fieldType ().validateLon () != Defaults .VALIDATE_LON ) {
768- builder .field ("validate_lon" , fieldType ().validateLon ());
769- }
770- }
744+ if (includeDefaults || fieldType ().coerce != Defaults .COERCE ) {
745+ builder .field (Names .COERCE , fieldType ().coerce );
771746 }
772- if (includeDefaults || fieldType ().normalizeLat () != Defaults .NORMALIZE_LAT || fieldType ().normalizeLon () != Defaults .NORMALIZE_LON ) {
773- if (fieldType ().normalizeLat () && fieldType ().normalizeLon ()) {
774- builder .field ("normalize" , true );
775- } else if (!fieldType ().normalizeLat () && !fieldType ().normalizeLon ()) {
776- builder .field ("normalize" , false );
777- } else {
778- if (includeDefaults || fieldType ().normalizeLat () != Defaults .NORMALIZE_LAT ) {
779- builder .field ("normalize_lat" , fieldType ().normalizeLat ());
780- }
781- if (includeDefaults || fieldType ().normalizeLon () != Defaults .NORMALIZE_LON ) {
782- builder .field ("normalize_lon" , fieldType ().normalizeLon ());
783- }
784- }
747+ if (includeDefaults || fieldType ().ignoreMalformed != Defaults .IGNORE_MALFORMED ) {
748+ builder .field (Names .IGNORE_MALFORMED , fieldType ().ignoreMalformed );
785749 }
786750 }
787751
@@ -812,5 +776,4 @@ public BytesRef binaryValue() {
812776 return new BytesRef (bytes );
813777 }
814778 }
815-
816779}
0 commit comments