Test: Simplify watch stats test script engine (elastic/x-pack-elasticsearch#1520)
This commit simplifies the WatchStatsTests to use a MockScriptPlugin. The latch script engine previously depended on a static instance of the engine to contain the latches. These are now moved to statics of the test class itself. Original commit: elastic/x-pack-elasticsearch@4170cd1bd3
This commit is contained in:
parent
ed827970f1
commit
b664e66a0d
|
@ -1,108 +0,0 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
package org.elasticsearch.script;
|
||||
|
||||
import org.apache.logging.log4j.Logger;
|
||||
import org.elasticsearch.ElasticsearchException;
|
||||
import org.elasticsearch.common.Nullable;
|
||||
import org.elasticsearch.common.logging.ESLoggerFactory;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.plugins.Plugin;
|
||||
import org.elasticsearch.plugins.ScriptPlugin;
|
||||
import org.elasticsearch.search.lookup.SearchLookup;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.Collections;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.CountDownLatch;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import static org.hamcrest.MatcherAssert.assertThat;
|
||||
import static org.hamcrest.Matchers.is;
|
||||
|
||||
public class LatchScriptEngine implements ScriptEngine {
|
||||
|
||||
private static final String NAME = "latch";
|
||||
private static final LatchScriptEngine INSTANCE = new LatchScriptEngine();
|
||||
|
||||
private CountDownLatch scriptStartedLatch = new CountDownLatch(1);
|
||||
private CountDownLatch scriptCompletionLatch = new CountDownLatch(1);
|
||||
private Logger logger = ESLoggerFactory.getLogger(getClass());
|
||||
|
||||
@Override
|
||||
public String getType() {
|
||||
return NAME;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object compile(String scriptName, String scriptSource, Map<String, String> params) {
|
||||
return scriptSource;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ExecutableScript executable(CompiledScript compiledScript, @Nullable Map<String, Object> vars) {
|
||||
return new ExecutableScript() {
|
||||
@Override
|
||||
public void setNextVar(String name, Object value) {}
|
||||
|
||||
@Override
|
||||
public Object run() {
|
||||
scriptStartedLatch.countDown();
|
||||
try {
|
||||
if (scriptCompletionLatch.await(10, TimeUnit.SECONDS) == false) {
|
||||
logger.error("Script completion latch was not counted down after 10 seconds");
|
||||
}
|
||||
} catch (InterruptedException e) {}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public SearchScript search(CompiledScript compiledScript, SearchLookup lookup, @Nullable Map<String, Object> vars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() throws IOException {
|
||||
}
|
||||
|
||||
public void awaitScriptStartedExecution() throws InterruptedException {
|
||||
if (scriptStartedLatch.await(10, TimeUnit.SECONDS) == false) {
|
||||
throw new ElasticsearchException("Expected script to be called within 10 seconds, did not happen");
|
||||
}
|
||||
}
|
||||
|
||||
public void finishScriptExecution() throws InterruptedException {
|
||||
scriptCompletionLatch.countDown();
|
||||
boolean countedDown = scriptCompletionLatch.await(10, TimeUnit.SECONDS);
|
||||
String msg = String.format(Locale.ROOT, "Script completion latch value is [%s], but should be 0", scriptCompletionLatch.getCount());
|
||||
assertThat(msg, countedDown, is(true));
|
||||
}
|
||||
|
||||
public void reset() {
|
||||
scriptStartedLatch = new CountDownLatch(1);
|
||||
scriptCompletionLatch = new CountDownLatch(1);
|
||||
}
|
||||
|
||||
public static Script latchScript() {
|
||||
return new Script(ScriptType.INLINE, NAME, "", Collections.emptyMap());
|
||||
}
|
||||
|
||||
public static class LatchScriptPlugin extends Plugin implements ScriptPlugin {
|
||||
|
||||
@Override
|
||||
public ScriptEngine getScriptEngine(Settings settings) {
|
||||
return INSTANCE;
|
||||
}
|
||||
|
||||
public LatchScriptEngine getScriptEngineService() {
|
||||
return INSTANCE;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -5,10 +5,15 @@
|
|||
*/
|
||||
package org.elasticsearch.xpack.watcher.transport.action.stats;
|
||||
|
||||
import org.apache.logging.log4j.Logger;
|
||||
import org.elasticsearch.ElasticsearchException;
|
||||
import org.elasticsearch.common.logging.ESLoggerFactory;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.common.util.concurrent.EsExecutors;
|
||||
import org.elasticsearch.plugins.Plugin;
|
||||
import org.elasticsearch.script.LatchScriptEngine;
|
||||
import org.elasticsearch.script.MockScriptPlugin;
|
||||
import org.elasticsearch.script.Script;
|
||||
import org.elasticsearch.script.ScriptType;
|
||||
import org.elasticsearch.test.ESIntegTestCase;
|
||||
import org.elasticsearch.test.junit.annotations.TestLogging;
|
||||
import org.elasticsearch.xpack.watcher.WatcherState;
|
||||
|
@ -20,13 +25,20 @@ import org.elasticsearch.xpack.watcher.execution.WatchExecutionSnapshot;
|
|||
import org.elasticsearch.xpack.watcher.input.InputBuilders;
|
||||
import org.elasticsearch.xpack.watcher.test.AbstractWatcherIntegrationTestCase;
|
||||
import org.elasticsearch.xpack.watcher.transport.actions.stats.WatcherStatsResponse;
|
||||
import org.hamcrest.Matchers;
|
||||
import org.joda.time.DateTime;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.CountDownLatch;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.function.Function;
|
||||
|
||||
import static org.elasticsearch.test.ESIntegTestCase.Scope.SUITE;
|
||||
import static org.elasticsearch.xpack.watcher.client.WatchSourceBuilders.watchBuilder;
|
||||
|
@ -45,6 +57,38 @@ import static org.hamcrest.core.Is.is;
|
|||
randomDynamicTemplates = false, numDataNodes = 1, supportsDedicatedMasters = false)
|
||||
public class WatchStatsTests extends AbstractWatcherIntegrationTestCase {
|
||||
|
||||
private static CountDownLatch scriptStartedLatch = new CountDownLatch(1);
|
||||
private static CountDownLatch scriptCompletionLatch = new CountDownLatch(1);
|
||||
private static Logger logger = ESLoggerFactory.getLogger(WatchStatsTests.class);
|
||||
|
||||
public static class LatchScriptPlugin extends MockScriptPlugin {
|
||||
|
||||
private static final String NAME = "latch";
|
||||
|
||||
protected Map<String, Function<Map<String, Object>, Object>> pluginScripts() {
|
||||
return Collections.singletonMap(NAME, p -> {
|
||||
scriptStartedLatch.countDown();
|
||||
try {
|
||||
if (scriptCompletionLatch.await(10, TimeUnit.SECONDS) == false) {
|
||||
logger.error("Script completion latch was not counted down after 10 seconds");
|
||||
}
|
||||
} catch (InterruptedException e) {
|
||||
}
|
||||
return true;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
static Script latchScript() {
|
||||
return new Script(ScriptType.INLINE, "mockscript", LatchScriptPlugin.NAME, Collections.emptyMap());
|
||||
}
|
||||
|
||||
public void awaitScriptStartedExecution() throws InterruptedException {
|
||||
if (scriptStartedLatch.await(10, TimeUnit.SECONDS) == false) {
|
||||
throw new ElasticsearchException("Expected script to be called within 10 seconds, did not happen");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean timeWarped() {
|
||||
return false;
|
||||
|
@ -58,7 +102,7 @@ public class WatchStatsTests extends AbstractWatcherIntegrationTestCase {
|
|||
@Override
|
||||
protected Collection<Class<? extends Plugin>> nodePlugins() {
|
||||
List<Class<? extends Plugin>> plugins = new ArrayList<>(super.nodePlugins());
|
||||
plugins.add(LatchScriptEngine.LatchScriptPlugin.class);
|
||||
plugins.add(LatchScriptPlugin.class);
|
||||
return plugins;
|
||||
}
|
||||
|
||||
|
@ -73,12 +117,16 @@ public class WatchStatsTests extends AbstractWatcherIntegrationTestCase {
|
|||
|
||||
@Before
|
||||
public void createLatches() {
|
||||
getLatchScriptEngine().reset();
|
||||
scriptStartedLatch = new CountDownLatch(1);
|
||||
scriptCompletionLatch = new CountDownLatch(1);
|
||||
}
|
||||
|
||||
@After
|
||||
public void clearLatches() throws InterruptedException {
|
||||
getLatchScriptEngine().finishScriptExecution();
|
||||
scriptCompletionLatch.countDown();
|
||||
boolean countedDown = scriptCompletionLatch.await(10, TimeUnit.SECONDS);
|
||||
String msg = String.format(Locale.ROOT, "Script completion latch value is [%s], but should be 0", scriptCompletionLatch.getCount());
|
||||
assertThat(msg, countedDown, Matchers.is(true));
|
||||
}
|
||||
|
||||
@TestLogging("org.elasticsearch.xpack.watcher.trigger.schedule.engine:TRACE,org.elasticsearch.xpack.scheduler:TRACE,org.elasticsearch" +
|
||||
|
@ -87,12 +135,12 @@ public class WatchStatsTests extends AbstractWatcherIntegrationTestCase {
|
|||
watcherClient().preparePutWatch("_id").setSource(watchBuilder()
|
||||
.trigger(schedule(interval("1s")))
|
||||
.input(InputBuilders.simpleInput("key", "value"))
|
||||
.condition(new ScriptCondition(LatchScriptEngine.latchScript()))
|
||||
.condition(new ScriptCondition(latchScript()))
|
||||
.addAction("_action", ActionBuilders.loggingAction("some logging"))
|
||||
).get();
|
||||
|
||||
logger.info("Waiting for first script invocation");
|
||||
getLatchScriptEngine().awaitScriptStartedExecution();
|
||||
awaitScriptStartedExecution();
|
||||
logger.info("First script got executed, checking currently running watches");
|
||||
|
||||
WatcherStatsResponse response = watcherClient().prepareWatcherStats().setIncludeCurrentWatches(true).get();
|
||||
|
@ -116,13 +164,13 @@ public class WatchStatsTests extends AbstractWatcherIntegrationTestCase {
|
|||
watcherClient().preparePutWatch("_id" + i).setSource(watchBuilder()
|
||||
.trigger(schedule(interval("1s")))
|
||||
.input(noneInput())
|
||||
.condition(new ScriptCondition(LatchScriptEngine.latchScript()))
|
||||
.condition(new ScriptCondition(latchScript()))
|
||||
.addAction("_action", ActionBuilders.loggingAction("some logging"))
|
||||
).get();
|
||||
}
|
||||
|
||||
logger.info("Waiting for first script invocation");
|
||||
getLatchScriptEngine().awaitScriptStartedExecution();
|
||||
awaitScriptStartedExecution();
|
||||
// I know this still sucks, but it is still way faster than the older implementation
|
||||
logger.info("Sleeping 2.5 seconds to make sure a new round of watches is queued");
|
||||
Thread.sleep(2500);
|
||||
|
@ -162,8 +210,4 @@ public class WatchStatsTests extends AbstractWatcherIntegrationTestCase {
|
|||
.forEach(node -> queuedWatches.addAll(node.getQueuedWatches()));
|
||||
return queuedWatches;
|
||||
}
|
||||
|
||||
private LatchScriptEngine getLatchScriptEngine() {
|
||||
return internalCluster().getInstance(LatchScriptEngine.LatchScriptPlugin.class).getScriptEngineService();
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue