Skip to content
This repository has been archived by the owner on Aug 2, 2022. It is now read-only.

Commit

Permalink
Adding test coverage for Preview Transport Action
Browse files Browse the repository at this point in the history
  • Loading branch information
saratvemulapalli committed Jan 6, 2021
1 parent 4213a23 commit bcf1b51
Show file tree
Hide file tree
Showing 4 changed files with 375 additions and 192 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
import org.elasticsearch.action.support.HandledTransportAction;
import org.elasticsearch.client.Client;
import org.elasticsearch.cluster.service.ClusterService;
import org.elasticsearch.common.CheckedConsumer;
import org.elasticsearch.common.inject.Inject;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.util.concurrent.ThreadContext;
Expand Down Expand Up @@ -108,24 +109,22 @@ private ActionListener<List<AnomalyResult>> getPreviewDetectorActionListener(
ActionListener<PreviewAnomalyDetectorResponse> listener,
AnomalyDetector detector
) {
return new ActionListener<List<AnomalyResult>>() {
return ActionListener.wrap(new CheckedConsumer<List<AnomalyResult>, Exception>() {
@Override
public void onResponse(List<AnomalyResult> anomalyResults) {
PreviewAnomalyDetectorResponse response = new PreviewAnomalyDetectorResponse(anomalyResults, detector);
public void accept(List<AnomalyResult> anomalyResult) throws Exception {
PreviewAnomalyDetectorResponse response = new PreviewAnomalyDetectorResponse(anomalyResult, detector);
listener.onResponse(response);
}

@Override
public void onFailure(Exception e) {
listener
.onFailure(
new ElasticsearchException(
"Unexpected error running anomaly detector " + detector.getDetectorId(),
RestStatus.INTERNAL_SERVER_ERROR
)
);
}
};
}, exception -> {
logger.error("Unexpected error running anomaly detector " + detector.getDetectorId(), exception);
listener
.onFailure(
new ElasticsearchException(
"Unexpected error running anomaly detector " + detector.getDetectorId(),
RestStatus.INTERNAL_SERVER_ERROR
)
);
});
}

private void previewAnomalyDetector(
Expand All @@ -138,7 +137,7 @@ private void previewAnomalyDetector(
GetRequest getRequest = new GetRequest(AnomalyDetector.ANOMALY_DETECTORS_INDEX).id(detectorId);
client.get(getRequest, onGetAnomalyDetectorResponse(listener, startTime, endTime));
} else {
listener.onFailure(new ElasticsearchException("Wrong input, no detector id", RestStatus.NOT_FOUND));
listener.onFailure(new ElasticsearchException("Wrong input, no detector id", RestStatus.BAD_REQUEST));
}
}

Expand All @@ -147,9 +146,9 @@ private ActionListener<GetResponse> onGetAnomalyDetectorResponse(
Instant startTime,
Instant endTime
) {
return new ActionListener<GetResponse>() {
return ActionListener.wrap(new CheckedConsumer<GetResponse, Exception>() {
@Override
public void onResponse(GetResponse response) {
public void accept(GetResponse response) throws Exception {
if (!response.isExists()) {
listener
.onFailure(
Expand All @@ -170,11 +169,6 @@ public void onResponse(GetResponse response) {
listener.onFailure(e);
}
}

@Override
public void onFailure(Exception e) {
listener.onFailure(new ElasticsearchException("Could not execute get query to find detector"));
}
};
}, exception -> { listener.onFailure(new ElasticsearchException("Could not execute get query to find detector")); });
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
import java.nio.ByteBuffer;
import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.AbstractMap;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
Expand Down Expand Up @@ -113,6 +114,8 @@

import com.amazon.opendistroforelasticsearch.ad.constant.CommonName;
import com.amazon.opendistroforelasticsearch.ad.constant.CommonValue;
import com.amazon.opendistroforelasticsearch.ad.feature.Features;
import com.amazon.opendistroforelasticsearch.ad.ml.ThresholdingResult;
import com.amazon.opendistroforelasticsearch.ad.model.ADTask;
import com.amazon.opendistroforelasticsearch.ad.model.ADTaskState;
import com.amazon.opendistroforelasticsearch.ad.model.ADTaskType;
Expand Down Expand Up @@ -477,6 +480,25 @@ public static Feature randomFeature(String featureName, String aggregationName,
return new Feature(randomAlphaOfLength(5), featureName, enabled, testAggregation);
}

public static Features randomFeatures() {
List<Map.Entry<Long, Long>> ranges = Arrays.asList(new AbstractMap.SimpleEntry<>(0L, 1L));
double[][] unprocessed = new double[][] { { randomDouble(), randomDouble() } };
double[][] processed = new double[][] { { randomDouble(), randomDouble() } };

return new Features(ranges, unprocessed, processed);
}

public static List<ThresholdingResult> randomThresholdingResults() {
double grade = 1.;
double confidence = 0.5;
double score = 1.;

ThresholdingResult thresholdingResult = new ThresholdingResult(grade, confidence, score);
List<ThresholdingResult> results = new ArrayList<>();
results.add(thresholdingResult);
return results;
}

public static User randomUser() {
return new User(
randomAlphaOfLength(8),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,197 +15,29 @@

package com.amazon.opendistroforelasticsearch.ad.transport;

import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;

import java.io.IOException;
import java.time.Instant;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashSet;
import java.util.concurrent.TimeUnit;

import org.elasticsearch.action.ActionListener;
import org.elasticsearch.action.admin.indices.create.CreateIndexRequest;
import org.elasticsearch.action.support.ActionFilters;
import org.elasticsearch.client.Client;
import org.elasticsearch.cluster.service.ClusterService;
import org.elasticsearch.common.io.stream.BytesStreamOutput;
import org.elasticsearch.common.io.stream.NamedWriteableAwareStreamInput;
import org.elasticsearch.common.io.stream.NamedWriteableRegistry;
import org.elasticsearch.common.settings.ClusterSettings;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.xcontent.ToXContent;
import org.elasticsearch.tasks.Task;
import org.elasticsearch.test.ESSingleNodeTestCase;
import org.elasticsearch.transport.TransportService;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;

import com.amazon.opendistroforelasticsearch.ad.AnomalyDetectorRunner;
import com.amazon.opendistroforelasticsearch.ad.TestHelpers;
import com.amazon.opendistroforelasticsearch.ad.feature.FeatureManager;
import com.amazon.opendistroforelasticsearch.ad.ml.ModelManager;
import com.amazon.opendistroforelasticsearch.ad.model.AnomalyDetector;
import com.amazon.opendistroforelasticsearch.ad.model.AnomalyResult;
import com.amazon.opendistroforelasticsearch.ad.settings.AnomalyDetectorSettings;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;

public class PreviewAnomalyDetectorActionTests extends ESSingleNodeTestCase {
private ActionListener<PreviewAnomalyDetectorResponse> response;
private PreviewAnomalyDetectorTransportAction action;
private AnomalyDetectorRunner runner;
private ClusterService clusterService;
private Task task;

@Override
@Before
public void setUp() throws Exception {
super.setUp();
task = mock(Task.class);
clusterService = mock(ClusterService.class);
ClusterSettings clusterSettings = new ClusterSettings(
Settings.EMPTY,
Collections.unmodifiableSet(new HashSet<>(Arrays.asList(AnomalyDetectorSettings.MAX_ANOMALY_FEATURES)))
);
when(clusterService.getClusterSettings()).thenReturn(clusterSettings);
runner = new AnomalyDetectorRunner(
mock(ModelManager.class),
mock(FeatureManager.class),
AnomalyDetectorSettings.MAX_PREVIEW_RESULTS
);
action = new PreviewAnomalyDetectorTransportAction(
Settings.EMPTY,
mock(TransportService.class),
clusterService,
mock(ActionFilters.class),
client(),
runner,
xContentRegistry()
);
}

@Override
protected NamedWriteableRegistry writableRegistry() {
return getInstanceFromNode(NamedWriteableRegistry.class);
}

@Test
public void testPreviewTransportActionWithNoFeature() throws IOException {
// Detector with no feature, Preview should fail
AnomalyDetector detector = TestHelpers.randomAnomalyDetector(Collections.emptyList());
PreviewAnomalyDetectorRequest request = new PreviewAnomalyDetectorRequest(
detector,
detector.getDetectorId(),
Instant.now(),
Instant.now()
);
ActionListener<PreviewAnomalyDetectorResponse> previewResponse = new ActionListener<PreviewAnomalyDetectorResponse>() {
@Override
public void onResponse(PreviewAnomalyDetectorResponse response) {
Assert.assertTrue(false);
}

@Override
public void onFailure(Exception e) {
Assert.assertTrue(e.getMessage().contains("Can't preview detector without feature"));
}
};
action.doExecute(task, request, previewResponse);
}

@Test
public void testPreviewTransportActionWithNoDetector() throws IOException {
// When detectorId is null, preview should fail
PreviewAnomalyDetectorRequest request = new PreviewAnomalyDetectorRequest(null, "", Instant.now(), Instant.now());
ActionListener<PreviewAnomalyDetectorResponse> previewResponse = new ActionListener<PreviewAnomalyDetectorResponse>() {
@Override
public void onResponse(PreviewAnomalyDetectorResponse response) {
Assert.assertTrue(false);
}

@Override
public void onFailure(Exception e) {
Assert.assertTrue(e.getMessage().contains("Wrong input, no detector id"));
}
};
action.doExecute(task, request, previewResponse);
}

@Test
public void testPreviewTransportActionWithDetectorID() throws IOException {
// When AD index does not exist, cannot query the detector
PreviewAnomalyDetectorRequest request = new PreviewAnomalyDetectorRequest(null, "1234", Instant.now(), Instant.now());
ActionListener<PreviewAnomalyDetectorResponse> previewResponse = new ActionListener<PreviewAnomalyDetectorResponse>() {
@Override
public void onResponse(PreviewAnomalyDetectorResponse response) {
Assert.assertTrue(false);
}

@Override
public void onFailure(Exception e) {
Assert.assertTrue(e.getMessage().contains("Could not execute get query to find detector"));
}
};
action.doExecute(task, request, previewResponse);
}

@Test
public void testPreviewTransportActionWithIndex() throws IOException {
// When AD index exists, and detector does not exist
PreviewAnomalyDetectorRequest request = new PreviewAnomalyDetectorRequest(null, "1234", Instant.now(), Instant.now());
Settings indexSettings = Settings.builder().put("index.number_of_shards", 5).put("index.number_of_replicas", 1).build();
CreateIndexRequest indexRequest = new CreateIndexRequest(AnomalyDetector.ANOMALY_DETECTORS_INDEX, indexSettings);
client().admin().indices().create(indexRequest).actionGet();
ActionListener<PreviewAnomalyDetectorResponse> previewResponse = new ActionListener<PreviewAnomalyDetectorResponse>() {
@Override
public void onResponse(PreviewAnomalyDetectorResponse response) {
Assert.assertTrue(false);
}

@Override
public void onFailure(Exception e) {
Assert.assertTrue(e.getMessage().contains("Can't find anomaly detector with id:1234"));
}
};
action.doExecute(task, request, previewResponse);
}

@Test
public void testPreviewTransportActionNoContext() throws IOException {
Client client = mock(Client.class);
PreviewAnomalyDetectorTransportAction previewAction = new PreviewAnomalyDetectorTransportAction(
Settings.EMPTY,
mock(TransportService.class),
clusterService,
mock(ActionFilters.class),
client,
runner,
xContentRegistry()
);
AnomalyDetector detector = TestHelpers.randomAnomalyDetector(ImmutableMap.of("testKey", "testValue"), Instant.now());
PreviewAnomalyDetectorRequest request = new PreviewAnomalyDetectorRequest(
detector,
detector.getDetectorId(),
Instant.now(),
Instant.now()
);
ActionListener<PreviewAnomalyDetectorResponse> previewResponse = new ActionListener<PreviewAnomalyDetectorResponse>() {
@Override
public void onResponse(PreviewAnomalyDetectorResponse response) {
Assert.assertTrue(false);
}

@Override
public void onFailure(Exception e) {
Assert.assertTrue(e.getClass() == NullPointerException.class);
}
};
previewAction.doExecute(task, request, previewResponse);
}

@Test
public void testPreviewRequest() throws Exception {
BytesStreamOutput out = new BytesStreamOutput();
Expand Down
Loading

0 comments on commit bcf1b51

Please sign in to comment.