Scripting: Remove native scripts (#24726)

Native scripts have been replaced in documentation by implementing
a ScriptEngine and they were deprecated in 5.5.0. This commit
removes the native script infrastructure for 6.0.

closes #19966
This commit is contained in:
Ryan Ernst 2017-05-17 14:49:24 -07:00 committed by GitHub
parent 463fe2f4d4
commit 26e2e933f5
31 changed files with 267 additions and 1446 deletions

View File

@ -19,13 +19,9 @@
package org.elasticsearch.plugins;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.ScriptContext;
import org.elasticsearch.script.ScriptEngine;
import java.util.Collections;
import java.util.List;
/**
* An additional extension point for {@link Plugin}s that extends Elasticsearch's scripting functionality.
*/
@ -38,13 +34,6 @@ public interface ScriptPlugin {
return null;
}
/**
* Returns a list of {@link NativeScriptFactory} instances.
*/
default List<NativeScriptFactory> getNativeScripts() {
return Collections.emptyList();
}
/**
* Returns a {@link ScriptContext.Plugin} instance or <code>null</code> if this plugin doesn't add a new script context plugin
*/

View File

@ -1,40 +0,0 @@
/*
* 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;
/**
* A simpler base class instead of {@link AbstractSearchScript} for computations
* that return a double number.
*/
public abstract class AbstractDoubleSearchScript extends AbstractSearchScript {
@Override
public Object run() {
return runAsDouble();
}
@Override
public abstract double runAsDouble();
@Override
public long runAsLong() {
return (long) runAsDouble();
}
}

View File

@ -1,27 +0,0 @@
/*
* 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;
public abstract class AbstractExecutableScript implements ExecutableScript {
@Override
public void setNextVar(String name, Object value) {
}
}

View File

@ -1,40 +0,0 @@
/*
* 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;
/**
* A simpler base class instead of {@link AbstractSearchScript} for computations
* that return a long number.
*/
public abstract class AbstractLongSearchScript extends AbstractSearchScript {
@Override
public Object run() {
return runAsLong();
}
@Override
public abstract long runAsLong();
@Override
public double runAsDouble() {
return runAsLong();
}
}

View File

@ -1,124 +0,0 @@
/*
* 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.apache.lucene.search.Scorer;
import org.elasticsearch.index.fielddata.ScriptDocValues;
import org.elasticsearch.search.lookup.LeafDocLookup;
import org.elasticsearch.search.lookup.LeafFieldsLookup;
import org.elasticsearch.search.lookup.LeafSearchLookup;
import org.elasticsearch.search.lookup.SourceLookup;
import java.io.IOException;
import java.util.Map;
/**
* A base class for any script type that is used during the search process (custom score, aggs, and so on).
* <p>
* If the script returns a specific numeric type, consider overriding the type specific base classes
* such as {@link AbstractDoubleSearchScript} and {@link AbstractLongSearchScript}
* for better performance.
* <p>
* The use is required to implement the {@link #run()} method.
*/
public abstract class AbstractSearchScript extends AbstractExecutableScript implements LeafSearchScript {
private LeafSearchLookup lookup;
private Scorer scorer;
/**
* Returns the doc lookup allowing to access field data (cached) values as well as the current document score
* (where applicable).
*/
protected final LeafDocLookup doc() {
return lookup.doc();
}
/**
* Returns the current score and only applicable when used as a scoring script in a custom score query!.
*/
protected final float score() throws IOException {
return scorer.score();
}
/**
* Returns field data strings access for the provided field.
*/
protected ScriptDocValues.Strings docFieldStrings(String field) {
return (ScriptDocValues.Strings) doc().get(field);
}
/**
* Returns field data double (floating point) access for the provided field.
*/
protected ScriptDocValues.Doubles docFieldDoubles(String field) {
return (ScriptDocValues.Doubles) doc().get(field);
}
/**
* Returns field data long (integers) access for the provided field.
*/
protected ScriptDocValues.Longs docFieldLongs(String field) {
return (ScriptDocValues.Longs) doc().get(field);
}
/**
* Allows to access the actual source (loaded and parsed).
*/
protected final SourceLookup source() {
return lookup.source();
}
/**
* Allows to access the *stored* fields.
*/
protected final LeafFieldsLookup fields() {
return lookup.fields();
}
void setLookup(LeafSearchLookup lookup) {
this.lookup = lookup;
}
@Override
public void setScorer(Scorer scorer) {
this.scorer = scorer;
}
@Override
public void setDocument(int doc) {
lookup.setDocument(doc);
}
@Override
public void setSource(Map<String, Object> source) {
lookup.source().setSource(source);
}
@Override
public long runAsLong() {
return ((Number) run()).longValue();
}
@Override
public double runAsDouble() {
return ((Number) run()).doubleValue();
}
}

View File

@ -1,100 +0,0 @@
/*
* 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.apache.logging.log4j.Logger;
import org.apache.lucene.index.LeafReaderContext;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.component.AbstractComponent;
import org.elasticsearch.common.logging.DeprecationLogger;
import org.elasticsearch.common.logging.Loggers;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.search.lookup.SearchLookup;
import java.io.IOException;
import java.util.Map;
import static java.util.Collections.unmodifiableMap;
/**
* A native script engine service.
*/
public class NativeScriptEngine extends AbstractComponent implements ScriptEngine {
public static final String NAME = "native";
private final Map<String, NativeScriptFactory> scripts;
public NativeScriptEngine(Settings settings, Map<String, NativeScriptFactory> scripts) {
super(settings);
if (scripts.isEmpty() == false) {
Logger logger = Loggers.getLogger(ScriptModule.class);
DeprecationLogger deprecationLogger = new DeprecationLogger(logger);
deprecationLogger.deprecated("Native scripts are deprecated. Use a custom ScriptEngine to write scripts in java.");
}
this.scripts = unmodifiableMap(scripts);
}
@Override
public String getType() {
return NAME;
}
@Override
public Object compile(String scriptName, String scriptSource, Map<String, String> params) {
NativeScriptFactory scriptFactory = scripts.get(scriptSource);
if (scriptFactory != null) {
return scriptFactory;
}
throw new IllegalArgumentException("Native script [" + scriptSource + "] not found");
}
@Override
public ExecutableScript executable(CompiledScript compiledScript, @Nullable Map<String, Object> vars) {
NativeScriptFactory scriptFactory = (NativeScriptFactory) compiledScript.compiled();
return scriptFactory.newScript(vars);
}
@Override
public SearchScript search(CompiledScript compiledScript, final SearchLookup lookup, @Nullable final Map<String, Object> vars) {
final NativeScriptFactory scriptFactory = (NativeScriptFactory) compiledScript.compiled();
final AbstractSearchScript script = (AbstractSearchScript) scriptFactory.newScript(vars);
return new SearchScript() {
@Override
public LeafSearchScript getLeafSearchScript(LeafReaderContext context) throws IOException {
script.setLookup(lookup.getLeafSearchLookup(context));
return script;
}
@Override
public boolean needsScores() {
return scriptFactory.needsScores();
}
};
}
@Override
public void close() {
}
@Override
public boolean isInlineScriptEnabled() {
return true;
}
}

View File

@ -1,57 +0,0 @@
/*
* 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.Nullable;
import java.util.Map;
/**
* A factory to create instances of either {@link ExecutableScript} or {@link SearchScript}. Note,
* if this factory creates {@link SearchScript}, it must extend {@link AbstractSearchScript}.
*
* @see AbstractExecutableScript
* @see AbstractSearchScript
* @see AbstractLongSearchScript
* @see AbstractDoubleSearchScript
* @deprecated Create a {@link ScriptEngine} instead of using native scripts
*/
@Deprecated
public interface NativeScriptFactory {
/**
* Creates a new instance of either a {@link ExecutableScript} or a {@link SearchScript}.
*
* @param params The parameters passed to the script. Can be <tt>null</tt>.
*/
ExecutableScript newScript(@Nullable Map<String, Object> params);
/**
* Indicates if document scores may be needed by the produced scripts.
*
* @return {@code true} if scores are needed.
*/
boolean needsScores();
/**
* Returns the name of the script factory
*/
String getName();
}

View File

@ -105,11 +105,6 @@ public class ScriptModes {
* @return whether scripts are enabled (true) or disabled (false)
*/
public boolean getScriptEnabled(String lang, ScriptType scriptType, ScriptContext scriptContext) {
//native scripts are always enabled as they are static by definition
if (NativeScriptEngine.NAME.equals(lang)) {
return true;
}
if (typesAllowed != null && typesAllowed.contains(scriptType.getName()) == false) {
throw new IllegalArgumentException("[" + scriptType.getName() + "] scripts cannot be executed");
}

View File

@ -45,12 +45,8 @@ public class ScriptModule {
* {@link ScriptModule#ScriptModule(Settings, List, List)} for easier use in tests.
*/
public static ScriptModule create(Settings settings, List<ScriptPlugin> scriptPlugins) {
Map<String, NativeScriptFactory> factoryMap = scriptPlugins.stream().flatMap(x -> x.getNativeScripts().stream())
.collect(Collectors.toMap(NativeScriptFactory::getName, Function.identity()));
NativeScriptEngine nativeScriptEngineService = new NativeScriptEngine(settings, factoryMap);
List<ScriptEngine> scriptEngines = scriptPlugins.stream().map(x -> x.getScriptEngine(settings))
.filter(Objects::nonNull).collect(Collectors.toList());
scriptEngines.add(nativeScriptEngineService);
List<ScriptContext.Plugin> plugins = scriptPlugins.stream().map(x -> x.getCustomScriptContexts()).filter(Objects::nonNull)
.collect(Collectors.toList());
return new ScriptModule(settings, scriptEngines, plugins);

View File

@ -74,10 +74,6 @@ public class ScriptSettings {
final List<Setting<Boolean>> scriptModeSettings = new ArrayList<>();
for (final Class<? extends ScriptEngine> scriptEngineService : scriptEngineRegistry.getRegisteredScriptEngineServices()) {
if (scriptEngineService == NativeScriptEngine.class) {
// native scripts are always enabled, and their settings can not be changed
continue;
}
final String language = scriptEngineRegistry.getLanguage(scriptEngineService);
for (final ScriptType scriptType : ScriptType.values()) {
// Top level, like "script.engine.groovy.inline"

View File

@ -20,7 +20,6 @@
package org.elasticsearch.common.lucene.search.function;
import org.apache.lucene.index.LeafReaderContext;
import org.elasticsearch.script.AbstractDoubleSearchScript;
import org.elasticsearch.script.GeneralScriptException;
import org.elasticsearch.script.LeafSearchScript;
import org.elasticsearch.script.SearchScript;
@ -37,17 +36,7 @@ public class ScriptScoreFunctionTests extends ESTestCase {
ScoreFunction scoreFunction = new ScriptScoreFunction(mockScript("Double.NaN"), new SearchScript() {
@Override
public LeafSearchScript getLeafSearchScript(LeafReaderContext context) throws IOException {
return new AbstractDoubleSearchScript() {
@Override
public double runAsDouble() {
return Double.NaN;
}
@Override
public void setDocument(int doc) {
// do nothing: we are a fake with no lookup
}
};
return () -> Double.NaN;
}
@Override

View File

@ -31,10 +31,8 @@ import org.elasticsearch.action.update.UpdateResponse;
import org.elasticsearch.client.Requests;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.rest.RestStatus;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.MockScriptPlugin;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.test.ESIntegTestCase;
@ -42,9 +40,9 @@ import org.junit.Before;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ExecutionException;
import java.util.function.Function;
import static java.util.Collections.emptyMap;
import static java.util.Collections.singleton;
@ -111,7 +109,8 @@ public class WaitUntilRefreshIT extends ESIntegTestCase {
assertSearchHits(client().prepareSearch("test").setQuery(matchQuery("foo", "cat")).get(), "2");
// Update-becomes-delete with RefreshPolicy.WAIT_UNTIL
update = client().prepareUpdate("test", "test", "2").setScript(new Script(ScriptType.INLINE, "native", "delete_plz", emptyMap()))
update = client().prepareUpdate("test", "test", "2").setScript(
new Script(ScriptType.INLINE, "mockscript", "delete_plz", emptyMap()))
.setRefreshPolicy(RefreshPolicy.WAIT_UNTIL).get();
assertEquals(2, update.getVersion());
assertFalse("request shouldn't have forced a refresh", update.forcedRefresh());
@ -171,43 +170,15 @@ public class WaitUntilRefreshIT extends ESIntegTestCase {
return singleton(DeletePlzPlugin.class);
}
public static class DeletePlzPlugin extends Plugin implements ScriptPlugin {
public static class DeletePlzPlugin extends MockScriptPlugin {
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Collections.singletonList(new DeletePlzFactory());
}
}
public static class DeletePlzFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(Map<String, Object> params) {
return new ExecutableScript() {
private Map<String, Object> ctx;
@Override
@SuppressWarnings("unchecked") // Elasicsearch convention
public void setNextVar(String name, Object value) {
if (name.equals("ctx")) {
ctx = (Map<String, Object>) value;
}
}
@Override
public Object run() {
ctx.put("op", "delete");
return null;
}
};
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return "delete_plz";
public Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
return Collections.singletonMap("delete_plz", params -> {
@SuppressWarnings("unchecked")
Map<String, Object> ctx = (Map<String, Object>) params.get("ctx");
ctx.put("op", "delete");
return null;
});
}
}
}

View File

@ -1,111 +0,0 @@
/*
* 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 java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.settings.Setting;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.env.Environment;
import org.elasticsearch.test.ESTestCase;
import org.elasticsearch.test.InternalSettingsPlugin;
import org.elasticsearch.watcher.ResourceWatcherService;
import static java.util.Collections.emptyList;
import static java.util.Collections.singletonList;
import static java.util.Collections.singletonMap;
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.notNullValue;
public class NativeScriptTests extends ESTestCase {
public void testNativeScript() throws InterruptedException {
Settings settings = Settings.builder()
.put("node.name", "testNativeScript")
.put(Environment.PATH_HOME_SETTING.getKey(), createTempDir())
.build();
ScriptModule scriptModule = new ScriptModule(settings,
singletonList(new NativeScriptEngine(settings, singletonMap("my", new MyNativeScriptFactory()))), emptyList());
List<Setting<?>> scriptSettings = scriptModule.getSettings();
scriptSettings.add(InternalSettingsPlugin.VERSION_CREATED);
Script script = new Script(ScriptType.INLINE, NativeScriptEngine.NAME, "my", Collections.emptyMap());
CompiledScript compiledScript = scriptModule.getScriptService().compile(script, ScriptContext.Standard.SEARCH);
ExecutableScript executable = scriptModule.getScriptService().executable(compiledScript, script.getParams());
assertThat(executable.run().toString(), equalTo("test"));
assertWarnings("Native scripts are deprecated. Use a custom ScriptEngine to write scripts in java.");
}
public void testFineGrainedSettingsDontAffectNativeScripts() throws IOException {
Settings.Builder builder = Settings.builder();
if (randomBoolean()) {
ScriptType scriptType = randomFrom(ScriptType.values());
builder.put("script" + "." + scriptType.getName(), randomBoolean());
} else {
ScriptContext scriptContext = randomFrom(ScriptContext.Standard.values());
builder.put("script" + "." + scriptContext.getKey(), randomBoolean());
}
Settings settings = builder.put(Environment.PATH_HOME_SETTING.getKey(), createTempDir()).build();
Map<String, NativeScriptFactory> nativeScriptFactoryMap = new HashMap<>();
nativeScriptFactoryMap.put("my", new MyNativeScriptFactory());
ScriptEngineRegistry scriptEngineRegistry = new ScriptEngineRegistry(Collections.singleton(new NativeScriptEngine(settings,
nativeScriptFactoryMap)));
ScriptContextRegistry scriptContextRegistry = new ScriptContextRegistry(new ArrayList<>());
ScriptSettings scriptSettings = new ScriptSettings(scriptEngineRegistry, scriptContextRegistry);
ScriptService scriptService = new ScriptService(settings, scriptEngineRegistry,
scriptContextRegistry, scriptSettings);
for (ScriptContext scriptContext : scriptContextRegistry.scriptContexts()) {
assertThat(scriptService.compile(new Script(ScriptType.INLINE, NativeScriptEngine.NAME, "my", Collections.emptyMap()),
scriptContext), notNullValue());
}
assertWarnings("Native scripts are deprecated. Use a custom ScriptEngine to write scripts in java.");
}
public static class MyNativeScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new MyScript();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return "my";
}
}
static class MyScript extends AbstractExecutableScript {
@Override
public Object run() {
return "test";
}
}
}

View File

@ -1,184 +0,0 @@
/*
* 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.action.search.SearchResponse;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.search.SearchHit;
import org.elasticsearch.test.ESIntegTestCase;
import org.elasticsearch.test.ESIntegTestCase.ClusterScope;
import org.elasticsearch.test.ESIntegTestCase.Scope;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ExecutionException;
import static org.hamcrest.Matchers.equalTo;
@ClusterScope(scope = Scope.SUITE, numDataNodes = 3)
public class ScriptFieldIT extends ESIntegTestCase {
@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Arrays.asList(CustomScriptPlugin.class);
}
static int[] intArray = { Integer.MAX_VALUE, Integer.MIN_VALUE, 3 };
static long[] longArray = { Long.MAX_VALUE, Long.MIN_VALUE, 9223372036854775807L };
static float[] floatArray = { Float.MAX_VALUE, Float.MIN_VALUE, 3.3f };
static double[] doubleArray = { Double.MAX_VALUE, Double.MIN_VALUE, 3.3d };
public void testNativeScript() throws InterruptedException, ExecutionException {
indexRandom(true, client().prepareIndex("test", "type1", "1").setSource("text", "doc1"), client()
.prepareIndex("test", "type1", "2").setSource("text", "doc2"),
client().prepareIndex("test", "type1", "3").setSource("text", "doc3"), client().prepareIndex("test", "type1", "4")
.setSource("text", "doc4"), client().prepareIndex("test", "type1", "5").setSource("text", "doc5"), client()
.prepareIndex("test", "type1", "6").setSource("text", "doc6"));
client().admin().indices().prepareFlush("test").execute().actionGet();
SearchResponse sr = client().prepareSearch("test").setQuery(QueryBuilders.matchAllQuery())
.addScriptField("int", new Script(ScriptType.INLINE, "native", "int", Collections.emptyMap()))
.addScriptField("float", new Script(ScriptType.INLINE, "native", "float", Collections.emptyMap()))
.addScriptField("double", new Script(ScriptType.INLINE, "native", "double", Collections.emptyMap()))
.addScriptField("long", new Script(ScriptType.INLINE, "native", "long", Collections.emptyMap())).execute().actionGet();
assertThat(sr.getHits().getHits().length, equalTo(6));
for (SearchHit hit : sr.getHits().getHits()) {
Object result = hit.getFields().get("int").getValues().get(0);
assertThat(result, equalTo((Object) intArray));
result = hit.getFields().get("long").getValues().get(0);
assertThat(result, equalTo((Object) longArray));
result = hit.getFields().get("float").getValues().get(0);
assertThat(result, equalTo((Object) floatArray));
result = hit.getFields().get("double").getValues().get(0);
assertThat(result, equalTo((Object) doubleArray));
}
}
public static class IntArrayScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new IntScript();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return "int";
}
}
static class IntScript extends AbstractSearchScript {
@Override
public Object run() {
return intArray;
}
}
public static class LongArrayScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new LongScript();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return "long";
}
}
static class LongScript extends AbstractSearchScript {
@Override
public Object run() {
return longArray;
}
}
public static class FloatArrayScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new FloatScript();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return "float";
}
}
static class FloatScript extends AbstractSearchScript {
@Override
public Object run() {
return floatArray;
}
}
public static class DoubleArrayScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new DoubleScript();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return "double";
}
}
static class DoubleScript extends AbstractSearchScript {
@Override
public Object run() {
return doubleArray;
}
}
public static class CustomScriptPlugin extends Plugin implements ScriptPlugin {
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Arrays.asList(new IntArrayScriptFactory(), new LongArrayScriptFactory(), new FloatArrayScriptFactory(),
new DoubleArrayScriptFactory());
}
}
}

View File

@ -65,10 +65,7 @@ public class ScriptModesTests extends ESTestCase {
}
scriptContextRegistry = new ScriptContextRegistry(contexts.values());
scriptContexts = scriptContextRegistry.scriptContexts().toArray(new ScriptContext[scriptContextRegistry.scriptContexts().size()]);
scriptEngines = buildScriptEnginesByLangMap(newHashSet(
//add the native engine just to make sure it gets filtered out
new NativeScriptEngine(Settings.EMPTY, Collections.<String, NativeScriptFactory>emptyMap()),
new CustomScriptEngine()));
scriptEngines = buildScriptEnginesByLangMap(newHashSet(new CustomScriptEngine()));
ScriptEngineRegistry scriptEngineRegistry = new ScriptEngineRegistry(scriptEngines.values());
scriptSettings = new ScriptSettings(scriptEngineRegistry, scriptContextRegistry);
checkedSettings = new HashSet<>();
@ -76,13 +73,6 @@ public class ScriptModesTests extends ESTestCase {
assertScriptModesNonNull = true;
}
@After
public void assertNativeScriptsAreAlwaysAllowed() {
if (assertScriptModesNonNull) {
assertThat(scriptModes.getScriptEnabled(NativeScriptEngine.NAME, randomFrom(ScriptType.values()), randomFrom(scriptContexts)), equalTo(true));
}
}
@After
public void assertAllSettingsWereChecked() {
if (assertScriptModesNonNull) {

View File

@ -35,12 +35,10 @@ import org.elasticsearch.common.xcontent.ToXContent;
import org.elasticsearch.common.xcontent.XContentHelper;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.PluginsService;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.script.AbstractSearchScript;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.MockScriptPlugin;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.search.lookup.LeafFieldsLookup;
import org.elasticsearch.tasks.TaskInfo;
import org.elasticsearch.test.ESIntegTestCase;
@ -51,8 +49,10 @@ import java.util.List;
import java.util.Map;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.function.Function;
import static org.elasticsearch.index.query.QueryBuilders.scriptQuery;
import static org.elasticsearch.search.SearchCancellationIT.ScriptedBlockPlugin.SCRIPT_NAME;
import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertNoFailures;
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.greaterThan;
@ -93,8 +93,8 @@ public class SearchCancellationIT extends ESIntegTestCase {
plugins.addAll(pluginsService.filterPlugins(ScriptedBlockPlugin.class));
}
for (ScriptedBlockPlugin plugin : plugins) {
plugin.scriptedBlockFactory.reset();
plugin.scriptedBlockFactory.enableBlock();
plugin.reset();
plugin.enableBlock();
}
return plugins;
}
@ -104,7 +104,7 @@ public class SearchCancellationIT extends ESIntegTestCase {
assertBusy(() -> {
int numberOfBlockedPlugins = 0;
for (ScriptedBlockPlugin plugin : plugins) {
numberOfBlockedPlugins += plugin.scriptedBlockFactory.hits.get();
numberOfBlockedPlugins += plugin.hits.get();
}
logger.info("The plugin blocked on {} out of {} shards", numberOfBlockedPlugins, numberOfShards);
assertThat(numberOfBlockedPlugins, greaterThan(0));
@ -113,7 +113,7 @@ public class SearchCancellationIT extends ESIntegTestCase {
private void disableBlocks(List<ScriptedBlockPlugin> plugins) throws Exception {
for (ScriptedBlockPlugin plugin : plugins) {
plugin.scriptedBlockFactory.disableBlock();
plugin.disableBlock();
}
}
@ -148,7 +148,7 @@ public class SearchCancellationIT extends ESIntegTestCase {
logger.info("Executing search");
ActionFuture<SearchResponse> searchResponse = client().prepareSearch("test").setQuery(
scriptQuery(new Script(
ScriptType.INLINE, "native", NativeTestScriptedBlockFactory.TEST_NATIVE_BLOCK_SCRIPT, Collections.emptyMap())))
ScriptType.INLINE, "mockscript", SCRIPT_NAME, Collections.emptyMap())))
.execute();
awaitForBlock(plugins);
@ -166,7 +166,7 @@ public class SearchCancellationIT extends ESIntegTestCase {
logger.info("Executing search");
ActionFuture<SearchResponse> searchResponse = client().prepareSearch("test")
.addScriptField("test_field",
new Script(ScriptType.INLINE, "native", NativeTestScriptedBlockFactory.TEST_NATIVE_BLOCK_SCRIPT, Collections.emptyMap())
new Script(ScriptType.INLINE, "mockscript", SCRIPT_NAME, Collections.emptyMap())
).execute();
awaitForBlock(plugins);
@ -187,7 +187,7 @@ public class SearchCancellationIT extends ESIntegTestCase {
.setSize(5)
.setQuery(
scriptQuery(new Script(
ScriptType.INLINE, "native", NativeTestScriptedBlockFactory.TEST_NATIVE_BLOCK_SCRIPT, Collections.emptyMap())))
ScriptType.INLINE, "mockscript", SCRIPT_NAME, Collections.emptyMap())))
.execute();
awaitForBlock(plugins);
@ -217,15 +217,15 @@ public class SearchCancellationIT extends ESIntegTestCase {
.setSize(2)
.setQuery(
scriptQuery(new Script(
ScriptType.INLINE, "native", NativeTestScriptedBlockFactory.TEST_NATIVE_BLOCK_SCRIPT, Collections.emptyMap())))
ScriptType.INLINE, "mockscript", SCRIPT_NAME, Collections.emptyMap())))
.get();
assertNotNull(searchResponse.getScrollId());
// Enable block so the second request would block
for (ScriptedBlockPlugin plugin : plugins) {
plugin.scriptedBlockFactory.reset();
plugin.scriptedBlockFactory.enableBlock();
plugin.reset();
plugin.enableBlock();
}
String scrollId = searchResponse.getScrollId();
@ -247,30 +247,13 @@ public class SearchCancellationIT extends ESIntegTestCase {
}
public static class ScriptedBlockPlugin extends Plugin implements ScriptPlugin {
private NativeTestScriptedBlockFactory scriptedBlockFactory;
public ScriptedBlockPlugin() {
scriptedBlockFactory = new NativeTestScriptedBlockFactory();
}
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Collections.singletonList(scriptedBlockFactory);
}
}
private static class NativeTestScriptedBlockFactory implements NativeScriptFactory {
public static final String TEST_NATIVE_BLOCK_SCRIPT = "native_test_search_block_script";
public static class ScriptedBlockPlugin extends MockScriptPlugin {
static final String SCRIPT_NAME = "search_block";
private final AtomicInteger hits = new AtomicInteger();
private final AtomicBoolean shouldBlock = new AtomicBoolean(true);
NativeTestScriptedBlockFactory() {
}
public void reset() {
hits.set(0);
}
@ -284,24 +267,10 @@ public class SearchCancellationIT extends ESIntegTestCase {
}
@Override
public ExecutableScript newScript(Map<String, Object> params) {
return new NativeTestScriptedBlock();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return TEST_NATIVE_BLOCK_SCRIPT;
}
public class NativeTestScriptedBlock extends AbstractSearchScript {
@Override
public Object run() {
Loggers.getLogger(SearchCancellationIT.class).info("Blocking on the document {}", fields().get("_uid"));
public Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
return Collections.singletonMap(SCRIPT_NAME, params -> {
LeafFieldsLookup fieldsLookup = (LeafFieldsLookup) params.get("_fields");
Loggers.getLogger(SearchCancellationIT.class).info("Blocking on the document {}", fieldsLookup.get("_uid"));
hits.incrementAndGet();
try {
awaitBusy(() -> shouldBlock.get() == false);
@ -309,8 +278,7 @@ public class SearchCancellationIT extends ESIntegTestCase {
throw new RuntimeException(e);
}
return true;
}
});
}
}
}

View File

@ -23,22 +23,20 @@ import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.unit.TimeValue;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.script.AbstractSearchScript;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.MockScriptPlugin;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.test.ESIntegTestCase;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;
import java.util.function.Function;
import static org.elasticsearch.action.support.WriteRequest.RefreshPolicy.IMMEDIATE;
import static org.elasticsearch.index.query.QueryBuilders.scriptQuery;
import static org.elasticsearch.search.SearchTimeoutIT.ScriptedTimeoutPlugin.SCRIPT_NAME;
import static org.hamcrest.Matchers.equalTo;
@ESIntegTestCase.ClusterScope(scope = ESIntegTestCase.Scope.SUITE)
@ -59,49 +57,23 @@ public class SearchTimeoutIT extends ESIntegTestCase {
SearchResponse searchResponse = client().prepareSearch("test").setTimeout(new TimeValue(10, TimeUnit.MILLISECONDS))
.setQuery(scriptQuery(
new Script(ScriptType.INLINE, "native", NativeTestScriptedTimeout.TEST_NATIVE_SCRIPT_TIMEOUT, Collections.emptyMap())))
new Script(ScriptType.INLINE, "mockscript", SCRIPT_NAME, Collections.emptyMap())))
.execute().actionGet();
assertThat(searchResponse.isTimedOut(), equalTo(true));
}
public static class ScriptedTimeoutPlugin extends Plugin implements ScriptPlugin {
public static class ScriptedTimeoutPlugin extends MockScriptPlugin {
static final String SCRIPT_NAME = "search_timeout";
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Collections.singletonList(new NativeTestScriptedTimeout.Factory());
public Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
return Collections.singletonMap(SCRIPT_NAME, params -> {
try {
Thread.sleep(500);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
return true;
});
}
}
public static class NativeTestScriptedTimeout extends AbstractSearchScript {
public static final String TEST_NATIVE_SCRIPT_TIMEOUT = "native_test_search_timeout_script";
public static class Factory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(Map<String, Object> params) {
return new NativeTestScriptedTimeout();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return TEST_NATIVE_SCRIPT_TIMEOUT;
}
}
@Override
public Object run() {
try {
Thread.sleep(500);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
return true;
}
}
}

View File

@ -34,7 +34,6 @@ import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.search.aggregations.AggregationExecutionException;
import org.elasticsearch.search.aggregations.InternalAggregation;
import org.elasticsearch.search.aggregations.bucket.DateScriptMocks.DateScriptsMockPlugin;
import org.elasticsearch.search.aggregations.bucket.histogram.DateHistogramInterval;
import org.elasticsearch.search.aggregations.bucket.histogram.ExtendedBounds;
import org.elasticsearch.search.aggregations.bucket.histogram.Histogram;
@ -53,6 +52,7 @@ import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
@ -184,8 +184,7 @@ public class DateHistogramIT extends ESIntegTestCase {
@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Arrays.asList(
DateScriptsMockPlugin.class);
return Collections.singleton(DateScriptMocksPlugin.class);
}
@After
@ -608,7 +607,7 @@ public class DateHistogramIT extends ESIntegTestCase {
SearchResponse response = client().prepareSearch("idx")
.addAggregation(dateHistogram("histo")
.field("date")
.script(new Script(ScriptType.INLINE, "native", DateScriptMocks.PlusOneMonthScript.NAME, params))
.script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.LONG_PLUS_ONE_MONTH, params))
.dateHistogramInterval(DateHistogramInterval.MONTH)).execute().actionGet();
assertSearchResponse(response);
@ -747,7 +746,7 @@ public class DateHistogramIT extends ESIntegTestCase {
SearchResponse response = client().prepareSearch("idx")
.addAggregation(dateHistogram("histo")
.field("dates")
.script(new Script(ScriptType.INLINE, "native", DateScriptMocks.PlusOneMonthScript.NAME, params))
.script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.LONG_PLUS_ONE_MONTH, params))
.dateHistogramInterval(DateHistogramInterval.MONTH)).execute().actionGet();
assertSearchResponse(response);
@ -799,8 +798,9 @@ public class DateHistogramIT extends ESIntegTestCase {
Map<String, Object> params = new HashMap<>();
params.put("fieldname", "date");
SearchResponse response = client().prepareSearch("idx")
.addAggregation(dateHistogram("histo").script(new Script(ScriptType.INLINE, "native", DateScriptMocks.ExtractFieldScript.NAME,
params)).dateHistogramInterval(DateHistogramInterval.MONTH))
.addAggregation(dateHistogram("histo").script(
new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.EXTRACT_FIELD, params))
.dateHistogramInterval(DateHistogramInterval.MONTH))
.execute().actionGet();
assertSearchResponse(response);
@ -837,8 +837,9 @@ public class DateHistogramIT extends ESIntegTestCase {
Map<String, Object> params = new HashMap<>();
params.put("fieldname", "dates");
SearchResponse response = client().prepareSearch("idx")
.addAggregation(dateHistogram("histo").script(new Script(ScriptType.INLINE, "native", DateScriptMocks.ExtractFieldScript.NAME,
params)).dateHistogramInterval(DateHistogramInterval.MONTH))
.addAggregation(dateHistogram("histo").script(
new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.EXTRACT_FIELD, params))
.dateHistogramInterval(DateHistogramInterval.MONTH))
.execute().actionGet();
assertSearchResponse(response);
@ -1329,7 +1330,7 @@ public class DateHistogramIT extends ESIntegTestCase {
Map<String, Object> params = new HashMap<>();
params.put("fieldname", "d");
SearchResponse r = client().prepareSearch("cache_test_idx").setSize(0).addAggregation(dateHistogram("histo").field("d")
.script(new Script(ScriptType.INLINE, "native", DateScriptMocks.PlusOneMonthScript.NAME, params))
.script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.LONG_PLUS_ONE_MONTH, params))
.dateHistogramInterval(DateHistogramInterval.MONTH)).get();
assertSearchResponse(r);

View File

@ -26,7 +26,6 @@ import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.search.aggregations.InternalAggregation;
import org.elasticsearch.search.aggregations.bucket.DateScriptMocks.DateScriptsMockPlugin;
import org.elasticsearch.search.aggregations.bucket.histogram.Histogram;
import org.elasticsearch.search.aggregations.bucket.range.Range;
import org.elasticsearch.search.aggregations.bucket.range.Range.Bucket;
@ -40,6 +39,7 @@ import org.joda.time.DateTimeZone;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@ -111,8 +111,7 @@ public class DateRangeIT extends ESIntegTestCase {
@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Arrays.asList(
DateScriptsMockPlugin.class);
return Collections.singleton(DateScriptMocksPlugin.class);
}
public void testDateMath() throws Exception {
@ -122,7 +121,7 @@ public class DateRangeIT extends ESIntegTestCase {
if (randomBoolean()) {
rangeBuilder.field("date");
} else {
rangeBuilder.script(new Script(ScriptType.INLINE, "native", DateScriptMocks.ExtractFieldScript.NAME, params));
rangeBuilder.script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.EXTRACT_FIELD, params));
}
SearchResponse response = client()
.prepareSearch("idx")
@ -544,7 +543,7 @@ public class DateRangeIT extends ESIntegTestCase {
SearchResponse response = client().prepareSearch("idx")
.addAggregation(dateRange("range")
.field("dates")
.script(new Script(ScriptType.INLINE, "native", DateScriptMocks.PlusOneMonthScript.NAME, params))
.script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.DOUBLE_PLUS_ONE_MONTH, params))
.addUnboundedTo(date(2, 15)).addRange(date(2, 15), date(3, 15)).addUnboundedFrom(date(3, 15))).execute()
.actionGet();
@ -600,7 +599,7 @@ public class DateRangeIT extends ESIntegTestCase {
params.put("fieldname", "date");
SearchResponse response = client().prepareSearch("idx")
.addAggregation(dateRange("range")
.script(new Script(ScriptType.INLINE, "native", DateScriptMocks.ExtractFieldScript.NAME, params))
.script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.EXTRACT_FIELD, params))
.addUnboundedTo(date(2, 15))
.addRange(date(2, 15), date(3, 15))
.addUnboundedFrom(date(3, 15)))
@ -662,7 +661,7 @@ public class DateRangeIT extends ESIntegTestCase {
SearchResponse response = client()
.prepareSearch("idx")
.addAggregation(
dateRange("range").script(new Script(ScriptType.INLINE, "native", DateScriptMocks.ExtractFieldScript.NAME, params))
dateRange("range").script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.EXTRACT_FIELD, params))
.addUnboundedTo(date(2, 15)).addRange(date(2, 15), date(3, 15))
.addUnboundedFrom(date(3, 15))).execute().actionGet();
@ -905,7 +904,7 @@ public class DateRangeIT extends ESIntegTestCase {
Map<String, Object> params = new HashMap<>();
params.put("fieldname", "date");
SearchResponse r = client().prepareSearch("cache_test_idx").setSize(0).addAggregation(dateRange("foo").field("date")
.script(new Script(ScriptType.INLINE, "native", DateScriptMocks.PlusOneMonthScript.NAME, params))
.script(new Script(ScriptType.INLINE, "mockscript", DateScriptMocksPlugin.DOUBLE_PLUS_ONE_MONTH, params))
.addRange(new DateTime(2012, 1, 1, 0, 0, 0, 0, DateTimeZone.UTC), new DateTime(2013, 1, 1, 0, 0, 0, 0, DateTimeZone.UTC)))
.get();
assertSearchResponse(r);

View File

@ -1,130 +0,0 @@
/*
* 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.bucket;
import org.elasticsearch.common.inject.internal.Nullable;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.script.AbstractSearchScript;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.ScriptModule;
import org.joda.time.DateTime;
import org.joda.time.DateTimeZone;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* Mock scripts shared by DateRangeIT and DateHistogramIT
*/
public class DateScriptMocks {
/**
* Mock plugin for the {@link DateScriptMocks.ExtractFieldScript} and {@link DateScriptMocks.PlusOneMonthScript}
*/
public static class DateScriptsMockPlugin extends Plugin implements ScriptPlugin {
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Arrays.asList(new ExtractFieldScriptFactory(), new PlusOneMonthScriptFactory());
}
}
public static class ExtractFieldScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new ExtractFieldScript((String) params.get("fieldname"));
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return ExtractFieldScript.NAME;
}
}
public static class ExtractFieldScript extends AbstractSearchScript {
public static final String NAME = "extract_field";
private String fieldname;
public ExtractFieldScript(String fieldname) {
this.fieldname = fieldname;
}
@Override
public Object run() {
return doc().get(fieldname);
}
}
public static class PlusOneMonthScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(Map<String, Object> params) {
return new PlusOneMonthScript();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return PlusOneMonthScript.NAME;
}
}
/**
* This mock script takes date field value and adds one month to the returned date
*/
public static class PlusOneMonthScript extends AbstractSearchScript {
public static final String NAME = "date_plus_1_month";
private Map<String, Object> vars = new HashMap<>();
@Override
public void setNextVar(String name, Object value) {
vars.put(name, value);
}
@Override
public long runAsLong() {
return new DateTime((long) vars.get("_value"), DateTimeZone.UTC).plusMonths(1).getMillis();
}
@Override
public double runAsDouble() {
return new DateTime(Double.valueOf((double) vars.get("_value")).longValue(), DateTimeZone.UTC).plusMonths(1).getMillis();
}
@Override
public Object run() {
return new UnsupportedOperationException();
}
}
}

View File

@ -0,0 +1,56 @@
/*
* 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.bucket;
import org.elasticsearch.script.MockScriptPlugin;
import org.elasticsearch.search.lookup.LeafDocLookup;
import org.joda.time.DateTime;
import org.joda.time.DateTimeZone;
import java.util.HashMap;
import java.util.Map;
import java.util.function.Function;
/**
* Mock scripts shared by DateRangeIT and DateHistogramIT.
*
* Provides {@link DateScriptMocksPlugin#EXTRACT_FIELD}, {@link DateScriptMocksPlugin#DOUBLE_PLUS_ONE_MONTH},
* and {@link DateScriptMocksPlugin#LONG_PLUS_ONE_MONTH} scripts.
*/
public class DateScriptMocksPlugin extends MockScriptPlugin {
static final String EXTRACT_FIELD = "extract_field";
static final String DOUBLE_PLUS_ONE_MONTH = "double_date_plus_1_month";
static final String LONG_PLUS_ONE_MONTH = "long_date_plus_1_month";
@Override
public Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
Map<String, Function<Map<String, Object>, Object>> scripts = new HashMap<>();
scripts.put(EXTRACT_FIELD, params -> {
LeafDocLookup docLookup = (LeafDocLookup) params.get("doc");
String fieldname = (String) params.get("fieldname");
return docLookup.get(fieldname);
});
scripts.put(DOUBLE_PLUS_ONE_MONTH, params ->
new DateTime(Double.valueOf((double) params.get("_value")).longValue(), DateTimeZone.UTC).plusMonths(1).getMillis());
scripts.put(LONG_PLUS_ONE_MONTH, params ->
new DateTime((long) params.get("_value"), DateTimeZone.UTC).plusMonths(1).getMillis());
return scripts;
}
}

View File

@ -18,27 +18,23 @@
*/
package org.elasticsearch.search.aggregations.bucket;
import org.elasticsearch.action.search.SearchPhaseExecutionException;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.Map;
import java.util.function.Function;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.action.search.SearchPhaseExecutionException;
import org.elasticsearch.cluster.health.ClusterHealthStatus;
import org.elasticsearch.common.inject.internal.Nullable;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.script.AbstractSearchScript;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.MockScriptPlugin;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.search.aggregations.AggregationBuilders;
import org.elasticsearch.search.aggregations.bucket.range.Range;
import org.elasticsearch.test.ESIntegTestCase;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertAcked;
import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertSearchResponse;
import static org.hamcrest.Matchers.containsString;
@ -47,6 +43,13 @@ import static org.hamcrest.Matchers.instanceOf;
@ESIntegTestCase.SuiteScopeTestCase
public class IpRangeIT extends ESIntegTestCase {
public static class DummyScriptPlugin extends MockScriptPlugin {
@Override
public Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
return Collections.singletonMap("dummy", params -> null);
}
}
@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Arrays.asList(DummyScriptPlugin.class);
@ -210,7 +213,7 @@ public class IpRangeIT extends ESIntegTestCase {
IllegalArgumentException e = expectThrows(IllegalArgumentException.class,
() -> client().prepareSearch("idx").addAggregation(
AggregationBuilders.ipRange("my_range")
.script(new Script(ScriptType.INLINE, "native", DummyScript.NAME, Collections.emptyMap())) ).get());
.script(new Script(ScriptType.INLINE, "mockscript", "dummy", Collections.emptyMap())) ).get());
assertThat(e.getMessage(), containsString("[ip_range] does not support scripts"));
}
@ -219,7 +222,7 @@ public class IpRangeIT extends ESIntegTestCase {
() -> client().prepareSearch("idx").addAggregation(
AggregationBuilders.ipRange("my_range")
.field("ip")
.script(new Script(ScriptType.INLINE, "native", DummyScript.NAME, Collections.emptyMap())) ).get());
.script(new Script(ScriptType.INLINE, "mockscript", "dummy", Collections.emptyMap())) ).get());
assertThat(e.getMessage(), containsString("[ip_range] does not support scripts"));
}
@ -236,39 +239,4 @@ public class IpRangeIT extends ESIntegTestCase {
assertEquals(rootCause.getMessage(), "No [ranges] specified for the [my_range] aggregation");
}
}
public static class DummyScriptPlugin extends Plugin implements ScriptPlugin {
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Collections.singletonList(new DummyScriptFactory());
}
}
public static class DummyScriptFactory implements NativeScriptFactory {
public DummyScriptFactory() {}
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new DummyScript();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return DummyScript.NAME;
}
}
private static class DummyScript extends AbstractSearchScript {
public static final String NAME = "dummy";
@Override
public Object run() {
return null;
}
}
}

View File

@ -31,16 +31,13 @@ import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.index.query.QueryParseContext;
import org.elasticsearch.index.query.QueryShardException;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.plugins.SearchPlugin;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.MockScriptPlugin;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.search.aggregations.Aggregation;
import org.elasticsearch.search.aggregations.Aggregations;
import org.elasticsearch.search.aggregations.bucket.filter.InternalFilter;
import org.elasticsearch.search.aggregations.bucket.script.NativeSignificanceScoreScriptNoParams;
import org.elasticsearch.search.aggregations.bucket.script.NativeSignificanceScoreScriptWithParams;
import org.elasticsearch.search.aggregations.bucket.significant.SignificantTerms;
import org.elasticsearch.search.aggregations.bucket.significant.SignificantTermsAggregatorFactory;
import org.elasticsearch.search.aggregations.bucket.significant.heuristics.ChiSquare;
@ -64,6 +61,7 @@ import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ExecutionException;
import java.util.function.Function;
import static java.util.Collections.singletonList;
import static org.elasticsearch.cluster.metadata.IndexMetaData.SETTING_NUMBER_OF_REPLICAS;
@ -168,7 +166,7 @@ public class SignificantTermsSignificanceScoreIT extends ESIntegTestCase {
}
}
public static class CustomSignificanceHeuristicPlugin extends Plugin implements ScriptPlugin, SearchPlugin {
public static class CustomSignificanceHeuristicPlugin extends MockScriptPlugin implements SearchPlugin {
@Override
public List<SearchExtensionSpec<SignificanceHeuristic, SignificanceHeuristicParser>> getSignificanceHeuristics() {
return singletonList(new SearchExtensionSpec<SignificanceHeuristic, SignificanceHeuristicParser>(SimpleHeuristic.NAME,
@ -176,9 +174,22 @@ public class SignificantTermsSignificanceScoreIT extends ESIntegTestCase {
}
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Arrays.asList(new NativeSignificanceScoreScriptNoParams.Factory(),
new NativeSignificanceScoreScriptWithParams.Factory());
public Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
Map<String, Function<Map<String, Object>, Object>> scripts = new HashMap<>();
scripts.put("script_with_params", params -> {
double factor = ((Number) params.get("param")).doubleValue();
return factor * (longValue(params.get("_subset_freq")) + longValue(params.get("_subset_size")) +
longValue(params.get("_superset_freq")) + longValue(params.get("_superset_size"))) / factor;
});
scripts.put("script_no_params", params ->
longValue(params.get("_subset_freq")) + longValue(params.get("_subset_size")) +
longValue(params.get("_superset_freq")) + longValue(params.get("_superset_size"))
);
return scripts;
}
private static long longValue(Object value) {
return ((ScriptHeuristic.LongAccessor) value).longValue();
}
}
@ -514,9 +525,9 @@ public class SignificantTermsSignificanceScoreIT extends ESIntegTestCase {
if (randomBoolean()) {
Map<String, Object> params = new HashMap<>();
params.put("param", randomIntBetween(1, 100));
script = new Script(ScriptType.INLINE, "native", "native_significance_score_script_with_params", params);
script = new Script(ScriptType.INLINE, "mockscript", "script_with_params", params);
} else {
script = new Script(ScriptType.INLINE, "native", "native_significance_score_script_no_params", Collections.emptyMap());
script = new Script(ScriptType.INLINE, "mockscript", "script_no_params", Collections.emptyMap());
}
return new ScriptHeuristic(script);
}

View File

@ -19,22 +19,29 @@
package org.elasticsearch.search.functionscore;
import org.apache.lucene.index.LeafReaderContext;
import org.apache.lucene.search.Explanation;
import org.elasticsearch.action.index.IndexRequestBuilder;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.action.search.SearchType;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.lucene.search.function.CombineFunction;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.index.fielddata.ScriptDocValues;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.script.AbstractDoubleSearchScript;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.script.CompiledScript;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.ExplainableSearchScript;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.LeafSearchScript;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptEngine;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.script.SearchScript;
import org.elasticsearch.search.SearchHit;
import org.elasticsearch.search.SearchHits;
import org.elasticsearch.search.lookup.LeafDocLookup;
import org.elasticsearch.search.lookup.SearchLookup;
import org.elasticsearch.test.ESIntegTestCase;
import org.elasticsearch.test.ESIntegTestCase.ClusterScope;
import org.elasticsearch.test.ESIntegTestCase.Scope;
@ -60,12 +67,77 @@ import static org.hamcrest.Matchers.equalTo;
@ClusterScope(scope = Scope.SUITE, supportsDedicatedMasters = false, numDataNodes = 1)
public class ExplainableScriptIT extends ESIntegTestCase {
public static class ExplainableScriptPlugin extends Plugin implements ScriptPlugin {
@Override
public ScriptEngine getScriptEngine(Settings settings) {
return new ScriptEngine() {
@Override
public String getType() {
return "test";
}
@Override
public Object compile(String scriptName, String scriptSource, Map<String, String> params) {
assert scriptSource.equals("explainable_script");
return null;
}
@Override
public ExecutableScript executable(CompiledScript compiledScript, @Nullable Map<String, Object> vars) {
throw new UnsupportedOperationException();
}
@Override
public SearchScript search(CompiledScript compiledScript, SearchLookup lookup, @Nullable Map<String, Object> vars) {
return new SearchScript() {
@Override
public LeafSearchScript getLeafSearchScript(LeafReaderContext context) throws IOException {
return new MyScript(lookup.doc().getLeafDocLookup(context));
}
@Override
public boolean needsScores() {
return false;
}
};
}
@Override
public void close() {}
};
}
}
static class MyScript implements ExplainableSearchScript {
LeafDocLookup docLookup;
MyScript(LeafDocLookup docLookup) {
this.docLookup = docLookup;
}
@Override
public void setDocument(int doc) {
docLookup.setDocument(doc);
}
@Override
public Explanation explain(Explanation subQueryScore) throws IOException {
Explanation scoreExp = Explanation.match(subQueryScore.getValue(), "_score: ", subQueryScore);
return Explanation.match((float) (runAsDouble()), "This script returned " + runAsDouble(), scoreExp);
}
@Override
public double runAsDouble() {
return ((Number) ((ScriptDocValues) docLookup.get("number_field")).getValues().get(0)).doubleValue();
}
}
@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Arrays.asList(ExplainableScriptPlugin.class);
}
public void testNativeExplainScript() throws InterruptedException, IOException, ExecutionException {
public void testExplainScript() throws InterruptedException, IOException, ExecutionException {
List<IndexRequestBuilder> indexRequests = new ArrayList<>();
for (int i = 0; i < 20; i++) {
indexRequests.add(client().prepareIndex("test", "type").setId(Integer.toString(i)).setSource(
@ -78,7 +150,7 @@ public class ExplainableScriptIT extends ESIntegTestCase {
searchSource().explain(true).query(
functionScoreQuery(termQuery("text", "text"),
scriptFunction(
new Script(ScriptType.INLINE, "native", "native_explainable_script", Collections.emptyMap())))
new Script(ScriptType.INLINE, "test", "explainable_script", Collections.emptyMap())))
.boostMode(CombineFunction.REPLACE)))).actionGet();
ElasticsearchAssertions.assertNoFailures(response);
@ -89,39 +161,10 @@ public class ExplainableScriptIT extends ESIntegTestCase {
assertThat(hit.getId(), equalTo(Integer.toString(idCounter)));
assertThat(hit.getExplanation().toString(),
containsString(Double.toString(idCounter) + " = This script returned " + Double.toString(idCounter)));
assertThat(hit.getExplanation().toString(), containsString("freq=1.0 = termFreq=1.0"));
assertThat(hit.getExplanation().toString(), containsString("freq=1.0"));
assertThat(hit.getExplanation().toString(), containsString("termFreq=1.0"));
assertThat(hit.getExplanation().getDetails().length, equalTo(2));
idCounter--;
}
}
public static class MyNativeScriptFactory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new MyScript();
}
@Override
public boolean needsScores() {
return true;
}
@Override
public String getName() {
return "native_explainable_script";
}
}
static class MyScript extends AbstractDoubleSearchScript implements ExplainableSearchScript, ExecutableScript {
@Override
public Explanation explain(Explanation subQueryScore) throws IOException {
Explanation scoreExp = Explanation.match(subQueryScore.getValue(), "_score: ", subQueryScore);
return Explanation.match((float) (runAsDouble()), "This script returned " + runAsDouble(), scoreExp);
}
@Override
public double runAsDouble() {
return ((Number) ((ScriptDocValues) doc().get("number_field")).getValues().get(0)).doubleValue();
}
}
}

View File

@ -1,35 +0,0 @@
/*
* 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.functionscore;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.script.NativeScriptFactory;
import java.util.Collections;
import java.util.List;
public class ExplainableScriptPlugin extends Plugin implements ScriptPlugin {
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Collections.singletonList(new ExplainableScriptIT.MyNativeScriptFactory());
}
}

View File

@ -1,117 +0,0 @@
/*
* 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.update;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.plugins.ScriptPlugin;
import org.elasticsearch.script.AbstractExecutableScript;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptEngine;
import org.elasticsearch.script.NativeScriptFactory;
import org.elasticsearch.script.Script;
import org.elasticsearch.script.ScriptType;
import org.elasticsearch.test.ESIntegTestCase;
import org.elasticsearch.test.ESIntegTestCase.ClusterScope;
import org.elasticsearch.test.ESIntegTestCase.Scope;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import static org.hamcrest.Matchers.hasKey;
import static org.hamcrest.Matchers.is;
@ClusterScope(scope= Scope.SUITE, numDataNodes =1)
public class UpdateByNativeScriptIT extends ESIntegTestCase {
@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Arrays.asList(CustomNativeScriptFactory.TestPlugin.class);
}
public void testThatUpdateUsingNativeScriptWorks() throws Exception {
createIndex("test");
index("test", "type", "1", "text", "value");
Map<String, Object> params = new HashMap<>();
params.put("foo", "SETVALUE");
client().prepareUpdate("test", "type", "1")
.setScript(new Script(ScriptType.INLINE, NativeScriptEngine.NAME, "custom", params)).get();
Map<String, Object> data = client().prepareGet("test", "type", "1").get().getSource();
assertThat(data, hasKey("foo"));
assertThat(data.get("foo").toString(), is("SETVALUE"));
}
public static class CustomNativeScriptFactory implements NativeScriptFactory {
public static class TestPlugin extends Plugin implements ScriptPlugin {
@Override
public List<NativeScriptFactory> getNativeScripts() {
return Collections.singletonList(new CustomNativeScriptFactory());
}
}
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new CustomScript(params);
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return "custom";
}
}
static class CustomScript extends AbstractExecutableScript {
private Map<String, Object> params;
private Map<String, Object> vars = new HashMap<>(2);
CustomScript(Map<String, Object> params) {
this.params = params;
}
@Override
public Object run() {
if (vars.containsKey("ctx") && vars.get("ctx") instanceof Map) {
Map ctx = (Map) vars.get("ctx");
if (ctx.containsKey("_source") && ctx.get("_source") instanceof Map) {
Map source = (Map) ctx.get("_source");
source.putAll(params);
}
}
// return value does not matter, the UpdateHelper class
return null;
}
@Override
public void setNextVar(String name, Object value) {
vars.put(name, value);
}
}
}

View File

@ -6,6 +6,11 @@
The Groovy, JavaScript, and Python scripting languages were deprecated in
elasticsearch 5.0 and have now been removed. Use painless instead.
==== Native scripts removed
Native scripts have been removed. Instead,
<<modules-scripting-engine, implement a `ScriptEngine`>>.
==== Date fields now return dates
`doc.some_date_field.value` now returns ++ReadableDateTime++s instead of

View File

@ -183,13 +183,22 @@ public class MockScriptEngine implements ScriptEngine {
ctx.putAll(vars);
}
AbstractSearchScript leafSearchScript = new AbstractSearchScript() {
return new LeafSearchScript() {
@Override
public Object run() {
return script.apply(ctx);
}
@Override
public long runAsLong() {
return ((Number) run()).longValue();
}
@Override
public double runAsDouble() {
return ((Number) run()).doubleValue();
}
@Override
public void setNextVar(String name, Object value) {
ctx.put(name, value);
@ -197,12 +206,20 @@ public class MockScriptEngine implements ScriptEngine {
@Override
public void setScorer(Scorer scorer) {
super.setScorer(scorer);
ctx.put("_score", new ScoreAccessor(scorer));
}
@Override
public void setDocument(int doc) {
leafLookup.setDocument(doc);
}
@Override
public void setSource(Map<String, Object> source) {
leafLookup.source().setSource(source);
}
};
leafSearchScript.setLookup(leafLookup);
return leafSearchScript;
}
@Override

View File

@ -1,58 +0,0 @@
/*
* 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.bucket.script;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptFactory;
import java.util.Map;
public class NativeSignificanceScoreScriptNoParams extends TestScript {
public static final String NATIVE_SIGNIFICANCE_SCORE_SCRIPT_NO_PARAMS = "native_significance_score_script_no_params";
public static class Factory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new NativeSignificanceScoreScriptNoParams();
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return NATIVE_SIGNIFICANCE_SCORE_SCRIPT_NO_PARAMS;
}
}
private NativeSignificanceScoreScriptNoParams() {
}
@Override
public Object run() {
checkParams();
return _subset_freq.longValue() + _subset_size.longValue() + _superset_freq.longValue() + _superset_size.longValue();
}
}

View File

@ -1,63 +0,0 @@
/*
* 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.bucket.script;
import org.elasticsearch.common.Nullable;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.script.NativeScriptFactory;
import java.util.Map;
import java.util.Objects;
public class NativeSignificanceScoreScriptWithParams extends TestScript {
public static final String NATIVE_SIGNIFICANCE_SCORE_SCRIPT_WITH_PARAMS = "native_significance_score_script_with_params";
double factor = 0.0;
public static class Factory implements NativeScriptFactory {
@Override
public ExecutableScript newScript(@Nullable Map<String, Object> params) {
return new NativeSignificanceScoreScriptWithParams(params);
}
@Override
public boolean needsScores() {
return false;
}
@Override
public String getName() {
return NATIVE_SIGNIFICANCE_SCORE_SCRIPT_WITH_PARAMS;
}
}
private NativeSignificanceScoreScriptWithParams(Map<String, Object> params) {
factor = ((Number) params.get("param")).doubleValue();
}
@Override
public Object run() {
checkParams();
Objects.requireNonNull(factor, "factor");
return factor * (_subset_freq.longValue() + _subset_size.longValue() + _superset_freq.longValue() + _superset_size.longValue()) / factor;
}
}

View File

@ -1,59 +0,0 @@
/*
* 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.bucket.script;
import java.util.Objects;
import org.elasticsearch.script.ExecutableScript;
import org.elasticsearch.search.aggregations.bucket.significant.heuristics.ScriptHeuristic;
public abstract class TestScript implements ExecutableScript{
ScriptHeuristic.LongAccessor _subset_freq;
ScriptHeuristic.LongAccessor _subset_size;
ScriptHeuristic.LongAccessor _superset_freq;
ScriptHeuristic.LongAccessor _superset_size;
protected TestScript() {
}
@Override
public void setNextVar(String name, Object value) {
if (name.equals("_subset_freq")) {
_subset_freq = (ScriptHeuristic.LongAccessor)value;
}
if (name.equals("_subset_size")) {
_subset_size = (ScriptHeuristic.LongAccessor)value;
}
if (name.equals("_superset_freq")) {
_superset_freq = (ScriptHeuristic.LongAccessor)value;
}
if (name.equals("_superset_size")) {
_superset_size = (ScriptHeuristic.LongAccessor)value;
}
}
protected final void checkParams() {
Objects.requireNonNull(_subset_freq, "_subset_freq");
Objects.requireNonNull(_subset_size, "_subset_size");
Objects.requireNonNull(_superset_freq, "_superset_freq");
Objects.requireNonNull(_superset_size, "_superset_size");
}
}