Adds deprecation logging to ScriptDocValues#getValues. (#34279)
`ScriptDocValues#getValues` was added for backwards compatibility but no longer needed. Scripts using the syntax `doc['foo'].values` when `doc['foo']` is a list should be using `doc['foo']` instead. Closes #22919
This commit is contained in:
parent
3337fa7351
commit
49087f16f5
|
@ -108,7 +108,7 @@ POST /stackoverflow/_search?size=0
|
||||||
"max_docs_per_value" : 3,
|
"max_docs_per_value" : 3,
|
||||||
"script" : {
|
"script" : {
|
||||||
"lang": "painless",
|
"lang": "painless",
|
||||||
"source": "doc['tags'].values.hashCode()"
|
"source": "doc['tags'].hashCode()"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"aggs": {
|
"aggs": {
|
||||||
|
|
|
@ -144,7 +144,7 @@ access `text` fields from scripts.
|
||||||
|
|
||||||
_Stored fields_ -- fields explicitly marked as
|
_Stored fields_ -- fields explicitly marked as
|
||||||
<<mapping-store,`"store": true`>> -- can be accessed using the
|
<<mapping-store,`"store": true`>> -- can be accessed using the
|
||||||
`_fields['field_name'].value` or `_fields['field_name'].values` syntax.
|
`_fields['field_name'].value` or `_fields['field_name']` syntax.
|
||||||
|
|
||||||
The document <<mapping-source-field,`_source`>>, which is really just a
|
The document <<mapping-source-field,`_source`>>, which is really just a
|
||||||
special stored field, can be accessed using the `_source.field_name` syntax.
|
special stored field, can be accessed using the `_source.field_name` syntax.
|
||||||
|
|
|
@ -370,7 +370,7 @@
|
||||||
script_fields:
|
script_fields:
|
||||||
foobar:
|
foobar:
|
||||||
script:
|
script:
|
||||||
source: "doc['f'].values.size()"
|
source: "doc['f'].size()"
|
||||||
lang: painless
|
lang: painless
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -19,6 +19,7 @@
|
||||||
|
|
||||||
package org.elasticsearch.index.fielddata;
|
package org.elasticsearch.index.fielddata;
|
||||||
|
|
||||||
|
import org.apache.logging.log4j.LogManager;
|
||||||
import org.apache.lucene.index.SortedNumericDocValues;
|
import org.apache.lucene.index.SortedNumericDocValues;
|
||||||
import org.apache.lucene.util.ArrayUtil;
|
import org.apache.lucene.util.ArrayUtil;
|
||||||
import org.apache.lucene.util.BytesRef;
|
import org.apache.lucene.util.BytesRef;
|
||||||
|
@ -26,15 +27,19 @@ import org.apache.lucene.util.BytesRefBuilder;
|
||||||
import org.elasticsearch.common.geo.GeoHashUtils;
|
import org.elasticsearch.common.geo.GeoHashUtils;
|
||||||
import org.elasticsearch.common.geo.GeoPoint;
|
import org.elasticsearch.common.geo.GeoPoint;
|
||||||
import org.elasticsearch.common.geo.GeoUtils;
|
import org.elasticsearch.common.geo.GeoUtils;
|
||||||
|
import org.elasticsearch.common.logging.DeprecationLogger;
|
||||||
import org.elasticsearch.script.JodaCompatibleZonedDateTime;
|
import org.elasticsearch.script.JodaCompatibleZonedDateTime;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.security.AccessController;
|
||||||
|
import java.security.PrivilegedAction;
|
||||||
import java.time.Instant;
|
import java.time.Instant;
|
||||||
import java.time.ZoneOffset;
|
import java.time.ZoneOffset;
|
||||||
import java.util.AbstractList;
|
import java.util.AbstractList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Comparator;
|
import java.util.Comparator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.function.BiConsumer;
|
||||||
import java.util.function.UnaryOperator;
|
import java.util.function.UnaryOperator;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -48,6 +53,25 @@ import java.util.function.UnaryOperator;
|
||||||
*/
|
*/
|
||||||
public abstract class ScriptDocValues<T> extends AbstractList<T> {
|
public abstract class ScriptDocValues<T> extends AbstractList<T> {
|
||||||
|
|
||||||
|
private static final DeprecationLogger deprecationLogger = new DeprecationLogger(LogManager.getLogger(ScriptDocValues.class));
|
||||||
|
/**
|
||||||
|
* Callback for deprecated fields. In production this should always point to
|
||||||
|
* {@link #deprecationLogger} but tests will override it so they can test
|
||||||
|
* that we use the required permissions when calling it.
|
||||||
|
*/
|
||||||
|
private final BiConsumer<String, String> deprecationCallback;
|
||||||
|
|
||||||
|
public ScriptDocValues() {
|
||||||
|
deprecationCallback = deprecationLogger::deprecatedAndMaybeLog;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructor for testing deprecation callback.
|
||||||
|
*/
|
||||||
|
ScriptDocValues(BiConsumer<String, String> deprecationCallback) {
|
||||||
|
this.deprecationCallback = deprecationCallback;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the current doc ID.
|
* Set the current doc ID.
|
||||||
*/
|
*/
|
||||||
|
@ -57,6 +81,8 @@ public abstract class ScriptDocValues<T> extends AbstractList<T> {
|
||||||
* Return a copy of the list of the values for the current document.
|
* Return a copy of the list of the values for the current document.
|
||||||
*/
|
*/
|
||||||
public final List<T> getValues() {
|
public final List<T> getValues() {
|
||||||
|
deprecated("ScriptDocValues#getValues", "Deprecated getValues used, the field is a list and should be accessed directly."
|
||||||
|
+ " For example, use doc['foo'] instead of doc['foo'].values.");
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -86,6 +112,21 @@ public abstract class ScriptDocValues<T> extends AbstractList<T> {
|
||||||
throw new UnsupportedOperationException("doc values are unmodifiable");
|
throw new UnsupportedOperationException("doc values are unmodifiable");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Log a deprecation log, with the server's permissions and not the permissions
|
||||||
|
* of the script calling this method. We need to do this to prevent errors
|
||||||
|
* when rolling the log file.
|
||||||
|
*/
|
||||||
|
private void deprecated(String key, String message) {
|
||||||
|
AccessController.doPrivileged(new PrivilegedAction<Void>() {
|
||||||
|
@Override
|
||||||
|
public Void run() {
|
||||||
|
deprecationCallback.accept(key, message);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
public static final class Longs extends ScriptDocValues<Long> {
|
public static final class Longs extends ScriptDocValues<Long> {
|
||||||
private final SortedNumericDocValues in;
|
private final SortedNumericDocValues in;
|
||||||
private long[] values = new long[0];
|
private long[] values = new long[0];
|
||||||
|
@ -98,6 +139,14 @@ public abstract class ScriptDocValues<T> extends AbstractList<T> {
|
||||||
this.in = in;
|
this.in = in;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructor for testing deprecation callback.
|
||||||
|
*/
|
||||||
|
Longs(SortedNumericDocValues in, BiConsumer<String, String> deprecationCallback) {
|
||||||
|
super(deprecationCallback);
|
||||||
|
this.in = in;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setNextDocId(int docId) throws IOException {
|
public void setNextDocId(int docId) throws IOException {
|
||||||
if (in.advanceExact(docId)) {
|
if (in.advanceExact(docId)) {
|
||||||
|
@ -155,6 +204,14 @@ public abstract class ScriptDocValues<T> extends AbstractList<T> {
|
||||||
this.in = in;
|
this.in = in;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructor for testing deprecation callback.
|
||||||
|
*/
|
||||||
|
Dates(SortedNumericDocValues in, BiConsumer<String, String> deprecationCallback) {
|
||||||
|
super(deprecationCallback);
|
||||||
|
this.in = in;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Fetch the first field value or 0 millis after epoch if there are no
|
* Fetch the first field value or 0 millis after epoch if there are no
|
||||||
* in.
|
* in.
|
||||||
|
@ -273,6 +330,14 @@ public abstract class ScriptDocValues<T> extends AbstractList<T> {
|
||||||
this.in = in;
|
this.in = in;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructor for testing deprecation callback.
|
||||||
|
*/
|
||||||
|
GeoPoints(MultiGeoPointValues in, BiConsumer<String, String> deprecationCallback) {
|
||||||
|
super(deprecationCallback);
|
||||||
|
this.in = in;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setNextDocId(int docId) throws IOException {
|
public void setNextDocId(int docId) throws IOException {
|
||||||
if (in.advanceExact(docId)) {
|
if (in.advanceExact(docId)) {
|
||||||
|
|
|
@ -0,0 +1,93 @@
|
||||||
|
/*
|
||||||
|
* Licensed to Elasticsearch under one or more contributor
|
||||||
|
* license agreements. See the NOTICE file distributed with
|
||||||
|
* this work for additional information regarding copyright
|
||||||
|
* ownership. Elasticsearch 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.elasticsearch.index.fielddata;
|
||||||
|
|
||||||
|
import org.elasticsearch.index.fielddata.ScriptDocValues.Dates;
|
||||||
|
import org.elasticsearch.test.ESTestCase;
|
||||||
|
|
||||||
|
import java.security.AccessControlContext;
|
||||||
|
import java.security.AccessController;
|
||||||
|
import java.security.PermissionCollection;
|
||||||
|
import java.security.Permissions;
|
||||||
|
import java.security.PrivilegedAction;
|
||||||
|
import java.security.ProtectionDomain;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.function.BiConsumer;
|
||||||
|
|
||||||
|
import static org.hamcrest.Matchers.contains;
|
||||||
|
|
||||||
|
public class ScriptDocValuesDatesTests extends ESTestCase {
|
||||||
|
|
||||||
|
public void testGetValues() {
|
||||||
|
Set<String> keys = new HashSet<>();
|
||||||
|
Set<String> warnings = new HashSet<>();
|
||||||
|
|
||||||
|
Dates dates = biconsumerWrap((deprecationKey, deprecationMessage) -> {
|
||||||
|
keys.add(deprecationKey);
|
||||||
|
warnings.add(deprecationMessage);
|
||||||
|
|
||||||
|
// Create a temporary directory to prove we are running with the server's permissions.
|
||||||
|
createTempDir();
|
||||||
|
});
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Invoke getValues() without any permissions to verify it still works.
|
||||||
|
* This is done using the callback created above, which creates a temp
|
||||||
|
* directory, which is not possible with "noPermission".
|
||||||
|
*/
|
||||||
|
PermissionCollection noPermissions = new Permissions();
|
||||||
|
AccessControlContext noPermissionsAcc = new AccessControlContext(
|
||||||
|
new ProtectionDomain[] {
|
||||||
|
new ProtectionDomain(null, noPermissions)
|
||||||
|
}
|
||||||
|
);
|
||||||
|
AccessController.doPrivileged(new PrivilegedAction<Void>(){
|
||||||
|
public Void run() {
|
||||||
|
dates.getValues();
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}, noPermissionsAcc);
|
||||||
|
|
||||||
|
assertThat(warnings, contains(
|
||||||
|
"Deprecated getValues used, the field is a list and should be accessed directly."
|
||||||
|
+ " For example, use doc['foo'] instead of doc['foo'].values."));
|
||||||
|
assertThat(keys, contains("ScriptDocValues#getValues"));
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private Dates biconsumerWrap(BiConsumer<String, String> deprecationHandler) {
|
||||||
|
return new Dates(new AbstractSortedNumericDocValues() {
|
||||||
|
@Override
|
||||||
|
public boolean advanceExact(int doc) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public int docValueCount() {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public long nextValue() {
|
||||||
|
return 0L;
|
||||||
|
}
|
||||||
|
}, deprecationHandler);
|
||||||
|
}
|
||||||
|
}
|
|
@ -21,10 +21,22 @@ package org.elasticsearch.index.fielddata;
|
||||||
|
|
||||||
import org.elasticsearch.common.geo.GeoPoint;
|
import org.elasticsearch.common.geo.GeoPoint;
|
||||||
import org.elasticsearch.common.geo.GeoUtils;
|
import org.elasticsearch.common.geo.GeoUtils;
|
||||||
|
import org.elasticsearch.index.fielddata.ScriptDocValues.GeoPoints;
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.security.AccessControlContext;
|
||||||
|
import java.security.AccessController;
|
||||||
|
import java.security.PermissionCollection;
|
||||||
|
import java.security.Permissions;
|
||||||
|
import java.security.PrivilegedAction;
|
||||||
|
import java.security.ProtectionDomain;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.function.BiConsumer;
|
||||||
|
|
||||||
|
import static org.hamcrest.Matchers.contains;
|
||||||
|
|
||||||
public class ScriptDocValuesGeoPointsTests extends ESTestCase {
|
public class ScriptDocValuesGeoPointsTests extends ESTestCase {
|
||||||
|
|
||||||
|
@ -70,8 +82,18 @@ public class ScriptDocValuesGeoPointsTests extends ESTestCase {
|
||||||
final double lat2 = randomLat();
|
final double lat2 = randomLat();
|
||||||
final double lon1 = randomLon();
|
final double lon1 = randomLon();
|
||||||
final double lon2 = randomLon();
|
final double lon2 = randomLon();
|
||||||
|
|
||||||
|
Set<String> warnings = new HashSet<>();
|
||||||
|
Set<String> keys = new HashSet<>();
|
||||||
|
|
||||||
final MultiGeoPointValues values = wrap(new GeoPoint(lat1, lon1), new GeoPoint(lat2, lon2));
|
final MultiGeoPointValues values = wrap(new GeoPoint(lat1, lon1), new GeoPoint(lat2, lon2));
|
||||||
final ScriptDocValues.GeoPoints script = new ScriptDocValues.GeoPoints(values);
|
final ScriptDocValues.GeoPoints script = geoPointsWrap(values, (deprecationKey, deprecationMessage) -> {
|
||||||
|
keys.add(deprecationKey);
|
||||||
|
warnings.add(deprecationMessage);
|
||||||
|
|
||||||
|
// Create a temporary directory to prove we are running with the server's permissions.
|
||||||
|
createTempDir();
|
||||||
|
});
|
||||||
script.setNextDocId(1);
|
script.setNextDocId(1);
|
||||||
assertEquals(true, script.isEmpty());
|
assertEquals(true, script.isEmpty());
|
||||||
script.setNextDocId(0);
|
script.setNextDocId(0);
|
||||||
|
@ -82,6 +104,30 @@ public class ScriptDocValuesGeoPointsTests extends ESTestCase {
|
||||||
assertEquals(lon1, script.getLon(), 0);
|
assertEquals(lon1, script.getLon(), 0);
|
||||||
assertTrue(Arrays.equals(new double[] {lat1, lat2}, script.getLats()));
|
assertTrue(Arrays.equals(new double[] {lat1, lat2}, script.getLats()));
|
||||||
assertTrue(Arrays.equals(new double[] {lon1, lon2}, script.getLons()));
|
assertTrue(Arrays.equals(new double[] {lon1, lon2}, script.getLons()));
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Invoke getValues() without any permissions to verify it still works.
|
||||||
|
* This is done using the callback created above, which creates a temp
|
||||||
|
* directory, which is not possible with "noPermission".
|
||||||
|
*/
|
||||||
|
PermissionCollection noPermissions = new Permissions();
|
||||||
|
AccessControlContext noPermissionsAcc = new AccessControlContext(
|
||||||
|
new ProtectionDomain[] {
|
||||||
|
new ProtectionDomain(null, noPermissions)
|
||||||
|
}
|
||||||
|
);
|
||||||
|
AccessController.doPrivileged(new PrivilegedAction<Void>(){
|
||||||
|
public Void run() {
|
||||||
|
script.getValues();
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}, noPermissionsAcc);
|
||||||
|
|
||||||
|
assertThat(warnings, contains(
|
||||||
|
"Deprecated getValues used, the field is a list and should be accessed directly."
|
||||||
|
+ " For example, use doc['foo'] instead of doc['foo'].values."));
|
||||||
|
assertThat(keys, contains("ScriptDocValues#getValues"));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testGeoDistance() throws IOException {
|
public void testGeoDistance() throws IOException {
|
||||||
|
@ -110,4 +156,8 @@ public class ScriptDocValuesGeoPointsTests extends ESTestCase {
|
||||||
assertEquals(42, emptyScript.planeDistanceWithDefault(otherLat, otherLon, 42), 0);
|
assertEquals(42, emptyScript.planeDistanceWithDefault(otherLat, otherLon, 42), 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private GeoPoints geoPointsWrap(MultiGeoPointValues in, BiConsumer<String, String> deprecationHandler) {
|
||||||
|
return new GeoPoints(in, deprecationHandler);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,6 +23,17 @@ import org.elasticsearch.index.fielddata.ScriptDocValues.Longs;
|
||||||
import org.elasticsearch.test.ESTestCase;
|
import org.elasticsearch.test.ESTestCase;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.security.AccessControlContext;
|
||||||
|
import java.security.AccessController;
|
||||||
|
import java.security.PermissionCollection;
|
||||||
|
import java.security.Permissions;
|
||||||
|
import java.security.PrivilegedAction;
|
||||||
|
import java.security.ProtectionDomain;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.function.BiConsumer;
|
||||||
|
|
||||||
|
import static org.hamcrest.Matchers.contains;
|
||||||
|
|
||||||
public class ScriptDocValuesLongsTests extends ESTestCase {
|
public class ScriptDocValuesLongsTests extends ESTestCase {
|
||||||
public void testLongs() throws IOException {
|
public void testLongs() throws IOException {
|
||||||
|
@ -33,7 +44,17 @@ public class ScriptDocValuesLongsTests extends ESTestCase {
|
||||||
values[d][i] = randomLong();
|
values[d][i] = randomLong();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Longs longs = wrap(values);
|
|
||||||
|
Set<String> warnings = new HashSet<>();
|
||||||
|
Set<String> keys = new HashSet<>();
|
||||||
|
|
||||||
|
Longs longs = wrap(values, (deprecationKey, deprecationMessage) -> {
|
||||||
|
keys.add(deprecationKey);
|
||||||
|
warnings.add(deprecationMessage);
|
||||||
|
|
||||||
|
// Create a temporary directory to prove we are running with the server's permissions.
|
||||||
|
createTempDir();
|
||||||
|
});
|
||||||
|
|
||||||
for (int round = 0; round < 10; round++) {
|
for (int round = 0; round < 10; round++) {
|
||||||
int d = between(0, values.length - 1);
|
int d = between(0, values.length - 1);
|
||||||
|
@ -55,9 +76,33 @@ public class ScriptDocValuesLongsTests extends ESTestCase {
|
||||||
Exception e = expectThrows(UnsupportedOperationException.class, () -> longs.getValues().add(100L));
|
Exception e = expectThrows(UnsupportedOperationException.class, () -> longs.getValues().add(100L));
|
||||||
assertEquals("doc values are unmodifiable", e.getMessage());
|
assertEquals("doc values are unmodifiable", e.getMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Invoke getValues() without any permissions to verify it still works.
|
||||||
|
* This is done using the callback created above, which creates a temp
|
||||||
|
* directory, which is not possible with "noPermission".
|
||||||
|
*/
|
||||||
|
PermissionCollection noPermissions = new Permissions();
|
||||||
|
AccessControlContext noPermissionsAcc = new AccessControlContext(
|
||||||
|
new ProtectionDomain[] {
|
||||||
|
new ProtectionDomain(null, noPermissions)
|
||||||
|
}
|
||||||
|
);
|
||||||
|
AccessController.doPrivileged(new PrivilegedAction<Void>(){
|
||||||
|
public Void run() {
|
||||||
|
longs.getValues();
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}, noPermissionsAcc);
|
||||||
|
|
||||||
|
assertThat(warnings, contains(
|
||||||
|
"Deprecated getValues used, the field is a list and should be accessed directly."
|
||||||
|
+ " For example, use doc['foo'] instead of doc['foo'].values."));
|
||||||
|
assertThat(keys, contains("ScriptDocValues#getValues"));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private Longs wrap(long[][] values) {
|
private Longs wrap(long[][] values, BiConsumer<String, String> deprecationCallback) {
|
||||||
return new Longs(new AbstractSortedNumericDocValues() {
|
return new Longs(new AbstractSortedNumericDocValues() {
|
||||||
long[] current;
|
long[] current;
|
||||||
int i;
|
int i;
|
||||||
|
@ -76,6 +121,6 @@ public class ScriptDocValuesLongsTests extends ESTestCase {
|
||||||
public long nextValue() {
|
public long nextValue() {
|
||||||
return current[i++];
|
return current[i++];
|
||||||
}
|
}
|
||||||
});
|
}, deprecationCallback);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -37,7 +37,7 @@ public class AggregationTestScriptsPlugin extends MockScriptPlugin {
|
||||||
|
|
||||||
// Equivalent to:
|
// Equivalent to:
|
||||||
//
|
//
|
||||||
// List values = doc['values'].values;
|
// List values = doc['values'];
|
||||||
// double[] res = new double[values.size()];
|
// double[] res = new double[values.size()];
|
||||||
// for (int i = 0; i < res.length; i++) {
|
// for (int i = 0; i < res.length; i++) {
|
||||||
// res[i] = values.get(i) - dec;
|
// res[i] = values.get(i) - dec;
|
||||||
|
@ -85,7 +85,7 @@ public class AggregationTestScriptsPlugin extends MockScriptPlugin {
|
||||||
return value.getValue() + inc;
|
return value.getValue() + inc;
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc['values'].values", vars -> {
|
scripts.put("doc['values']", vars -> {
|
||||||
Map<?, ?> doc = (Map<?,?>) vars.get("doc");
|
Map<?, ?> doc = (Map<?,?>) vars.get("doc");
|
||||||
return doc.get("values");
|
return doc.get("values");
|
||||||
});
|
});
|
||||||
|
|
|
@ -53,7 +53,7 @@ public class IpTermsIT extends AbstractTermsTestCase {
|
||||||
return doc.get("ip");
|
return doc.get("ip");
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc['ip'].values", vars -> {
|
scripts.put("doc['ip']", vars -> {
|
||||||
Map<?, ?> doc = (Map<?,?>) vars.get("doc");
|
Map<?, ?> doc = (Map<?,?>) vars.get("doc");
|
||||||
return ((ScriptDocValues<?>) doc.get("ip")).get(0);
|
return ((ScriptDocValues<?>) doc.get("ip")).get(0);
|
||||||
});
|
});
|
||||||
|
@ -96,7 +96,7 @@ public class IpTermsIT extends AbstractTermsTestCase {
|
||||||
client().prepareIndex("index", "type", "3").setSource("ip", "2001:db8::2:1"));
|
client().prepareIndex("index", "type", "3").setSource("ip", "2001:db8::2:1"));
|
||||||
|
|
||||||
Script script = new Script(ScriptType.INLINE, CustomScriptPlugin.NAME,
|
Script script = new Script(ScriptType.INLINE, CustomScriptPlugin.NAME,
|
||||||
"doc['ip'].values", Collections.emptyMap());
|
"doc['ip']", Collections.emptyMap());
|
||||||
SearchResponse response = client().prepareSearch("index").addAggregation(
|
SearchResponse response = client().prepareSearch("index").addAggregation(
|
||||||
AggregationBuilders.terms("my_terms").script(script).executionHint(randomExecutionHint())).get();
|
AggregationBuilders.terms("my_terms").script(script).executionHint(randomExecutionHint())).get();
|
||||||
assertSearchResponse(response);
|
assertSearchResponse(response);
|
||||||
|
|
|
@ -81,19 +81,19 @@ public class MinDocCountIT extends AbstractTermsTestCase {
|
||||||
protected Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
|
protected Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
|
||||||
Map<String, Function<Map<String, Object>, Object>> scripts = new HashMap<>();
|
Map<String, Function<Map<String, Object>, Object>> scripts = new HashMap<>();
|
||||||
|
|
||||||
scripts.put("doc['d'].values", vars -> {
|
scripts.put("doc['d']", vars -> {
|
||||||
Map<?, ?> doc = (Map) vars.get("doc");
|
Map<?, ?> doc = (Map) vars.get("doc");
|
||||||
ScriptDocValues.Doubles value = (ScriptDocValues.Doubles) doc.get("d");
|
ScriptDocValues.Doubles value = (ScriptDocValues.Doubles) doc.get("d");
|
||||||
return value.getValues();
|
return value.getValues();
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc['l'].values", vars -> {
|
scripts.put("doc['l']", vars -> {
|
||||||
Map<?, ?> doc = (Map) vars.get("doc");
|
Map<?, ?> doc = (Map) vars.get("doc");
|
||||||
ScriptDocValues.Longs value = (ScriptDocValues.Longs) doc.get("l");
|
ScriptDocValues.Longs value = (ScriptDocValues.Longs) doc.get("l");
|
||||||
return value.getValues();
|
return value.getValues();
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc['s'].values", vars -> {
|
scripts.put("doc['s']", vars -> {
|
||||||
Map<?, ?> doc = (Map) vars.get("doc");
|
Map<?, ?> doc = (Map) vars.get("doc");
|
||||||
ScriptDocValues.Strings value = (ScriptDocValues.Strings) doc.get("s");
|
ScriptDocValues.Strings value = (ScriptDocValues.Strings) doc.get("s");
|
||||||
return value.getValues();
|
return value.getValues();
|
||||||
|
@ -154,7 +154,7 @@ public class MinDocCountIT extends AbstractTermsTestCase {
|
||||||
@Override
|
@Override
|
||||||
TermsAggregationBuilder apply(TermsAggregationBuilder builder, String field) {
|
TermsAggregationBuilder apply(TermsAggregationBuilder builder, String field) {
|
||||||
return builder.script(new org.elasticsearch.script.Script(ScriptType.INLINE,
|
return builder.script(new org.elasticsearch.script.Script(ScriptType.INLINE,
|
||||||
CustomScriptPlugin.NAME, "doc['" + field + "'].values", Collections.emptyMap()));
|
CustomScriptPlugin.NAME, "doc['" + field + "']", Collections.emptyMap()));
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
abstract TermsAggregationBuilder apply(TermsAggregationBuilder builder, String field);
|
abstract TermsAggregationBuilder apply(TermsAggregationBuilder builder, String field);
|
||||||
|
|
|
@ -84,7 +84,7 @@ public class RangeIT extends ESIntegTestCase {
|
||||||
return value.getValue();
|
return value.getValue();
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc['" + MULTI_VALUED_FIELD_NAME + "'].values", vars -> {
|
scripts.put("doc['" + MULTI_VALUED_FIELD_NAME + "']", vars -> {
|
||||||
Map<?, ?> doc = (Map) vars.get("doc");
|
Map<?, ?> doc = (Map) vars.get("doc");
|
||||||
ScriptDocValues.Longs value = (ScriptDocValues.Longs) doc.get(MULTI_VALUED_FIELD_NAME);
|
ScriptDocValues.Longs value = (ScriptDocValues.Longs) doc.get(MULTI_VALUED_FIELD_NAME);
|
||||||
return value.getValues();
|
return value.getValues();
|
||||||
|
@ -693,7 +693,7 @@ public class RangeIT extends ESIntegTestCase {
|
||||||
|
|
||||||
public void testScriptMultiValued() throws Exception {
|
public void testScriptMultiValued() throws Exception {
|
||||||
Script script =
|
Script script =
|
||||||
new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['" + MULTI_VALUED_FIELD_NAME + "'].values", Collections.emptyMap());
|
new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['" + MULTI_VALUED_FIELD_NAME + "']", Collections.emptyMap());
|
||||||
|
|
||||||
SearchResponse response = client()
|
SearchResponse response = client()
|
||||||
.prepareSearch("idx")
|
.prepareSearch("idx")
|
||||||
|
|
|
@ -72,7 +72,7 @@ public class CardinalityIT extends ESIntegTestCase {
|
||||||
return doc.get("str_value");
|
return doc.get("str_value");
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc['str_values'].values", vars -> {
|
scripts.put("doc['str_values']", vars -> {
|
||||||
Map<?, ?> doc = (Map<?, ?>) vars.get("doc");
|
Map<?, ?> doc = (Map<?, ?>) vars.get("doc");
|
||||||
ScriptDocValues.Strings strValue = (ScriptDocValues.Strings) doc.get("str_values");
|
ScriptDocValues.Strings strValue = (ScriptDocValues.Strings) doc.get("str_values");
|
||||||
return strValue.getValues();
|
return strValue.getValues();
|
||||||
|
@ -83,7 +83,7 @@ public class CardinalityIT extends ESIntegTestCase {
|
||||||
return doc.get(singleNumericField());
|
return doc.get(singleNumericField());
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc[' + multiNumericField(false) + '].values", vars -> {
|
scripts.put("doc[' + multiNumericField(false) + ']", vars -> {
|
||||||
Map<?, ?> doc =(Map<?, ?>) vars.get("doc");
|
Map<?, ?> doc =(Map<?, ?>) vars.get("doc");
|
||||||
return ((ScriptDocValues<?>) doc.get(multiNumericField(false))).getValues();
|
return ((ScriptDocValues<?>) doc.get(multiNumericField(false))).getValues();
|
||||||
});
|
});
|
||||||
|
@ -322,7 +322,7 @@ public class CardinalityIT extends ESIntegTestCase {
|
||||||
.addAggregation(
|
.addAggregation(
|
||||||
cardinality("cardinality")
|
cardinality("cardinality")
|
||||||
.precisionThreshold(precisionThreshold)
|
.precisionThreshold(precisionThreshold)
|
||||||
.script(new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['str_values'].values", emptyMap())))
|
.script(new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['str_values']", emptyMap())))
|
||||||
.execute().actionGet();
|
.execute().actionGet();
|
||||||
|
|
||||||
assertSearchResponse(response);
|
assertSearchResponse(response);
|
||||||
|
@ -349,7 +349,7 @@ public class CardinalityIT extends ESIntegTestCase {
|
||||||
|
|
||||||
public void testMultiValuedNumericScript() throws Exception {
|
public void testMultiValuedNumericScript() throws Exception {
|
||||||
Script script =
|
Script script =
|
||||||
new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc[' + multiNumericField(false) + '].values", Collections.emptyMap());
|
new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc[' + multiNumericField(false) + ']", Collections.emptyMap());
|
||||||
SearchResponse response = client().prepareSearch("idx").setTypes("type")
|
SearchResponse response = client().prepareSearch("idx").setTypes("type")
|
||||||
.addAggregation(cardinality("cardinality").precisionThreshold(precisionThreshold).script(script))
|
.addAggregation(cardinality("cardinality").precisionThreshold(precisionThreshold).script(script))
|
||||||
.execute().actionGet();
|
.execute().actionGet();
|
||||||
|
|
|
@ -502,7 +502,7 @@ public class ExtendedStatsIT extends AbstractNumericTestCase {
|
||||||
.addAggregation(
|
.addAggregation(
|
||||||
extendedStats("stats")
|
extendedStats("stats")
|
||||||
.script(new Script(ScriptType.INLINE,
|
.script(new Script(ScriptType.INLINE,
|
||||||
AggregationTestScriptsPlugin.NAME, "doc['values'].values", Collections.emptyMap()))
|
AggregationTestScriptsPlugin.NAME, "doc['values']", Collections.emptyMap()))
|
||||||
.sigma(sigma))
|
.sigma(sigma))
|
||||||
.execute().actionGet();
|
.execute().actionGet();
|
||||||
|
|
||||||
|
|
|
@ -457,7 +457,7 @@ public class HDRPercentileRanksIT extends AbstractNumericTestCase {
|
||||||
int sigDigits = randomSignificantDigits();
|
int sigDigits = randomSignificantDigits();
|
||||||
final double[] pcts = randomPercents(minValues, maxValues);
|
final double[] pcts = randomPercents(minValues, maxValues);
|
||||||
|
|
||||||
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values'].values", emptyMap());
|
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values']", emptyMap());
|
||||||
|
|
||||||
SearchResponse searchResponse = client()
|
SearchResponse searchResponse = client()
|
||||||
.prepareSearch("idx")
|
.prepareSearch("idx")
|
||||||
|
|
|
@ -416,7 +416,7 @@ public class HDRPercentilesIT extends AbstractNumericTestCase {
|
||||||
final double[] pcts = randomPercentiles();
|
final double[] pcts = randomPercentiles();
|
||||||
int sigDigits = randomSignificantDigits();
|
int sigDigits = randomSignificantDigits();
|
||||||
|
|
||||||
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values'].values", emptyMap());
|
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values']", emptyMap());
|
||||||
|
|
||||||
SearchResponse searchResponse = client()
|
SearchResponse searchResponse = client()
|
||||||
.prepareSearch("idx")
|
.prepareSearch("idx")
|
||||||
|
|
|
@ -294,7 +294,7 @@ public class MaxIT extends AbstractNumericTestCase {
|
||||||
.addAggregation(
|
.addAggregation(
|
||||||
max("max")
|
max("max")
|
||||||
.script(new Script(ScriptType.INLINE,
|
.script(new Script(ScriptType.INLINE,
|
||||||
AggregationTestScriptsPlugin.NAME, "doc['values'].values", Collections.emptyMap())))
|
AggregationTestScriptsPlugin.NAME, "doc['values']", Collections.emptyMap())))
|
||||||
.get();
|
.get();
|
||||||
|
|
||||||
assertHitCount(searchResponse, 10);
|
assertHitCount(searchResponse, 10);
|
||||||
|
|
|
@ -441,7 +441,7 @@ public class MedianAbsoluteDeviationIT extends AbstractNumericTestCase {
|
||||||
.script(new Script(
|
.script(new Script(
|
||||||
ScriptType.INLINE,
|
ScriptType.INLINE,
|
||||||
AggregationTestScriptsPlugin.NAME,
|
AggregationTestScriptsPlugin.NAME,
|
||||||
"doc['values'].values",
|
"doc['values']",
|
||||||
Collections.emptyMap())))
|
Collections.emptyMap())))
|
||||||
.execute()
|
.execute()
|
||||||
.actionGet();
|
.actionGet();
|
||||||
|
|
|
@ -305,7 +305,7 @@ public class MinIT extends AbstractNumericTestCase {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void testScriptMultiValued() throws Exception {
|
public void testScriptMultiValued() throws Exception {
|
||||||
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values'].values", emptyMap());
|
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values']", emptyMap());
|
||||||
SearchResponse searchResponse = client().prepareSearch("idx").setQuery(matchAllQuery())
|
SearchResponse searchResponse = client().prepareSearch("idx").setQuery(matchAllQuery())
|
||||||
.addAggregation(min("min").script(script))
|
.addAggregation(min("min").script(script))
|
||||||
.get();
|
.get();
|
||||||
|
|
|
@ -392,7 +392,7 @@ public class StatsIT extends AbstractNumericTestCase {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void testScriptMultiValued() throws Exception {
|
public void testScriptMultiValued() throws Exception {
|
||||||
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values'].values", emptyMap());
|
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values']", emptyMap());
|
||||||
|
|
||||||
SearchResponse searchResponse = client().prepareSearch("idx")
|
SearchResponse searchResponse = client().prepareSearch("idx")
|
||||||
.setQuery(matchAllQuery())
|
.setQuery(matchAllQuery())
|
||||||
|
|
|
@ -392,7 +392,7 @@ public class TDigestPercentileRanksIT extends AbstractNumericTestCase {
|
||||||
@Override
|
@Override
|
||||||
public void testScriptMultiValued() throws Exception {
|
public void testScriptMultiValued() throws Exception {
|
||||||
final double[] pcts = randomPercents(minValues, maxValues);
|
final double[] pcts = randomPercents(minValues, maxValues);
|
||||||
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values'].values", emptyMap());
|
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values']", emptyMap());
|
||||||
SearchResponse searchResponse = client().prepareSearch("idx")
|
SearchResponse searchResponse = client().prepareSearch("idx")
|
||||||
.setQuery(matchAllQuery())
|
.setQuery(matchAllQuery())
|
||||||
.addAggregation(
|
.addAggregation(
|
||||||
|
|
|
@ -371,7 +371,7 @@ public class TDigestPercentilesIT extends AbstractNumericTestCase {
|
||||||
@Override
|
@Override
|
||||||
public void testScriptMultiValued() throws Exception {
|
public void testScriptMultiValued() throws Exception {
|
||||||
final double[] pcts = randomPercentiles();
|
final double[] pcts = randomPercentiles();
|
||||||
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values'].values", emptyMap());
|
Script script = new Script(ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, "doc['values']", emptyMap());
|
||||||
|
|
||||||
SearchResponse searchResponse = client().prepareSearch("idx")
|
SearchResponse searchResponse = client().prepareSearch("idx")
|
||||||
.setQuery(matchAllQuery())
|
.setQuery(matchAllQuery())
|
||||||
|
|
|
@ -131,12 +131,12 @@ public class SearchFieldsIT extends ESIntegTestCase {
|
||||||
|
|
||||||
scripts.put("return null", vars -> null);
|
scripts.put("return null", vars -> null);
|
||||||
|
|
||||||
scripts.put("doc['l'].values", vars -> docScript(vars, "l"));
|
scripts.put("doc['l']", vars -> docScript(vars, "l"));
|
||||||
scripts.put("doc['ml'].values", vars -> docScript(vars, "ml"));
|
scripts.put("doc['ml']", vars -> docScript(vars, "ml"));
|
||||||
scripts.put("doc['d'].values", vars -> docScript(vars, "d"));
|
scripts.put("doc['d']", vars -> docScript(vars, "d"));
|
||||||
scripts.put("doc['md'].values", vars -> docScript(vars, "md"));
|
scripts.put("doc['md']", vars -> docScript(vars, "md"));
|
||||||
scripts.put("doc['s'].values", vars -> docScript(vars, "s"));
|
scripts.put("doc['s']", vars -> docScript(vars, "s"));
|
||||||
scripts.put("doc['ms'].values", vars -> docScript(vars, "ms"));
|
scripts.put("doc['ms']", vars -> docScript(vars, "ms"));
|
||||||
|
|
||||||
return scripts;
|
return scripts;
|
||||||
}
|
}
|
||||||
|
@ -925,7 +925,7 @@ public class SearchFieldsIT extends ESIntegTestCase {
|
||||||
SearchRequestBuilder req = client().prepareSearch("index");
|
SearchRequestBuilder req = client().prepareSearch("index");
|
||||||
for (String field : Arrays.asList("s", "ms", "l", "ml", "d", "md")) {
|
for (String field : Arrays.asList("s", "ms", "l", "ml", "d", "md")) {
|
||||||
req.addScriptField(field,
|
req.addScriptField(field,
|
||||||
new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['" + field + "'].values", Collections.emptyMap()));
|
new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['" + field + "']", Collections.emptyMap()));
|
||||||
}
|
}
|
||||||
SearchResponse resp = req.get();
|
SearchResponse resp = req.get();
|
||||||
assertSearchResponse(resp);
|
assertSearchResponse(resp);
|
||||||
|
|
|
@ -85,7 +85,7 @@ public class SimpleSortIT extends ESIntegTestCase {
|
||||||
return ((ScriptDocValues.Strings) doc.get("id")).getValue();
|
return ((ScriptDocValues.Strings) doc.get("id")).getValue();
|
||||||
});
|
});
|
||||||
|
|
||||||
scripts.put("doc['id'].values[0]", vars -> {
|
scripts.put("doc['id'][0]", vars -> {
|
||||||
Map<?, ?> doc = (Map) vars.get("doc");
|
Map<?, ?> doc = (Map) vars.get("doc");
|
||||||
return ((ScriptDocValues.Strings) doc.get("id")).getValues().get(0);
|
return ((ScriptDocValues.Strings) doc.get("id")).getValues().get(0);
|
||||||
});
|
});
|
||||||
|
@ -399,7 +399,7 @@ public class SimpleSortIT extends ESIntegTestCase {
|
||||||
|
|
||||||
searchResponse = client().prepareSearch()
|
searchResponse = client().prepareSearch()
|
||||||
.setQuery(matchAllQuery())
|
.setQuery(matchAllQuery())
|
||||||
.addScriptField("id", new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['id'].values[0]", Collections.emptyMap()))
|
.addScriptField("id", new Script(ScriptType.INLINE, CustomScriptPlugin.NAME, "doc['id'][0]", Collections.emptyMap()))
|
||||||
.addSort("svalue", SortOrder.ASC)
|
.addSort("svalue", SortOrder.ASC)
|
||||||
.get();
|
.get();
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue