From b58f2eb5c286abc65bbd620c165487b8f1fa2fdb Mon Sep 17 00:00:00 2001 From: Tanguy Leroux Date: Wed, 6 Jul 2016 12:55:20 +0200 Subject: [PATCH] Move back some messy tests from Groovy plugin to core This commit moves back some messy tests that have been placed in lang-groovy module in https://github.com/elastic/elasticsearch/pull/13834. It removes the dependency on Groovy plugin as well as change back the tests to integration tests (IT suffix). It also changes the current MockScriptEngine and MockScriptPlugin to make it easier to use. --- .../resources/checkstyle_suppressions.xml | 3 - .../elasticsearch/script/FileScriptTests.java | 2 +- .../elasticsearch/script/StoredScriptsIT.java | 12 +- .../AggregationTestScriptsPlugin.java | 85 +++++++ .../metrics/HDRPercentileRanksIT.java | 102 ++++++--- .../metrics/HDRPercentilesIT.java | 117 +++++++--- .../aggregations/metrics/TopHitsIT.java | 12 +- .../aggregations/pipeline/BucketScriptIT.java | 116 +++++++--- .../pipeline/BucketSelectorIT.java | 216 +++++++++++++----- .../search/innerhits/InnerHitsIT.java | 13 +- .../messy/tests/package-info.java | 4 - .../script/MockScriptEngine.java | 181 ++++++++++----- .../script/MockScriptPlugin.java | 46 ++++ 13 files changed, 699 insertions(+), 210 deletions(-) create mode 100644 core/src/test/java/org/elasticsearch/search/aggregations/AggregationTestScriptsPlugin.java rename modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentileRanksTests.java => core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentileRanksIT.java (82%) rename modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentilesTests.java => core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentilesIT.java (81%) rename modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketScriptTests.java => core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketScriptIT.java (84%) rename modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketSelectorTests.java => core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketSelectorIT.java (68%) create mode 100644 test/framework/src/main/java/org/elasticsearch/script/MockScriptPlugin.java diff --git a/buildSrc/src/main/resources/checkstyle_suppressions.xml b/buildSrc/src/main/resources/checkstyle_suppressions.xml index 7aa77a26458..574bb1e3b30 100644 --- a/buildSrc/src/main/resources/checkstyle_suppressions.xml +++ b/buildSrc/src/main/resources/checkstyle_suppressions.xml @@ -1125,12 +1125,9 @@ - - - diff --git a/core/src/test/java/org/elasticsearch/script/FileScriptTests.java b/core/src/test/java/org/elasticsearch/script/FileScriptTests.java index 9fbd4a81f19..f932317085b 100644 --- a/core/src/test/java/org/elasticsearch/script/FileScriptTests.java +++ b/core/src/test/java/org/elasticsearch/script/FileScriptTests.java @@ -58,7 +58,7 @@ public class FileScriptTests extends ESTestCase { CompiledScript compiledScript = scriptService.compile(script, ScriptContext.Standard.SEARCH, Collections.emptyMap()); assertNotNull(compiledScript); MockCompiledScript executable = (MockCompiledScript) compiledScript.compiled(); - assertEquals("script1.mockscript", executable.name); + assertEquals("script1.mockscript", executable.getName()); } public void testAllOpsDisabled() throws Exception { diff --git a/core/src/test/java/org/elasticsearch/script/StoredScriptsIT.java b/core/src/test/java/org/elasticsearch/script/StoredScriptsIT.java index 658a3bf5658..6ae607e7b8e 100644 --- a/core/src/test/java/org/elasticsearch/script/StoredScriptsIT.java +++ b/core/src/test/java/org/elasticsearch/script/StoredScriptsIT.java @@ -24,6 +24,9 @@ import org.elasticsearch.plugins.Plugin; import org.elasticsearch.test.ESIntegTestCase; import java.util.Collection; +import java.util.Collections; +import java.util.Map; +import java.util.function.Function; import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertAcked; @@ -41,7 +44,7 @@ public class StoredScriptsIT extends ESIntegTestCase { @Override protected Collection> nodePlugins() { - return pluginList(MockScriptEngine.TestPlugin.class); + return pluginList(CustomScriptPlugin.class); } public void testBasics() { @@ -79,4 +82,11 @@ public class StoredScriptsIT extends ESIntegTestCase { assertEquals("Limit of script size in bytes [64] has been exceeded for script [foobar] with size [65]", e.getMessage()); } + public static class CustomScriptPlugin extends MockScriptPlugin { + + @Override + protected Map, Object>> pluginScripts() { + return Collections.emptyMap(); + } + } } diff --git a/core/src/test/java/org/elasticsearch/search/aggregations/AggregationTestScriptsPlugin.java b/core/src/test/java/org/elasticsearch/search/aggregations/AggregationTestScriptsPlugin.java new file mode 100644 index 00000000000..218c3eae0c5 --- /dev/null +++ b/core/src/test/java/org/elasticsearch/search/aggregations/AggregationTestScriptsPlugin.java @@ -0,0 +1,85 @@ +/* + * 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.search.aggregations; + +import org.elasticsearch.index.fielddata.ScriptDocValues; +import org.elasticsearch.script.MockScriptPlugin; + +import java.util.HashMap; +import java.util.Map; +import java.util.function.Function; + +/** + * This class contains various mocked scripts that are used in aggregations integration tests. + */ +public class AggregationTestScriptsPlugin extends MockScriptPlugin { + + @Override + protected Map, Object>> pluginScripts() { + Map, Object>> scripts = new HashMap<>(); + + scripts.put("20 - _value", vars -> { + double value = (double) vars.get("_value"); + return 20.0d - value; + }); + + scripts.put("_value - 1", vars -> { + double value = (double) vars.get("_value"); + return value - 1.0d; + }); + + scripts.put("_value - dec", vars -> { + double value = (double) vars.get("_value"); + int dec = (int) vars.get("dec"); + return value - dec; + }); + + scripts.put("doc['value'].value", vars -> { + Map doc = (Map) vars.get("doc"); + return doc.get("value"); + }); + + scripts.put("doc['value'].value - dec", vars -> { + int dec = (int) vars.get("dec"); + Map doc = (Map) vars.get("doc"); + ScriptDocValues.Longs value = (ScriptDocValues.Longs) doc.get("value"); + return value.getValue() - dec; + }); + + scripts.put("doc['values'].values", vars -> { + Map doc = (Map) vars.get("doc"); + return doc.get("values"); + }); + + scripts.put("decrement all values", vars -> { + int dec = (int) vars.get("dec"); + Map doc = (Map) vars.get("doc"); + ScriptDocValues.Longs values = (ScriptDocValues.Longs) doc.get("values"); + + double[] res = new double[values.size()]; + for (int i = 0; i < res.length; i++) { + res[i] = values.get(i) - dec; + } + return res; + }); + + return scripts; + } +} diff --git a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentileRanksTests.java b/core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentileRanksIT.java similarity index 82% rename from modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentileRanksTests.java rename to core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentileRanksIT.java index 21fb5be6b9d..c1f6847e2b6 100644 --- a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentileRanksTests.java +++ b/core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentileRanksIT.java @@ -16,20 +16,19 @@ * specific language governing permissions and limitations * under the License. */ -package org.elasticsearch.messy.tests; +package org.elasticsearch.search.aggregations.metrics; import org.elasticsearch.action.search.SearchResponse; import org.elasticsearch.common.logging.Loggers; import org.elasticsearch.plugins.Plugin; import org.elasticsearch.script.Script; import org.elasticsearch.script.ScriptService.ScriptType; -import org.elasticsearch.script.groovy.GroovyPlugin; +import org.elasticsearch.search.aggregations.AggregationTestScriptsPlugin; import org.elasticsearch.search.aggregations.bucket.filter.Filter; import org.elasticsearch.search.aggregations.bucket.global.Global; import org.elasticsearch.search.aggregations.bucket.histogram.Histogram; import org.elasticsearch.search.aggregations.bucket.histogram.Histogram.Order; import org.elasticsearch.search.aggregations.bucket.terms.Terms; -import org.elasticsearch.search.aggregations.metrics.AbstractNumericTestCase; import org.elasticsearch.search.aggregations.metrics.percentiles.Percentile; import org.elasticsearch.search.aggregations.metrics.percentiles.PercentileRanks; import org.elasticsearch.search.aggregations.metrics.percentiles.PercentilesMethod; @@ -41,6 +40,7 @@ import java.util.HashMap; import java.util.List; import java.util.Map; +import static java.util.Collections.emptyMap; import static org.elasticsearch.common.util.CollectionUtils.iterableAsArrayList; import static org.elasticsearch.index.query.QueryBuilders.matchAllQuery; import static org.elasticsearch.index.query.QueryBuilders.termQuery; @@ -56,13 +56,11 @@ import static org.hamcrest.Matchers.lessThanOrEqualTo; import static org.hamcrest.Matchers.notNullValue; import static org.hamcrest.Matchers.sameInstance; -/** - * - */ -public class HDRPercentileRanksTests extends AbstractNumericTestCase { +public class HDRPercentileRanksIT extends AbstractNumericTestCase { + @Override protected Collection> nodePlugins() { - return Collections.singleton(GroovyPlugin.class); + return Collections.singleton(AggregationTestScriptsPlugin.class); } private static double[] randomPercents(long minValue, long maxValue) { @@ -82,7 +80,7 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { } } Arrays.sort(percents); - Loggers.getLogger(HDRPercentileRanksTests.class).info("Using values={}", Arrays.toString(percents)); + Loggers.getLogger(HDRPercentileRanksIT.class).info("Using values={}", Arrays.toString(percents)); return percents; } @@ -208,7 +206,7 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { PercentileRanks values = global.getAggregations().get("percentile_ranks"); assertThat(values, notNullValue()); assertThat(values.getName(), equalTo("percentile_ranks")); - assertThat((PercentileRanks) global.getProperty("percentile_ranks"), sameInstance(values)); + assertThat(global.getProperty("percentile_ranks"), sameInstance(values)); } @@ -255,8 +253,12 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .field("value").script(new Script("_value - 1")).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .field("value") + .script(new Script("_value - 1", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -275,8 +277,12 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .field("value").script(new Script("_value - dec", ScriptType.INLINE, null, params)).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .field("value") + .script(new Script("_value - dec", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params)) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -311,8 +317,12 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .field("values").script(new Script("_value - 1")).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .field("values") + .script(new Script("_value - 1", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -328,8 +338,12 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .field("values").script(new Script("20 - _value")).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .field("values") + .script(new Script("20 - _value", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -348,8 +362,12 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .field("values").script(new Script("_value - dec", ScriptType.INLINE, null, params)).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .field("values") + .script(new Script("_value - dec", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params)) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -366,8 +384,11 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .script(new Script("doc['value'].value")).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .script(new Script("doc['value'].value", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -381,13 +402,19 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { int sigDigits = randomSignificantDigits(); Map params = new HashMap<>(); params.put("dec", 1); + + Script script = new Script("doc['value'].value - dec", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params); + final double[] pcts = randomPercents(minValue - 1, maxValue - 1); SearchResponse searchResponse = client() .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .script(new Script("doc['value'].value - dec", ScriptType.INLINE, null, params)).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .script(script) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -400,12 +427,18 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { public void testScriptMultiValued() throws Exception { int sigDigits = randomSignificantDigits(); final double[] pcts = randomPercents(minValues, maxValues); + + Script script = new Script("doc['values'].values", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap()); + SearchResponse searchResponse = client() .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentileRanks("percentile_ranks").method(PercentilesMethod.HDR).numberOfSignificantValueDigits(sigDigits) - .script(new Script("doc['values'].values")).values(pcts)) + percentileRanks("percentile_ranks") + .method(PercentilesMethod.HDR) + .numberOfSignificantValueDigits(sigDigits) + .script(script) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -419,6 +452,17 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { int sigDigits = randomSignificantDigits(); Map params = new HashMap<>(); params.put("dec", 1); + + // Equivalent to: + // + // List values = doc['values'].values; + // double[] res = new double[values.size()]; + // for (int i = 0; i < res.length; i++) { + // res[i] = values.get(i) - dec; + // }; + // return res; + Script script = new Script("decrement all values", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params); + final double[] pcts = randomPercents(minValues - 1, maxValues - 1); SearchResponse searchResponse = client() .prepareSearch("idx") @@ -427,10 +471,8 @@ public class HDRPercentileRanksTests extends AbstractNumericTestCase { percentileRanks("percentile_ranks") .method(PercentilesMethod.HDR) .numberOfSignificantValueDigits(sigDigits) - .script(new Script( - "List values = doc['values'].values; double[] res = new double[values.size()]; for (int i = 0; i < res.length; i++) { res[i] = values.get(i) - dec; }; return res;", - ScriptType.INLINE, null, params)) - .values(pcts)) + .script(script) + .values(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); diff --git a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentilesTests.java b/core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentilesIT.java similarity index 81% rename from modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentilesTests.java rename to core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentilesIT.java index 9c21928798a..0dd0ee6799c 100644 --- a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentilesTests.java +++ b/core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentilesIT.java @@ -16,7 +16,7 @@ * specific language governing permissions and limitations * under the License. */ -package org.elasticsearch.messy.tests; +package org.elasticsearch.search.aggregations.metrics; import org.elasticsearch.action.search.SearchResponse; import org.elasticsearch.common.logging.Loggers; @@ -24,13 +24,12 @@ import org.elasticsearch.common.util.CollectionUtils; import org.elasticsearch.plugins.Plugin; import org.elasticsearch.script.Script; import org.elasticsearch.script.ScriptService.ScriptType; -import org.elasticsearch.script.groovy.GroovyPlugin; +import org.elasticsearch.search.aggregations.AggregationTestScriptsPlugin; import org.elasticsearch.search.aggregations.bucket.filter.Filter; import org.elasticsearch.search.aggregations.bucket.global.Global; import org.elasticsearch.search.aggregations.bucket.histogram.Histogram; import org.elasticsearch.search.aggregations.bucket.histogram.Histogram.Order; import org.elasticsearch.search.aggregations.bucket.terms.Terms; -import org.elasticsearch.search.aggregations.metrics.AbstractNumericTestCase; import org.elasticsearch.search.aggregations.metrics.percentiles.Percentile; import org.elasticsearch.search.aggregations.metrics.percentiles.Percentiles; import org.elasticsearch.search.aggregations.metrics.percentiles.PercentilesMethod; @@ -42,6 +41,7 @@ import java.util.HashMap; import java.util.List; import java.util.Map; +import static java.util.Collections.emptyMap; import static org.elasticsearch.index.query.QueryBuilders.matchAllQuery; import static org.elasticsearch.index.query.QueryBuilders.termQuery; import static org.elasticsearch.search.aggregations.AggregationBuilders.filter; @@ -57,13 +57,11 @@ import static org.hamcrest.Matchers.lessThanOrEqualTo; import static org.hamcrest.Matchers.notNullValue; import static org.hamcrest.Matchers.sameInstance; -/** - * - */ -public class HDRPercentilesTests extends AbstractNumericTestCase { +public class HDRPercentilesIT extends AbstractNumericTestCase { + @Override protected Collection> nodePlugins() { - return Collections.singleton(GroovyPlugin.class); + return Collections.singleton(AggregationTestScriptsPlugin.class); } private static double[] randomPercentiles() { @@ -83,7 +81,7 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { } } Arrays.sort(percentiles); - Loggers.getLogger(HDRPercentilesTests.class).info("Using percentiles={}", Arrays.toString(percentiles)); + Loggers.getLogger(HDRPercentilesIT.class).info("Using percentiles={}", Arrays.toString(percentiles)); return percentiles; } @@ -130,8 +128,8 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { percentiles("percentiles").field("value") .numberOfSignificantValueDigits(sigDigits) .method(PercentilesMethod.HDR) - .percentiles(10, - 15))).execute().actionGet(); + .percentiles(10, 15))) + .execute().actionGet(); assertThat(searchResponse.getHits().getTotalHits(), equalTo(2L)); Histogram histo = searchResponse.getAggregations().get("histo"); @@ -210,7 +208,7 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { Percentiles percentiles = global.getAggregations().get("percentiles"); assertThat(percentiles, notNullValue()); assertThat(percentiles.getName(), equalTo("percentiles")); - assertThat((Percentiles) global.getProperty("percentiles"), sameInstance(percentiles)); + assertThat(global.getProperty("percentiles"), sameInstance(percentiles)); } @@ -240,8 +238,13 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR).field("value") - .script(new Script("_value - 1")).percentiles(pcts)).execute().actionGet(); + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .field("value") + .script(new Script("_value - 1", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -253,15 +256,20 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { public void testSingleValuedFieldWithValueScriptWithParams() throws Exception { Map params = new HashMap<>(); params.put("dec", 1); + final double[] pcts = randomPercentiles(); int sigDigits = randomSignificantDigits(); SearchResponse searchResponse = client() .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR).field("value") - .script(new Script("_value - dec", ScriptType.INLINE, null, params)).percentiles(pcts)).execute() - .actionGet(); + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .field("value") + .script(new Script("_value - dec", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params)) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -295,8 +303,13 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR).field("values") - .script(new Script("_value - 1")).percentiles(pcts)).execute().actionGet(); + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .field("values") + .script(new Script("_value - 1", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -311,8 +324,13 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR).field("values") - .script(new Script("20 - _value")).percentiles(pcts)).execute().actionGet(); + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .field("values") + .script(new Script("20 - _value", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -324,15 +342,20 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { public void testMultiValuedFieldWithValueScriptWithParams() throws Exception { Map params = new HashMap<>(); params.put("dec", 1); + final double[] pcts = randomPercentiles(); int sigDigits = randomSignificantDigits(); SearchResponse searchResponse = client() .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR).field("values") - .script(new Script("_value - dec", ScriptType.INLINE, null, params)).percentiles(pcts)).execute() - .actionGet(); + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .field("values") + .script(new Script("_value - dec", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params)) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -348,8 +371,12 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR) - .script(new Script("doc['value'].value")).percentiles(pcts)).execute().actionGet(); + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .script(new Script("doc['value'].value", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap())) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -361,14 +388,20 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { public void testScriptSingleValuedWithParams() throws Exception { Map params = new HashMap<>(); params.put("dec", 1); + + Script script = new Script("doc['value'].value - dec", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params); + final double[] pcts = randomPercentiles(); int sigDigits = randomSignificantDigits(); SearchResponse searchResponse = client() .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR) - .script(new Script("doc['value'].value - dec", ScriptType.INLINE, null, params)).percentiles(pcts)) + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .script(script) + .percentiles(pcts)) .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -381,12 +414,19 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { public void testScriptMultiValued() throws Exception { final double[] pcts = randomPercentiles(); int sigDigits = randomSignificantDigits(); + + Script script = new Script("doc['values'].values", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, emptyMap()); + SearchResponse searchResponse = client() .prepareSearch("idx") .setQuery(matchAllQuery()) .addAggregation( - percentiles("percentiles").numberOfSignificantValueDigits(sigDigits).method(PercentilesMethod.HDR) - .script(new Script("doc['values'].values")).percentiles(pcts)).execute().actionGet(); + percentiles("percentiles") + .numberOfSignificantValueDigits(sigDigits) + .method(PercentilesMethod.HDR) + .script(script) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); @@ -398,6 +438,17 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { public void testScriptMultiValuedWithParams() throws Exception { Map params = new HashMap<>(); params.put("dec", 1); + + // Equivalent to: + // + // List values = doc['values'].values; + // double[] res = new double[values.size()]; + // for (int i = 0; i < res.length; i++) { + // res[i] = values.get(i) - dec; + // }; + // return res; + Script script = new Script("decrement all values", ScriptType.INLINE, AggregationTestScriptsPlugin.NAME, params); + final double[] pcts = randomPercentiles(); int sigDigits = randomSignificantDigits(); SearchResponse searchResponse = client() @@ -407,9 +458,9 @@ public class HDRPercentilesTests extends AbstractNumericTestCase { percentiles("percentiles") .numberOfSignificantValueDigits(sigDigits) .method(PercentilesMethod.HDR) - .script(new Script( - "List values = doc['values'].values; double[] res = new double[values.size()]; for (int i = 0; i < res.length; i++) { res[i] = values.get(i) - dec; }; return res;", - ScriptType.INLINE, null, params)).percentiles(pcts)).execute().actionGet(); + .script(script) + .percentiles(pcts)) + .execute().actionGet(); assertHitCount(searchResponse, 10); diff --git a/core/src/test/java/org/elasticsearch/search/aggregations/metrics/TopHitsIT.java b/core/src/test/java/org/elasticsearch/search/aggregations/metrics/TopHitsIT.java index 84455c231aa..bfd4ed8ada9 100644 --- a/core/src/test/java/org/elasticsearch/search/aggregations/metrics/TopHitsIT.java +++ b/core/src/test/java/org/elasticsearch/search/aggregations/metrics/TopHitsIT.java @@ -30,6 +30,7 @@ import org.elasticsearch.common.xcontent.support.XContentMapValues; import org.elasticsearch.index.query.QueryBuilders; import org.elasticsearch.plugins.Plugin; import org.elasticsearch.script.MockScriptEngine; +import org.elasticsearch.script.MockScriptPlugin; import org.elasticsearch.script.Script; import org.elasticsearch.script.ScriptService; import org.elasticsearch.search.SearchHit; @@ -54,6 +55,8 @@ import java.util.Collection; import java.util.Collections; import java.util.Iterator; import java.util.List; +import java.util.Map; +import java.util.function.Function; import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder; import static org.elasticsearch.common.xcontent.XContentFactory.smileBuilder; @@ -92,7 +95,14 @@ public class TopHitsIT extends ESIntegTestCase { @Override protected Collection> nodePlugins() { - return Collections.singleton(MockScriptEngine.TestPlugin.class); + return Collections.singleton(CustomScriptPlugin.class); + } + + public static class CustomScriptPlugin extends MockScriptPlugin { + @Override + protected Map, Object>> pluginScripts() { + return Collections.emptyMap(); + } } public static String randomExecutionHint() { diff --git a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketScriptTests.java b/core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketScriptIT.java similarity index 84% rename from modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketScriptTests.java rename to core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketScriptIT.java index e481e2f59ae..220dfd29817 100644 --- a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketScriptTests.java +++ b/core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketScriptIT.java @@ -17,23 +17,21 @@ * under the License. */ -package org.elasticsearch.messy.tests; +package org.elasticsearch.search.aggregations.pipeline; import org.elasticsearch.action.index.IndexRequestBuilder; import org.elasticsearch.action.search.SearchResponse; import org.elasticsearch.common.bytes.BytesArray; import org.elasticsearch.common.xcontent.XContentBuilder; import org.elasticsearch.plugins.Plugin; +import org.elasticsearch.script.MockScriptPlugin; import org.elasticsearch.script.Script; import org.elasticsearch.script.ScriptService.ScriptType; -import org.elasticsearch.script.groovy.GroovyPlugin; -import org.elasticsearch.script.groovy.GroovyScriptEngineService; import org.elasticsearch.search.aggregations.bucket.histogram.Histogram; import org.elasticsearch.search.aggregations.bucket.histogram.InternalHistogram; import org.elasticsearch.search.aggregations.bucket.histogram.InternalHistogram.Bucket; import org.elasticsearch.search.aggregations.metrics.sum.Sum; import org.elasticsearch.search.aggregations.pipeline.BucketHelpers.GapPolicy; -import org.elasticsearch.search.aggregations.pipeline.SimpleValue; import org.elasticsearch.test.ESIntegTestCase; import java.io.IOException; @@ -43,18 +41,20 @@ import java.util.Collections; import java.util.HashMap; import java.util.List; import java.util.Map; +import java.util.function.Function; import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder; import static org.elasticsearch.search.aggregations.AggregationBuilders.histogram; import static org.elasticsearch.search.aggregations.AggregationBuilders.sum; import static org.elasticsearch.search.aggregations.pipeline.PipelineAggregatorBuilders.bucketScript; +import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertAcked; import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertSearchResponse; import static org.hamcrest.Matchers.equalTo; import static org.hamcrest.Matchers.notNullValue; import static org.hamcrest.Matchers.nullValue; @ESIntegTestCase.SuiteScopeTestCase -public class BucketScriptTests extends ESIntegTestCase { +public class BucketScriptIT extends ESIntegTestCase { private static final String FIELD_1_NAME = "field1"; private static final String FIELD_2_NAME = "field2"; @@ -68,7 +68,54 @@ public class BucketScriptTests extends ESIntegTestCase { @Override protected Collection> nodePlugins() { - return Collections.singleton(GroovyPlugin.class); + return Collections.singleton(CustomScriptPlugin.class); + } + + public static class CustomScriptPlugin extends MockScriptPlugin { + + @Override + protected Map, Object>> pluginScripts() { + Map, Object>> scripts = new HashMap<>(); + + scripts.put("_value0 + _value1 + _value2", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + double value2 = (double) vars.get("_value2"); + return value0 + value1 + value2; + }); + + scripts.put("_value0 + _value1 / _value2", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + double value2 = (double) vars.get("_value2"); + return value0 + value1 / value2; + }); + + scripts.put("_value0", vars -> vars.get("_value0")); + + scripts.put("foo + bar + baz", vars -> { + double foo = (double) vars.get("foo"); + double bar = (double) vars.get("bar"); + double baz = (double) vars.get("baz"); + return foo + bar + baz; + }); + + scripts.put("(_value0 + _value1 + _value2) * factor", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + double value2 = (double) vars.get("_value2"); + return (value0 + value1 + value2) * (int) vars.get("factor"); + }); + + scripts.put("my_script", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + double value2 = (double) vars.get("_value2"); + return value0 + value1 + value2; + }); + + return scripts; + } } @Override @@ -86,11 +133,6 @@ public class BucketScriptTests extends ESIntegTestCase { builders.add(client().prepareIndex("idx", "type").setSource(newDocBuilder())); } - client().admin().cluster().preparePutStoredScript() - .setId("my_script") - .setScriptLang(GroovyScriptEngineService.NAME) - .setSource(new BytesArray("{ \"script\": \"_value0 + _value1 + _value2\" }")).get(); - indexRandom(true, builders); ensureSearchable(); } @@ -117,8 +159,10 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) .subAggregation( - bucketScript("seriesArithmetic", new Script("_value0 + _value1 + _value2", ScriptType.INLINE, null, null) - , "field2Sum", "field3Sum", "field4Sum"))).execute().actionGet(); + bucketScript("seriesArithmetic", + new Script("_value0 + _value1 + _value2", ScriptType.INLINE, CustomScriptPlugin.NAME, null) + , "field2Sum", "field3Sum", "field4Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -161,8 +205,10 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) .subAggregation( - bucketScript("seriesArithmetic", new Script("_value0 + _value1 / _value2", ScriptType.INLINE, null, null), - "field2Sum", "field3Sum", "field4Sum"))).execute().actionGet(); + bucketScript("seriesArithmetic", + new Script("_value0 + _value1 / _value2", ScriptType.INLINE, CustomScriptPlugin.NAME, null), + "field2Sum", "field3Sum", "field4Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -203,8 +249,10 @@ public class BucketScriptTests extends ESIntegTestCase { .interval(interval) .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) .subAggregation( - bucketScript("seriesArithmetic", new Script("_value0", ScriptType.INLINE, null, null), - "field2Sum"))).execute().actionGet(); + bucketScript("seriesArithmetic", + new Script("_value0", ScriptType.INLINE, CustomScriptPlugin.NAME, null), + "field2Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -246,7 +294,8 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) .subAggregation( bucketScript("seriesArithmetic", bucketsPathsMap, - new Script("foo + bar + baz", ScriptType.INLINE, null, null)))).execute().actionGet(); + new Script("foo + bar + baz", ScriptType.INLINE, CustomScriptPlugin.NAME, null)))) + .execute().actionGet(); assertSearchResponse(response); @@ -281,6 +330,9 @@ public class BucketScriptTests extends ESIntegTestCase { public void testInlineScriptWithParams() { Map params = new HashMap<>(); params.put("factor", 3); + + Script script = new Script("(_value0 + _value1 + _value2) * factor", ScriptType.INLINE, CustomScriptPlugin.NAME, params); + SearchResponse response = client() .prepareSearch("idx") .addAggregation( @@ -290,9 +342,8 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) - .subAggregation( - bucketScript("seriesArithmetic", new Script("(_value0 + _value1 + _value2) * factor", ScriptType.INLINE, null, params), - "field2Sum", "field3Sum", "field4Sum"))).execute().actionGet(); + .subAggregation(bucketScript("seriesArithmetic", script, "field2Sum", "field3Sum", "field4Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -335,8 +386,10 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) .subAggregation( - bucketScript("seriesArithmetic", new Script("_value0 + _value1 + _value2", ScriptType.INLINE, null, null), - "field2Sum", "field3Sum", "field4Sum").gapPolicy(GapPolicy.INSERT_ZEROS))).execute().actionGet(); + bucketScript("seriesArithmetic", + new Script("_value0 + _value1 + _value2", ScriptType.INLINE, CustomScriptPlugin.NAME, null), + "field2Sum", "field3Sum", "field4Sum").gapPolicy(GapPolicy.INSERT_ZEROS))) + .execute().actionGet(); assertSearchResponse(response); @@ -370,7 +423,13 @@ public class BucketScriptTests extends ESIntegTestCase { } } - public void testIndexedScript() { + public void testStoredScript() { + assertAcked(client().admin().cluster().preparePutStoredScript() + .setId("my_script") + .setScriptLang(CustomScriptPlugin.NAME) + // Script source is not interpreted but it references a pre-defined script from CustomScriptPlugin + .setSource(new BytesArray("{ \"script\": \"my_script\" }"))); + SearchResponse response = client() .prepareSearch("idx") .addAggregation( @@ -381,7 +440,8 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) .subAggregation( - bucketScript("seriesArithmetic", new Script("my_script", ScriptType.STORED, null, null), + bucketScript("seriesArithmetic", + new Script("my_script", ScriptType.STORED, CustomScriptPlugin.NAME, null), "field2Sum", "field3Sum", "field4Sum"))).execute().actionGet(); assertSearchResponse(response); @@ -425,7 +485,8 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) .subAggregation( - bucketScript("seriesArithmetic", new Script("_value0 + _value1 + _value2", ScriptType.INLINE, null, null), + bucketScript("seriesArithmetic", + new Script("_value0 + _value1 + _value2", ScriptType.INLINE, CustomScriptPlugin.NAME, null), "field2Sum", "field3Sum", "field4Sum"))) .execute().actionGet(); @@ -448,7 +509,8 @@ public class BucketScriptTests extends ESIntegTestCase { .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) .subAggregation(sum("field4Sum").field(FIELD_4_NAME)) .subAggregation( - bucketScript("seriesArithmetic", new Script("_value0 + _value1 + _value2", ScriptType.INLINE, null, null), + bucketScript("seriesArithmetic", + new Script("_value0 + _value1 + _value2", ScriptType.INLINE, CustomScriptPlugin.NAME, null), "field2Sum", "field3Sum", "field4Sum"))).execute().actionGet(); assertSearchResponse(response); diff --git a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketSelectorTests.java b/core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketSelectorIT.java similarity index 68% rename from modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketSelectorTests.java rename to core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketSelectorIT.java index 5b796a92d7f..64dc7e50bcc 100644 --- a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketSelectorTests.java +++ b/core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketSelectorIT.java @@ -17,17 +17,16 @@ * under the License. */ -package org.elasticsearch.messy.tests; +package org.elasticsearch.search.aggregations.pipeline; import org.elasticsearch.action.index.IndexRequestBuilder; import org.elasticsearch.action.search.SearchResponse; import org.elasticsearch.common.bytes.BytesArray; import org.elasticsearch.common.xcontent.XContentBuilder; import org.elasticsearch.plugins.Plugin; +import org.elasticsearch.script.MockScriptPlugin; import org.elasticsearch.script.Script; import org.elasticsearch.script.ScriptService.ScriptType; -import org.elasticsearch.script.groovy.GroovyPlugin; -import org.elasticsearch.script.groovy.GroovyScriptEngineService; import org.elasticsearch.search.aggregations.bucket.histogram.ExtendedBounds; import org.elasticsearch.search.aggregations.bucket.histogram.Histogram; import org.elasticsearch.search.aggregations.bucket.histogram.InternalHistogram; @@ -43,12 +42,14 @@ import java.util.Collections; import java.util.HashMap; import java.util.List; import java.util.Map; +import java.util.function.Function; import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder; import static org.elasticsearch.search.aggregations.AggregationBuilders.histogram; import static org.elasticsearch.search.aggregations.AggregationBuilders.sum; import static org.elasticsearch.search.aggregations.pipeline.PipelineAggregatorBuilders.bucketSelector; import static org.elasticsearch.search.aggregations.pipeline.PipelineAggregatorBuilders.derivative; +import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertAcked; import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertSearchResponse; import static org.hamcrest.Matchers.equalTo; import static org.hamcrest.Matchers.greaterThan; @@ -57,7 +58,7 @@ import static org.hamcrest.Matchers.notNullValue; import static org.hamcrest.Matchers.nullValue; @ESIntegTestCase.SuiteScopeTestCase -public class BucketSelectorTests extends ESIntegTestCase { +public class BucketSelectorIT extends ESIntegTestCase { private static final String FIELD_1_NAME = "field1"; private static final String FIELD_2_NAME = "field2"; @@ -71,7 +72,69 @@ public class BucketSelectorTests extends ESIntegTestCase { @Override protected Collection> nodePlugins() { - return Collections.singleton(GroovyPlugin.class); + return Collections.singleton(CustomScriptPlugin.class); + } + + public static class CustomScriptPlugin extends MockScriptPlugin { + + @Override + protected Map, Object>> pluginScripts() { + Map, Object>> scripts = new HashMap<>(); + + scripts.put("Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + return Double.isNaN(value0) ? false : (value0 + value1 > 100); + }); + + scripts.put("Double.isNaN(_value0) ? true : (_value0 < 10000)", vars -> { + double value0 = (double) vars.get("_value0"); + return Double.isNaN(value0) ? true : (value0 < 10000); + }); + + scripts.put("Double.isNaN(_value0) ? false : (_value0 > 10000)", vars -> { + double value0 = (double) vars.get("_value0"); + return Double.isNaN(value0) ? false : (value0 > 10000); + }); + + scripts.put("Double.isNaN(_value0) ? false : (_value0 < _value1)", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + return Double.isNaN(value0) ? false : (value0 < value1); + }); + + scripts.put("Double.isNaN(_value0) ? false : (_value0 > 100)", vars -> { + double value0 = (double) vars.get("_value0"); + return Double.isNaN(value0) ? false : (value0 > 10000); + }); + + scripts.put("Double.isNaN(my_value1) ? false : (my_value1 + my_value2 > 100)", vars -> { + double myValue1 = (double) vars.get("my_value1"); + double myValue2 = (double) vars.get("my_value2"); + return Double.isNaN(myValue1) ? false : (myValue1 + myValue2 > 100); + }); + + scripts.put("Double.isNaN(_value0) ? false : (_value0 + _value1 > threshold)", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + int threshold = (int) vars.get("threshold"); + return Double.isNaN(value0) ? false : (value0 + value1 > threshold); + }); + + scripts.put("_value0 + _value1 > 100", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + return (value0 + value1 > 100); + }); + + scripts.put("my_script", vars -> { + double value0 = (double) vars.get("_value0"); + double value1 = (double) vars.get("_value1"); + return Double.isNaN(value0) ? false : (value0 + value1 > 100); + }); + + return scripts; + } } @Override @@ -94,9 +157,6 @@ public class BucketSelectorTests extends ESIntegTestCase { builders.add(client().prepareIndex("idx_with_gaps", "type").setSource(newDocBuilder(3, 1, 0, 0))); builders.add(client().prepareIndex("idx_with_gaps", "type").setSource(newDocBuilder(3, 3, 0, 0))); - client().admin().cluster().preparePutStoredScript().setId("my_script").setScriptLang(GroovyScriptEngineService.NAME) - .setSource(new BytesArray("{ \"script\": \"Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)\" }")).get(); - indexRandom(true, builders); ensureSearchable(); } @@ -118,12 +178,13 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScript() { + Script script = + new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)", ScriptType.INLINE, CustomScriptPlugin.NAME, null); + SearchResponse response = client().prepareSearch("idx") .addAggregation(histogram("histo").field(FIELD_1_NAME).interval(interval) .subAggregation(sum("field2Sum").field(FIELD_2_NAME)).subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation(bucketSelector("bucketSelector", - new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)", ScriptType.INLINE, null, null), - "field2Sum", "field3Sum"))) + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) .execute().actionGet(); assertSearchResponse(response); @@ -146,6 +207,8 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScriptNoBucketsPruned() { + Script script = new Script("Double.isNaN(_value0) ? true : (_value0 < 10000)", ScriptType.INLINE, CustomScriptPlugin.NAME, null); + SearchResponse response = client() .prepareSearch("idx") .addAggregation( @@ -154,10 +217,8 @@ public class BucketSelectorTests extends ESIntegTestCase { .interval(interval) .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation( - bucketSelector("bucketSelector", new Script("Double.isNaN(_value0) ? true : (_value0 < 10000)", - ScriptType.INLINE, null, null), "field2Sum", "field3Sum"))).execute() - .actionGet(); + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -179,6 +240,8 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScriptNoBucketsLeft() { + Script script = new Script("Double.isNaN(_value0) ? false : (_value0 > 10000)", ScriptType.INLINE, CustomScriptPlugin.NAME, null); + SearchResponse response = client() .prepareSearch("idx") .addAggregation( @@ -187,9 +250,8 @@ public class BucketSelectorTests extends ESIntegTestCase { .interval(interval) .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation( - bucketSelector("bucketSelector", new Script("Double.isNaN(_value0) ? false : (_value0 > 10000)", - ScriptType.INLINE, null, null), "field2Sum", "field3Sum"))).execute().actionGet(); + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -201,6 +263,8 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScript2() { + Script script = new Script("Double.isNaN(_value0) ? false : (_value0 < _value1)", ScriptType.INLINE, CustomScriptPlugin.NAME, null); + SearchResponse response = client() .prepareSearch("idx") .addAggregation( @@ -209,9 +273,8 @@ public class BucketSelectorTests extends ESIntegTestCase { .interval(interval) .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation( - bucketSelector("bucketSelector", new Script("Double.isNaN(_value0) ? false : (_value0 < _value1)", - ScriptType.INLINE, null, null), "field2Sum", "field3Sum"))).execute().actionGet(); + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -233,6 +296,8 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScriptSingleVariable() { + Script script = new Script("Double.isNaN(_value0) ? false : (_value0 > 100)", ScriptType.INLINE, CustomScriptPlugin.NAME, null); + SearchResponse response = client() .prepareSearch("idx") .addAggregation( @@ -240,9 +305,8 @@ public class BucketSelectorTests extends ESIntegTestCase { .field(FIELD_1_NAME) .interval(interval) .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) - .subAggregation( - bucketSelector("bucketSelector", new Script("Double.isNaN(_value0) ? false : (_value0 > 100)", - ScriptType.INLINE,null, null), "field2Sum"))).execute().actionGet(); + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -261,15 +325,21 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScriptNamedVars() { + Script script = new Script("Double.isNaN(my_value1) ? false : (my_value1 + my_value2 > 100)", ScriptType.INLINE, + CustomScriptPlugin.NAME, null); + Map bucketPathsMap = new HashMap<>(); bucketPathsMap.put("my_value1", "field2Sum"); bucketPathsMap.put("my_value2", "field3Sum"); SearchResponse response = client().prepareSearch("idx") - .addAggregation(histogram("histo").field(FIELD_1_NAME).interval(interval) - .subAggregation(sum("field2Sum").field(FIELD_2_NAME)).subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation(bucketSelector("bucketSelector", bucketPathsMap, new Script( - "Double.isNaN(my_value1) ? false : (my_value1 + my_value2 > 100)", ScriptType.INLINE, null, null)))) + .addAggregation( + histogram("histo") + .field(FIELD_1_NAME) + .interval(interval) + .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) + .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) + .subAggregation(bucketSelector("bucketSelector", bucketPathsMap, script))) .execute().actionGet(); assertSearchResponse(response); @@ -292,13 +362,17 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScriptWithParams() { - Map params = new HashMap<>(); - params.put("threshold", 100); - SearchResponse response = client().prepareSearch("idx").addAggregation(histogram("histo").field(FIELD_1_NAME).interval(interval) - .subAggregation(sum("field2Sum").field(FIELD_2_NAME)).subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation(bucketSelector("bucketSelector", - new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > threshold)", ScriptType.INLINE, null, params), - "field2Sum", "field3Sum"))) + Script script = new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > threshold)", ScriptType.INLINE, + CustomScriptPlugin.NAME, Collections.singletonMap("threshold", 100)); + + SearchResponse response = client().prepareSearch("idx") + .addAggregation( + histogram("histo") + .field(FIELD_1_NAME) + .interval(interval) + .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) + .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) .execute().actionGet(); assertSearchResponse(response); @@ -321,13 +395,17 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testInlineScriptInsertZeros() { + Script script = new Script("_value0 + _value1 > 100", ScriptType.INLINE, CustomScriptPlugin.NAME, null); + SearchResponse response = client().prepareSearch("idx") .addAggregation( - histogram("histo").field(FIELD_1_NAME).interval(interval).subAggregation(sum("field2Sum").field(FIELD_2_NAME)) + histogram("histo") + .field(FIELD_1_NAME) + .interval(interval) + .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation(bucketSelector("bucketSelector", - new Script("_value0 + _value1 > 100", ScriptType.INLINE, null, null), "field2Sum", "field3Sum") - .gapPolicy(GapPolicy.INSERT_ZEROS))) + .subAggregation(bucketSelector("bucketSelector", script , "field2Sum", "field3Sum") + .gapPolicy(GapPolicy.INSERT_ZEROS))) .execute().actionGet(); assertSearchResponse(response); @@ -349,7 +427,15 @@ public class BucketSelectorTests extends ESIntegTestCase { } } - public void testIndexedScript() { + public void testStoredScript() { + assertAcked(client().admin().cluster().preparePutStoredScript() + .setId("my_script") + .setScriptLang(CustomScriptPlugin.NAME) + // Source is not interpreted but my_script is defined in CustomScriptPlugin + .setSource(new BytesArray("{ \"script\": \"Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)\" }"))); + + Script script = new Script("my_script", ScriptType.STORED, CustomScriptPlugin.NAME, null); + SearchResponse response = client() .prepareSearch("idx") .addAggregation( @@ -358,9 +444,8 @@ public class BucketSelectorTests extends ESIntegTestCase { .interval(interval) .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation( - bucketSelector("bucketSelector", new Script("my_script", ScriptType.STORED, null, null), - "field2Sum", "field3Sum"))).execute().actionGet(); + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) + .execute().actionGet(); assertSearchResponse(response); @@ -382,12 +467,17 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testUnmapped() throws Exception { + Script script = new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)", ScriptType.INLINE, + CustomScriptPlugin.NAME, null); + SearchResponse response = client().prepareSearch("idx_unmapped") - .addAggregation(histogram("histo").field(FIELD_1_NAME).interval(interval) - .subAggregation(sum("field2Sum").field(FIELD_2_NAME)).subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation(bucketSelector("bucketSelector", - new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)", ScriptType.INLINE, null, null), - "field2Sum", "field3Sum"))) + .addAggregation( + histogram("histo") + .field(FIELD_1_NAME) + .interval(interval) + .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) + .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) .execute().actionGet(); assertSearchResponse(response); @@ -399,12 +489,17 @@ public class BucketSelectorTests extends ESIntegTestCase { } public void testPartiallyUnmapped() throws Exception { + Script script = new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)", ScriptType.INLINE, + CustomScriptPlugin.NAME, null); + SearchResponse response = client().prepareSearch("idx", "idx_unmapped") - .addAggregation(histogram("histo").field(FIELD_1_NAME).interval(interval) - .subAggregation(sum("field2Sum").field(FIELD_2_NAME)).subAggregation(sum("field3Sum").field(FIELD_3_NAME)) - .subAggregation(bucketSelector("bucketSelector", - new Script("Double.isNaN(_value0) ? false : (_value0 + _value1 > 100)", ScriptType.INLINE, null, null), - "field2Sum", "field3Sum"))) + .addAggregation( + histogram("histo") + .field(FIELD_1_NAME) + .interval(interval) + .subAggregation(sum("field2Sum").field(FIELD_2_NAME)) + .subAggregation(sum("field3Sum").field(FIELD_3_NAME)) + .subAggregation(bucketSelector("bucketSelector", script, "field2Sum", "field3Sum"))) .execute().actionGet(); assertSearchResponse(response); @@ -428,9 +523,18 @@ public class BucketSelectorTests extends ESIntegTestCase { public void testEmptyBuckets() { SearchResponse response = client().prepareSearch("idx_with_gaps") - .addAggregation(histogram("histo").field(FIELD_1_NAME).interval(1) - .subAggregation(histogram("inner_histo").field(FIELD_1_NAME).interval(1).extendedBounds(new ExtendedBounds(1L, 4L)) - .minDocCount(0).subAggregation(derivative("derivative", "_count").gapPolicy(GapPolicy.INSERT_ZEROS)))) + .addAggregation( + histogram("histo") + .field(FIELD_1_NAME) + .interval(1) + .subAggregation( + histogram("inner_histo") + .field(FIELD_1_NAME) + .interval(1) + .extendedBounds(new ExtendedBounds(1L, 4L)) + .minDocCount(0) + .subAggregation(derivative("derivative", "_count") + .gapPolicy(GapPolicy.INSERT_ZEROS)))) .execute().actionGet(); assertSearchResponse(response); diff --git a/core/src/test/java/org/elasticsearch/search/innerhits/InnerHitsIT.java b/core/src/test/java/org/elasticsearch/search/innerhits/InnerHitsIT.java index 56b33c6007e..780e8cbcad4 100644 --- a/core/src/test/java/org/elasticsearch/search/innerhits/InnerHitsIT.java +++ b/core/src/test/java/org/elasticsearch/search/innerhits/InnerHitsIT.java @@ -31,6 +31,7 @@ import org.elasticsearch.index.query.BoolQueryBuilder; import org.elasticsearch.index.query.InnerHitBuilder; import org.elasticsearch.plugins.Plugin; import org.elasticsearch.script.MockScriptEngine; +import org.elasticsearch.script.MockScriptPlugin; import org.elasticsearch.script.Script; import org.elasticsearch.script.ScriptService; import org.elasticsearch.search.SearchHit; @@ -47,6 +48,8 @@ import java.util.Collection; import java.util.Collections; import java.util.List; import java.util.Locale; +import java.util.Map; +import java.util.function.Function; import static org.elasticsearch.action.support.WriteRequest.RefreshPolicy.IMMEDIATE; import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder; @@ -71,9 +74,17 @@ import static org.hamcrest.Matchers.notNullValue; import static org.hamcrest.Matchers.nullValue; public class InnerHitsIT extends ESIntegTestCase { + @Override protected Collection> nodePlugins() { - return pluginList(MockScriptEngine.TestPlugin.class); + return Collections.singleton(CustomScriptPlugin.class); + } + + public static class CustomScriptPlugin extends MockScriptPlugin { + @Override + protected Map, Object>> pluginScripts() { + return Collections.emptyMap(); + } } public void testSimpleNested() throws Exception { diff --git a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/package-info.java b/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/package-info.java index ebc03bea2b3..a9bf09344f2 100644 --- a/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/package-info.java +++ b/modules/lang-groovy/src/test/java/org/elasticsearch/messy/tests/package-info.java @@ -36,8 +36,6 @@ */ /* List of renames that took place: renamed: core/src/test/java/org/elasticsearch/search/aggregations/metrics/AvgIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/AvgTests.java - renamed: core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketScriptIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketScriptTests.java - renamed: core/src/test/java/org/elasticsearch/search/aggregations/pipeline/BucketSelectorIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BucketSelectorTests.java renamed: core/src/test/java/org/elasticsearch/document/BulkIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/BulkTests.java renamed: core/src/test/java/org/elasticsearch/search/aggregations/metrics/CardinalityIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/CardinalityTests.java renamed: core/src/test/java/org/elasticsearch/search/child/ChildQuerySearchIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/ChildQuerySearchTests.java @@ -50,8 +48,6 @@ renamed: core/src/test/java/org/elasticsearch/search/aggregations/metrics/ExtendedStatsIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/ExtendedStatsTests.java renamed: core/src/test/java/org/elasticsearch/search/functionscore/FunctionScoreIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/FunctionScoreTests.java renamed: core/src/test/java/org/elasticsearch/search/geo/GeoDistanceIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/GeoDistanceTests.java - renamed: core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentileRanksIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentileRanksTests.java - renamed: core/src/test/java/org/elasticsearch/search/aggregations/metrics/HDRPercentilesIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HDRPercentilesTests.java renamed: core/src/test/java/org/elasticsearch/search/aggregations/bucket/HistogramIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/HistogramTests.java renamed: core/src/test/java/org/elasticsearch/search/aggregations/bucket/IPv4RangeIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/IPv4RangeTests.java renamed: core/src/test/java/org/elasticsearch/script/IndexLookupIT.java -> plugins/lang-groovy/src/test/java/org/elasticsearch/messy/tests/IndexLookupTests.java diff --git a/test/framework/src/main/java/org/elasticsearch/script/MockScriptEngine.java b/test/framework/src/main/java/org/elasticsearch/script/MockScriptEngine.java index 61a0cf6c236..519e52074da 100644 --- a/test/framework/src/main/java/org/elasticsearch/script/MockScriptEngine.java +++ b/test/framework/src/main/java/org/elasticsearch/script/MockScriptEngine.java @@ -22,92 +22,60 @@ package org.elasticsearch.script; import org.apache.lucene.index.LeafReaderContext; import org.elasticsearch.common.Nullable; import org.elasticsearch.common.bytes.BytesArray; -import org.elasticsearch.common.settings.Settings; -import org.elasticsearch.plugins.Plugin; -import org.elasticsearch.plugins.ScriptPlugin; +import org.elasticsearch.search.lookup.LeafSearchLookup; import org.elasticsearch.search.lookup.SearchLookup; import java.io.IOException; +import java.util.Collections; +import java.util.HashMap; import java.util.Map; +import java.util.function.Function; /** - * A dummy script engine used for testing. Scripts must be a number. Many - * tests rely on the fact this thing returns a String as its compiled form. - * they even try to serialize it over the network! + * A mocked script engine that can be used for testing purpose. */ public class MockScriptEngine implements ScriptEngineService { public static final String NAME = "mockscript"; - /** A compiled script, just holds the scripts name, source, and params that were passed in */ - public static class MockCompiledScript { - public final String name; - public final String source; - public final Map params; + private final String type; + private final Map, Object>> scripts; - MockCompiledScript(String name, String source, Map params) { - this.name = name; - this.source = source; - this.params = params; - } + public MockScriptEngine(String type, Map, Object>> scripts) { + this.type = type; + this.scripts = Collections.unmodifiableMap(scripts); } - public static class TestPlugin extends Plugin implements ScriptPlugin { - @Override - public ScriptEngineService getScriptEngineService(Settings settings) { - return new MockScriptEngine(); - } + public MockScriptEngine() { + this(NAME, Collections.emptyMap()); } @Override public String getType() { - return NAME; + return type; } @Override public String getExtension() { - return NAME; + return getType(); } @Override - public Object compile(String scriptName, String scriptSource, Map params) { - return new MockCompiledScript(scriptName, scriptSource, params); + public Object compile(String name, String source, Map params) { + Function, Object> script = scripts.get(source); + return new MockCompiledScript(name, params, source, script); } @Override public ExecutableScript executable(CompiledScript compiledScript, @Nullable Map vars) { - assert compiledScript.compiled() instanceof MockCompiledScript - : "do NOT pass compiled scripts from other engines to me, I will fail your test, got: " + compiledScript; - return new AbstractExecutableScript() { - @Override - public Object run() { - return new BytesArray(((MockCompiledScript)compiledScript.compiled()).source); - } - }; + MockCompiledScript compiled = (MockCompiledScript) compiledScript.compiled(); + return compiled.createExecutableScript(vars); } @Override public SearchScript search(CompiledScript compiledScript, SearchLookup lookup, @Nullable Map vars) { - return new SearchScript() { - @Override - public LeafSearchScript getLeafSearchScript(LeafReaderContext context) throws IOException { - AbstractSearchScript leafSearchScript = new AbstractSearchScript() { - - @Override - public Object run() { - return ((MockCompiledScript)compiledScript.compiled()).source; - } - - }; - leafSearchScript.setLookup(lookup.getLeafSearchLookup(context)); - return leafSearchScript; - } - - @Override - public boolean needsScores() { - return false; - } - }; + MockCompiledScript compiled = (MockCompiledScript) compiledScript.compiled(); + return compiled.createSearchScript(vars, lookup); } @Override @@ -118,4 +86,111 @@ public class MockScriptEngine implements ScriptEngineService { public boolean isInlineScriptEnabled() { return true; } + + + public class MockCompiledScript { + + private final String name; + private final String source; + private final Map params; + private final Function, Object> script; + + public MockCompiledScript(String name, Map params, String source, Function, Object> script) { + this.name = name; + this.source = source; + this.params = params; + this.script = script; + } + + public String getName() { + return name; + } + + public ExecutableScript createExecutableScript(Map vars) { + Map context = new HashMap<>(); + if (params != null) { + context.putAll(params); + } + if (vars != null) { + context.putAll(vars); + } + return new MockExecutableScript(context, script != null ? script : ctx -> new BytesArray(source)); + } + + public SearchScript createSearchScript(Map vars, SearchLookup lookup) { + Map context = new HashMap<>(); + if (params != null) { + context.putAll(params); + } + if (vars != null) { + context.putAll(vars); + } + return new MockSearchScript(lookup, context, script != null ? script : ctx -> source); + } + } + + public class MockExecutableScript implements ExecutableScript { + + private final Function, Object> script; + private final Map vars; + + public MockExecutableScript(Map vars, Function, Object> script) { + this.vars = vars; + this.script = script; + } + + @Override + public void setNextVar(String name, Object value) { + vars.put(name, value); + } + + @Override + public Object run() { + return script.apply(vars); + } + } + + public class MockSearchScript implements SearchScript { + + private final Function, Object> script; + private final Map vars; + private final SearchLookup lookup; + + public MockSearchScript(SearchLookup lookup, Map vars, Function, Object> script) { + this.lookup = lookup; + this.vars = vars; + this.script = script; + } + + @Override + public LeafSearchScript getLeafSearchScript(LeafReaderContext context) throws IOException { + LeafSearchLookup leafLookup = lookup.getLeafSearchLookup(context); + + Map ctx = new HashMap<>(); + ctx.putAll(leafLookup.asMap()); + if (vars != null) { + ctx.putAll(vars); + } + + AbstractSearchScript leafSearchScript = new AbstractSearchScript() { + + @Override + public Object run() { + return script.apply(ctx); + } + + @Override + public void setNextVar(String name, Object value) { + ctx.put(name, value); + } + }; + leafSearchScript.setLookup(leafLookup); + return leafSearchScript; + } + + @Override + public boolean needsScores() { + return false; + } + } } diff --git a/test/framework/src/main/java/org/elasticsearch/script/MockScriptPlugin.java b/test/framework/src/main/java/org/elasticsearch/script/MockScriptPlugin.java new file mode 100644 index 00000000000..dc397bd0b14 --- /dev/null +++ b/test/framework/src/main/java/org/elasticsearch/script/MockScriptPlugin.java @@ -0,0 +1,46 @@ +/* + * 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.script; + +import org.elasticsearch.common.settings.Settings; +import org.elasticsearch.plugins.Plugin; +import org.elasticsearch.plugins.ScriptPlugin; + +import java.util.Map; +import java.util.function.Function; + +/** + * A script plugin that uses {@link MockScriptEngine} as the script engine for tests. + */ +public abstract class MockScriptPlugin extends Plugin implements ScriptPlugin { + + public static final String NAME = MockScriptEngine.NAME; + + @Override + public ScriptEngineService getScriptEngineService(Settings settings) { + return new MockScriptEngine(pluginScriptLang(), pluginScripts()); + } + + protected abstract Map, Object>> pluginScripts(); + + public String pluginScriptLang() { + return NAME; + } +}