Added a `scheme` option to the `http` input that supports the values http or https.

Closes elastic/elasticsearch#174

Original commit: elastic/x-pack-elasticsearch@9ad7665b66
This commit is contained in:
Martijn van Groningen 2015-04-01 17:26:37 +02:00
parent a778f1978d
commit feb745763b
12 changed files with 334 additions and 95 deletions

View File

@ -10,6 +10,7 @@ import org.elasticsearch.action.search.SearchRequestBuilder;
import org.elasticsearch.watcher.input.http.HttpInput;
import org.elasticsearch.watcher.input.search.SearchInput;
import org.elasticsearch.watcher.input.simple.SimpleInput;
import org.elasticsearch.watcher.support.http.TemplatedHttpRequest;
import java.util.HashMap;
import java.util.Map;
@ -38,7 +39,7 @@ public final class InputBuilders {
return new SimpleInput.SourceBuilder(data);
}
public static HttpInput.SourceBuilder httpInput() {
return new HttpInput.SourceBuilder();
public static HttpInput.SourceBuilder httpInput(TemplatedHttpRequest.SourceBuilder requestSource) {
return new HttpInput.SourceBuilder(requestSource);
}
}

View File

@ -23,8 +23,6 @@ import org.elasticsearch.watcher.support.http.HttpClient;
import org.elasticsearch.watcher.support.http.HttpRequest;
import org.elasticsearch.watcher.support.http.HttpResponse;
import org.elasticsearch.watcher.support.http.TemplatedHttpRequest;
import org.elasticsearch.watcher.support.http.auth.HttpAuth;
import org.elasticsearch.watcher.support.template.Template;
import org.elasticsearch.watcher.watch.Payload;
import org.elasticsearch.watcher.watch.WatchExecutionContext;
@ -78,7 +76,7 @@ public class HttpInput extends Input<HttpInput.Result> {
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
builder.startObject();
builder.field(Parser.REQUEST_FIELD.getPreferredName());
builder = request.toXContent(builder, params);
builder = request.toXContent(builder, params);
if (extractKeys != null) {
builder.startArray(Parser.EXTRACT_FIELD.getPreferredName());
for (String extractKey : extractKeys) {
@ -232,54 +230,11 @@ public class HttpInput extends Input<HttpInput.Result> {
public final static class SourceBuilder implements Input.SourceBuilder {
private String host;
private int port;
private String method;
private Template path;
private Map<String, Template> params;
private Map<String, Template> headers;
private HttpAuth auth;
private Template body;
private TemplatedHttpRequest.SourceBuilder request;
private Set<String> extractKeys;
public SourceBuilder setHost(String host) {
this.host = host;
return this;
}
public SourceBuilder setPort(int port) {
this.port = port;
return this;
}
public SourceBuilder setMethod(String method) {
this.method = method;
return this;
}
public SourceBuilder setPath(Template path) {
this.path = path;
return this;
}
public SourceBuilder setParams(Map<String, Template> params) {
this.params = params;
return this;
}
public SourceBuilder setHeaders(Map<String, Template> headers) {
this.headers = headers;
return this;
}
public SourceBuilder setAuth(HttpAuth auth) {
this.auth = auth;
return this;
}
public SourceBuilder setBody(Template body) {
this.body = body;
return this;
public SourceBuilder(TemplatedHttpRequest.SourceBuilder request) {
this.request = request;
}
public SourceBuilder addExtractKey(String key) {
@ -296,7 +251,7 @@ public class HttpInput extends Input<HttpInput.Result> {
}
@Override
public XContentBuilder toXContent(XContentBuilder builder, Params p) throws IOException {
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
builder.startObject();
if (extractKeys != null) {
builder.startArray(Parser.EXTRACT_FIELD.getPreferredName());
@ -305,28 +260,8 @@ public class HttpInput extends Input<HttpInput.Result> {
}
builder.endArray();
}
builder.startObject(Parser.REQUEST_FIELD.getPreferredName());
builder.field(HttpRequest.Parser.HOST_FIELD.getPreferredName(), host);
builder.field(HttpRequest.Parser.PORT_FIELD.getPreferredName(), port);
if (method != null) {
builder.field(HttpRequest.Parser.METHOD_FIELD.getPreferredName(), method);
}
if (path != null) {
builder.field(HttpRequest.Parser.PATH_FIELD.getPreferredName(), path);
}
if (params != null) {
builder.field(HttpRequest.Parser.PARAMS_FIELD.getPreferredName(), params);
}
if (headers != null) {
builder.field(HttpRequest.Parser.HEADERS_FIELD.getPreferredName(), headers);
}
if (auth != null) {
builder.field(HttpRequest.Parser.AUTH_FIELD.getPreferredName(), auth);
}
if (body != null) {
builder.field(HttpRequest.Parser.BODY_FIELD.getPreferredName(), body);
}
builder.endObject();
builder.field(Parser.REQUEST_FIELD.getPreferredName());
request.toXContent(builder, params);
return builder.endObject();
}
}

View File

@ -5,14 +5,22 @@
*/
package org.elasticsearch.watcher.support.http;
import org.elasticsearch.ElasticsearchIllegalStateException;
import org.elasticsearch.ExceptionsHelper;
import org.elasticsearch.common.base.Charsets;
import org.elasticsearch.common.component.AbstractComponent;
import org.elasticsearch.common.inject.Inject;
import org.elasticsearch.common.settings.Settings;
import javax.net.ssl.*;
import java.io.IOException;
import java.io.InputStream;
import java.net.*;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.security.KeyStore;
import java.security.SecureRandom;
import java.util.Map;
/**
@ -20,9 +28,30 @@ import java.util.Map;
*/
public class HttpClient extends AbstractComponent {
private static final String SETTINGS_SSL_PREFIX = "watcher.http.ssl.";
private static final String SETTINGS_SSL_SHIELD_PREFIX = "shield.ssl.";
public static final String SETTINGS_SSL_PROTOCOL = SETTINGS_SSL_PREFIX + "protocol";
private static final String SETTINGS_SSL_SHIELD_CONTEXT_ALGORITHM = SETTINGS_SSL_SHIELD_PREFIX + "context.algorithm";
public static final String SETTINGS_SSL_TRUSTSTORE = SETTINGS_SSL_PREFIX + "truststore.path";
private static final String SETTINGS_SSL_SHIELD_TRUSTSTORE = SETTINGS_SSL_SHIELD_PREFIX + "truststore.path";
public static final String SETTINGS_SSL_TRUSTSTORE_PASSWORD = SETTINGS_SSL_PREFIX + "truststore.password";
private static final String SETTINGS_SSL_SHIELD_TRUSTSTORE_PASSWORD = SETTINGS_SSL_SHIELD_PREFIX + "truststore.password";
public static final String SETTINGS_SSL_TRUSTSTORE_ALGORITHM = SETTINGS_SSL_PREFIX + "truststore.algorithm";
private static final String SETTINGS_SSL_SHIELD_TRUSTSTORE_ALGORITHM = SETTINGS_SSL_SHIELD_PREFIX + "truststore.algorithm";
final SSLSocketFactory sslSocketFactory;
@Inject
public HttpClient(Settings settings) {
super(settings);
if (!settings.getByPrefix(SETTINGS_SSL_PREFIX).getAsMap().isEmpty() ||
!settings.getByPrefix(SETTINGS_SSL_SHIELD_PREFIX).getAsMap().isEmpty()) {
sslSocketFactory = createSSLSocketFactory(settings);
} else {
logger.trace("no ssl context configured");
sslSocketFactory = null;
}
}
// TODO: Remove this when webhook action has been refactored to use this client properly
@ -50,7 +79,7 @@ public class HttpClient extends AbstractComponent {
URI uri;
try {
uri = new URI("http", null, request.host(), request.port(), request.path(), queryString, null);
uri = new URI(request.scheme().scheme(), null, request.host(), request.port(), request.path(), queryString, null);
} catch (URISyntaxException e) {
throw ExceptionsHelper.convertToElastic(e);
}
@ -63,6 +92,11 @@ public class HttpClient extends AbstractComponent {
logger.debug("making [{}] request to [{}]", request.method().method(), url);
logger.trace("sending [{}] as body of request", request.body());
HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
if (urlConnection instanceof HttpsURLConnection && sslSocketFactory != null) {
HttpsURLConnection httpsConn = (HttpsURLConnection) urlConnection;
httpsConn.setSSLSocketFactory(sslSocketFactory);
}
urlConnection.setRequestMethod(request.method().method());
if (request.headers() != null) {
for (Map.Entry<String, String> entry : request.headers().entrySet()) {
@ -89,4 +123,57 @@ public class HttpClient extends AbstractComponent {
return response;
}
/** SSL Initialization * */
private SSLSocketFactory createSSLSocketFactory(Settings settings) {
SSLContext sslContext;
// Initialize sslContext
try {
String sslContextProtocol = settings.get(SETTINGS_SSL_PROTOCOL, settings.get(SETTINGS_SSL_SHIELD_CONTEXT_ALGORITHM, "TLS"));
String trustStore = settings.get(SETTINGS_SSL_TRUSTSTORE, settings.get(SETTINGS_SSL_SHIELD_TRUSTSTORE, System.getProperty("javax.net.ssl.trustStore")));
String trustStorePassword = settings.get(SETTINGS_SSL_TRUSTSTORE_PASSWORD, settings.get(SETTINGS_SSL_SHIELD_TRUSTSTORE_PASSWORD, System.getProperty("javax.net.ssl.trustStorePassword")));
String trustStoreAlgorithm = settings.get(SETTINGS_SSL_TRUSTSTORE_ALGORITHM, settings.get(SETTINGS_SSL_SHIELD_TRUSTSTORE_ALGORITHM, System.getProperty("ssl.TrustManagerFactory.algorithm")));
if (trustStore == null) {
throw new RuntimeException("truststore is not configured, use " + SETTINGS_SSL_TRUSTSTORE);
}
if (trustStoreAlgorithm == null) {
trustStoreAlgorithm = TrustManagerFactory.getDefaultAlgorithm();
}
logger.debug("SSL: using trustStore[{}], trustAlgorithm[{}]", trustStore, trustStoreAlgorithm);
Path path = Paths.get(trustStore);
if (Files.notExists(path)) {
throw new ElasticsearchIllegalStateException("Truststore at path [" + trustStore + "] does not exist");
}
KeyManager[] keyManagers;
TrustManager[] trustManagers;
try (InputStream trustStoreStream = Files.newInputStream(path)) {
// Load TrustStore
KeyStore ks = KeyStore.getInstance("jks");
ks.load(trustStoreStream, trustStorePassword == null ? null : trustStorePassword.toCharArray());
KeyManagerFactory factory = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
factory.init(ks, trustStorePassword == null ? null : trustStorePassword.toCharArray());
keyManagers = factory.getKeyManagers();
// Initialize a trust manager factory with the trusted store
TrustManagerFactory trustFactory = TrustManagerFactory.getInstance(trustStoreAlgorithm);
trustFactory.init(ks);
// Retrieve the trust managers from the factory
trustManagers = trustFactory.getTrustManagers();
} catch (Exception e) {
throw new RuntimeException("Failed to initialize a TrustManagerFactory", e);
}
sslContext = SSLContext.getInstance(sslContextProtocol);
sslContext.init(keyManagers, trustManagers, new SecureRandom());
} catch (Exception e) {
throw new RuntimeException("[http.client] failed to initialize the SSLContext", e);
}
return sslContext.getSocketFactory();
}
}

View File

@ -21,6 +21,7 @@ import java.util.Map;
public class HttpRequest implements ToXContent {
private Scheme scheme;
private String host;
private int port;
private HttpMethod method;
@ -31,9 +32,18 @@ public class HttpRequest implements ToXContent {
private String body;
public HttpRequest() {
scheme = Scheme.HTTP;
method = HttpMethod.GET;
}
public Scheme scheme() {
return scheme;
}
public void scheme(Scheme scheme) {
this.scheme = scheme;
}
public String host() {
return host;
}
@ -129,6 +139,7 @@ public class HttpRequest implements ToXContent {
HttpRequest request = (HttpRequest) o;
if (scheme != request.scheme) return false;
if (port != request.port) return false;
if (auth != null ? !auth.equals(request.auth) : request.auth != null) return false;
if (body != null ? !body.equals(request.body) : request.body != null) return false;
@ -146,6 +157,7 @@ public class HttpRequest implements ToXContent {
int result = host.hashCode();
result = 31 * result + port;
result = 31 * result + method.hashCode();
result = 31 * result + scheme.hashCode();
result = 31 * result + (path != null ? path.hashCode() : 0);
result = 31 * result + (params != null ? params.hashCode() : 0);
result = 31 * result + (headers != null ? headers.hashCode() : 0);
@ -156,6 +168,7 @@ public class HttpRequest implements ToXContent {
public static class Parser {
public static final ParseField SCHEME_FIELD = new ParseField("scheme");
public static final ParseField HOST_FIELD = new ParseField("host");
public static final ParseField PORT_FIELD = new ParseField("port");
public static final ParseField METHOD_FIELD = new ParseField("method");
@ -192,7 +205,9 @@ public class HttpRequest implements ToXContent {
throw new ElasticsearchParseException("could not parse http request. unexpected field [" + currentFieldName + "]");
}
} else if (token == XContentParser.Token.VALUE_STRING) {
if (METHOD_FIELD.match(currentFieldName)) {
if (SCHEME_FIELD.match(currentFieldName)) {
request.scheme(Scheme.parse(parser.text()));
} else if (METHOD_FIELD.match(currentFieldName)) {
request.method(HttpMethod.parse(parser.text()));
} else if (HOST_FIELD.match(currentFieldName)) {
request.host(parser.text());
@ -210,7 +225,7 @@ public class HttpRequest implements ToXContent {
throw new ElasticsearchParseException("could not parse http request. unexpected field [" + currentFieldName + "]");
}
} else {
throw new ElasticsearchParseException("could not parse http request. unexpected token [" + token + "]");
throw new ElasticsearchParseException("could not parse http request. unexpected token [" + token + "] for field [" + currentFieldName + "]");
}
}
return request;
@ -220,6 +235,7 @@ public class HttpRequest implements ToXContent {
public final static class SourceBuilder implements ToXContent {
private String scheme;
private String host;
private int port;
private String method;
@ -229,6 +245,11 @@ public class HttpRequest implements ToXContent {
private HttpAuth auth;
private Template body;
public SourceBuilder setScheme(String scheme) {
this.scheme = scheme;
return this;
}
public SourceBuilder setHost(String host) {
this.host = host;
return this;
@ -272,6 +293,9 @@ public class HttpRequest implements ToXContent {
@Override
public XContentBuilder toXContent(XContentBuilder builder, Params p) throws IOException {
builder.startObject();
if (scheme != null) {
builder.field(Parser.SCHEME_FIELD.getPreferredName(), scheme);
}
builder.field(HttpRequest.Parser.HOST_FIELD.getPreferredName(), host);
builder.field(HttpRequest.Parser.PORT_FIELD.getPreferredName(), port);
if (method != null) {

View File

@ -0,0 +1,38 @@
/*
* 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.watcher.support.http;
import org.elasticsearch.ElasticsearchIllegalArgumentException;
import java.util.Locale;
public enum Scheme {
HTTP("http"),
HTTPS("https");
private final String scheme;
Scheme(String scheme) {
this.scheme = scheme;
}
public String scheme() {
return scheme;
}
public static Scheme parse(String value) {
value = value.toLowerCase(Locale.ROOT);
switch (value) {
case "http":
return HTTP;
case "https":
return HTTPS;
default:
throw new ElasticsearchIllegalArgumentException("unsupported http scheme [" + value + "]");
}
}
}

View File

@ -24,6 +24,7 @@ import java.util.Map;
*/
public class TemplatedHttpRequest implements ToXContent {
private Scheme scheme;
private String host;
private int port;
private HttpMethod method;
@ -34,9 +35,18 @@ public class TemplatedHttpRequest implements ToXContent {
private Template body;
public TemplatedHttpRequest() {
scheme = Scheme.HTTP;
method = HttpMethod.GET;
}
public Scheme scheme() {
return scheme;
}
public void scheme(Scheme scheme) {
this.scheme = scheme;
}
public String host() {
return host;
}
@ -132,6 +142,7 @@ public class TemplatedHttpRequest implements ToXContent {
public XContentBuilder toXContent(XContentBuilder builder, ToXContent.Params params) throws IOException {
builder.startObject();
builder.field(Parser.SCHEME_FIELD.getPreferredName(), scheme);
builder.field(Parser.HOST_FIELD.getPreferredName(), host);
builder.field(Parser.PORT_FIELD.getPreferredName(), port);
builder.field(Parser.METHOD_FIELD.getPreferredName(), method);
@ -155,6 +166,7 @@ public class TemplatedHttpRequest implements ToXContent {
public static class Parser {
public static final ParseField SCHEME_FIELD = new ParseField("scheme");
public static final ParseField HOST_FIELD = new ParseField("host");
public static final ParseField PORT_FIELD = new ParseField("port");
public static final ParseField METHOD_FIELD = new ParseField("method");
@ -195,7 +207,9 @@ public class TemplatedHttpRequest implements ToXContent {
throw new ElasticsearchParseException("could not parse templated http request. unexpected field [" + currentFieldName + "]");
}
} else if (token == XContentParser.Token.VALUE_STRING) {
if (METHOD_FIELD.match(currentFieldName)) {
if (SCHEME_FIELD.match(currentFieldName)) {
request.scheme(Scheme.parse(parser.text()));
} else if (METHOD_FIELD.match(currentFieldName)) {
request.method(HttpMethod.parse(parser.text()));
} else if (HOST_FIELD.match(currentFieldName)) {
request.host(parser.text());
@ -213,7 +227,7 @@ public class TemplatedHttpRequest implements ToXContent {
throw new ElasticsearchParseException("could not parse templated http request. unexpected field [" + currentFieldName + "]");
}
} else {
throw new ElasticsearchParseException("could not parse templated http request. unexpected token [" + token + "]");
throw new ElasticsearchParseException("could not parse templated http request. unexpected token [" + token + "] for field [" + currentFieldName + "]");
}
}
return request;
@ -240,4 +254,92 @@ public class TemplatedHttpRequest implements ToXContent {
}
public final static class SourceBuilder implements ToXContent {
private String scheme;
private String host;
private int port;
private String method;
private Template path;
private Map<String, Template> params;
private Map<String, Template> headers;
private HttpAuth auth;
private Template body;
public SourceBuilder setScheme(String scheme) {
this.scheme = scheme;
return this;
}
public SourceBuilder setHost(String host) {
this.host = host;
return this;
}
public SourceBuilder setPort(int port) {
this.port = port;
return this;
}
public SourceBuilder setMethod(String method) {
this.method = method;
return this;
}
public SourceBuilder setPath(Template path) {
this.path = path;
return this;
}
public SourceBuilder setParams(Map<String, Template> params) {
this.params = params;
return this;
}
public SourceBuilder setHeaders(Map<String, Template> headers) {
this.headers = headers;
return this;
}
public SourceBuilder setAuth(HttpAuth auth) {
this.auth = auth;
return this;
}
public SourceBuilder setBody(Template body) {
this.body = body;
return this;
}
@Override
public XContentBuilder toXContent(XContentBuilder builder, Params p) throws IOException {
builder.startObject();
if (scheme != null) {
builder.field(Parser.SCHEME_FIELD.getPreferredName(), scheme);
}
builder.field(Parser.HOST_FIELD.getPreferredName(), host);
builder.field(Parser.PORT_FIELD.getPreferredName(), port);
if (method != null) {
builder.field(Parser.METHOD_FIELD.getPreferredName(), method);
}
if (path != null) {
builder.field(Parser.PATH_FIELD.getPreferredName(), path);
}
if (params != null) {
builder.field(Parser.PARAMS_FIELD.getPreferredName(), params);
}
if (headers != null) {
builder.field(Parser.HEADERS_FIELD.getPreferredName(), headers);
}
if (auth != null) {
builder.field(Parser.AUTH_FIELD.getPreferredName(), auth);
}
if (body != null) {
builder.field(Parser.BODY_FIELD.getPreferredName(), body);
}
builder.endObject();
return builder;
}
}
}

View File

@ -20,6 +20,7 @@ import org.elasticsearch.watcher.actions.Action;
import org.elasticsearch.watcher.actions.Actions;
import org.elasticsearch.watcher.condition.simple.AlwaysTrueCondition;
import org.elasticsearch.watcher.input.Input;
import org.elasticsearch.watcher.input.InputBuilders;
import org.elasticsearch.watcher.input.simple.SimpleInput;
import org.elasticsearch.watcher.support.clock.ClockMock;
import org.elasticsearch.watcher.support.http.*;
@ -108,6 +109,7 @@ public class HttpInputTests extends ElasticsearchTestCase {
@Repeat(iterations = 12)
public void testParser() throws Exception {
final String httpMethod = randomFrom("PUT", "POST", "GET", "DELETE", "HEAD", null);
String scheme = randomFrom("http", "https", null);
String host = randomAsciiOfLength(3);
int port = randomInt();
Template path = new MockTemplate(randomAsciiOfLength(3));
@ -115,7 +117,8 @@ public class HttpInputTests extends ElasticsearchTestCase {
Map<String, Template> params = randomBoolean() ? new MapBuilder<String, Template>().put("a", new MockTemplate("b")).map() : null;
Map<String, Template> headers = randomBoolean() ? new MapBuilder<String, Template>().put("c", new MockTemplate("d")).map() : null;
HttpAuth auth = randomBoolean() ? new BasicAuth("username", "password") : null;
HttpInput.SourceBuilder sourceBuilder = new HttpInput.SourceBuilder()
TemplatedHttpRequest.SourceBuilder requestSource = new TemplatedHttpRequest.SourceBuilder()
.setScheme(scheme)
.setMethod(httpMethod)
.setHost(host)
.setPort(port)
@ -124,11 +127,12 @@ public class HttpInputTests extends ElasticsearchTestCase {
.setParams(params)
.setHeaders(headers)
.setAuth(auth);
XContentParser parser = XContentHelper.createParser(jsonBuilder().value(sourceBuilder).bytes());
XContentParser parser = XContentHelper.createParser(jsonBuilder().value(InputBuilders.httpInput(requestSource)).bytes());
parser.nextToken();
HttpInput result = httpParser.parse(parser);
assertThat(result.type(), equalTo(HttpInput.TYPE));
assertThat(result.getRequest().scheme().scheme(), equalTo(scheme != null ? scheme : "http")); // http is the default
assertThat(result.getRequest().method().method(), equalTo(httpMethod != null ? httpMethod : "GET")); // get is the default
assertThat(result.getRequest().host(), equalTo(host));
assertThat(result.getRequest().port(), equalTo(port));
@ -146,13 +150,13 @@ public class HttpInputTests extends ElasticsearchTestCase {
@Test(expected = ElasticsearchIllegalArgumentException.class)
public void testParser_invalidHttpMethod() throws Exception {
Map<String, Template> headers = new MapBuilder<String, Template>().put("a", new MockTemplate("b")).map();
HttpInput.SourceBuilder sourceBuilder = new HttpInput.SourceBuilder()
TemplatedHttpRequest.SourceBuilder requestBuilder = new TemplatedHttpRequest.SourceBuilder()
.setMethod("_method")
.setHost("_host")
.setPort(123)
.setBody(new MockTemplate("_body"))
.setHeaders(headers);
XContentParser parser = XContentHelper.createParser(jsonBuilder().value(sourceBuilder).bytes());
XContentParser parser = XContentHelper.createParser(jsonBuilder().value(InputBuilders.httpInput(requestBuilder)).bytes());
parser.nextToken();
httpParser.parse(parser);
}

View File

@ -20,6 +20,8 @@ import org.junit.Before;
import org.junit.Test;
import java.net.BindException;
import java.nio.file.Path;
import java.nio.file.Paths;
import static org.hamcrest.Matchers.equalTo;
@ -105,4 +107,29 @@ public class HttpClientTest extends ElasticsearchTestCase {
assertThat(recordedRequest.getHeader("Authorization"), equalTo("Basic dXNlcjpwYXNz"));
}
@Test
public void testHttps() throws Exception {
Path resource = Paths.get(HttpClientTest.class.getResource("/org/elasticsearch/shield/keystore/testnode.jks").toURI());
HttpClient httpClient = new HttpClient(
ImmutableSettings.builder()
.put(HttpClient.SETTINGS_SSL_TRUSTSTORE, resource.toString())
.put(HttpClient.SETTINGS_SSL_TRUSTSTORE_PASSWORD, "testnode")
.build()
);
webServer.useHttps(httpClient.sslSocketFactory, false);
webServer.enqueue(new MockResponse().setResponseCode(200).setBody("body"));
HttpRequest request = new HttpRequest();
request.scheme(Scheme.HTTPS);
request.host("localhost");
request.port(webPort);
request.path("/test");
request.body("body");
HttpResponse response = httpClient.execute(request);
assertThat(response.status(), equalTo(200));
assertThat(new String(response.body(), Charsets.UTF_8), equalTo("body"));
RecordedRequest recordedRequest = webServer.takeRequest();
assertThat(recordedRequest.getBody().readUtf8Line(), equalTo("body"));
}
}

View File

@ -18,6 +18,7 @@ import org.elasticsearch.search.builder.SearchSourceBuilder;
import org.elasticsearch.watcher.WatcherPlugin;
import org.elasticsearch.watcher.client.WatchSourceBuilder;
import org.elasticsearch.watcher.client.WatcherClient;
import org.elasticsearch.watcher.support.http.TemplatedHttpRequest;
import org.elasticsearch.watcher.transport.actions.put.PutWatchRequest;
import org.elasticsearch.watcher.trigger.ScheduleTriggerEngineMock;
import org.elasticsearch.watcher.trigger.TriggerModule;
@ -168,7 +169,7 @@ public class WatcherBenchmark {
final String name = "_name" + i;
PutWatchRequest putAlertRequest = new PutWatchRequest(name, new WatchSourceBuilder()
.trigger(schedule(interval("5s")))
.input(httpInput().setHost("localhost").setPort(9200))
.input(httpInput(new TemplatedHttpRequest.SourceBuilder().setHost("localhost").setPort(9200)))
.condition(scriptCondition("ctx.payload.tagline == \"You Know, for Search\"")));
putAlertRequest.setName(name);
watcherClient.putWatch(putAlertRequest).actionGet();

View File

@ -13,7 +13,8 @@ import org.elasticsearch.node.internal.InternalNode;
import org.elasticsearch.watcher.client.WatchSourceBuilder;
import org.elasticsearch.watcher.client.WatcherClient;
import org.elasticsearch.watcher.history.HistoryStore;
import org.elasticsearch.watcher.input.http.HttpInput;
import org.elasticsearch.watcher.input.InputBuilders;
import org.elasticsearch.watcher.support.http.TemplatedHttpRequest;
import org.elasticsearch.watcher.support.http.auth.BasicAuth;
import org.elasticsearch.watcher.support.init.proxy.ScriptServiceProxy;
import org.elasticsearch.watcher.support.template.ScriptTemplate;
@ -32,7 +33,6 @@ import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertHitC
import static org.elasticsearch.watcher.actions.ActionBuilders.indexAction;
import static org.elasticsearch.watcher.client.WatchSourceBuilder.watchSourceBuilder;
import static org.elasticsearch.watcher.condition.ConditionBuilders.scriptCondition;
import static org.elasticsearch.watcher.input.InputBuilders.httpInput;
import static org.elasticsearch.watcher.trigger.TriggerBuilders.schedule;
import static org.elasticsearch.watcher.trigger.schedule.Schedules.interval;
import static org.hamcrest.Matchers.equalTo;
@ -61,17 +61,17 @@ public class HttpInputIntegrationTest extends AbstractWatcherIntegrationTests {
client().prepareIndex("index", "type", "id").setSource("{}").setRefresh(true).get();
InetSocketAddress address = internalTestCluster().httpAddresses()[0];
HttpInput.SourceBuilder input = httpInput()
TemplatedHttpRequest.SourceBuilder requestBuilder = new TemplatedHttpRequest.SourceBuilder()
.setHost(address.getHostName())
.setPort(address.getPort())
.setPath(new ScriptTemplate(sc, "/index/_search"))
.setBody(new ScriptTemplate(sc, jsonBuilder().startObject().field("size", 1).endObject().string()));
if (shieldEnabled()) {
input.setAuth(new BasicAuth("test", "changeme"));
requestBuilder.setAuth(new BasicAuth("test", "changeme"));
}
WatchSourceBuilder source = watchSourceBuilder()
.trigger(TriggerBuilders.schedule(interval("5s")))
.input(input)
.input(InputBuilders.httpInput(requestBuilder))
.condition(scriptCondition("ctx.payload.hits.total == 1"))
.addAction(indexAction("idx", "action"));
watcherClient().preparePutWatch("_name")
@ -98,20 +98,19 @@ public class HttpInputIntegrationTest extends AbstractWatcherIntegrationTests {
String body = jsonBuilder().prettyPrint().startObject()
.field("query").value(termQuery("field", "value"))
.endObject().string();
HttpInput.SourceBuilder httpInputBuilder = httpInput()
TemplatedHttpRequest.SourceBuilder requestBuilder = new TemplatedHttpRequest.SourceBuilder()
.setHost(address.getHostName())
.setPort(address.getPort())
.setPath(new ScriptTemplate(sc, "/idx/_search"))
.setBody(new ScriptTemplate(sc, body))
.addExtractKey("hits.total");
.setBody(new ScriptTemplate(sc, body));
if (shieldEnabled()) {
httpInputBuilder.setAuth(new BasicAuth("test", "changeme"));
requestBuilder.setAuth(new BasicAuth("test", "changeme"));
}
watcherClient.preparePutWatch("_name1")
.source(watchSourceBuilder()
.trigger(schedule(interval(5, IntervalSchedule.Interval.Unit.SECONDS)))
.input(httpInputBuilder)
.input(InputBuilders.httpInput(requestBuilder).addExtractKey("hits.total"))
.condition(scriptCondition("ctx.payload.hits.total == 1")))
.get();
@ -119,7 +118,7 @@ public class HttpInputIntegrationTest extends AbstractWatcherIntegrationTests {
watcherClient.preparePutWatch("_name2")
.source(watchSourceBuilder()
.trigger(schedule(interval(5, IntervalSchedule.Interval.Unit.SECONDS)))
.input(httpInputBuilder)
.input(InputBuilders.httpInput(requestBuilder).addExtractKey("hits.total"))
.condition(scriptCondition("ctx.payload.hits.max_score >= 0")))
.get();

View File

@ -0,0 +1,21 @@
-----BEGIN CERTIFICATE-----
MIIDbTCCAlWgAwIBAgIJAJ+K5mGS3n/AMA0GCSqGSIb3DQEBCwUAMEgxDDAKBgNV
BAoTA29yZzEWMBQGA1UECxMNZWxhc3RpY3NlYXJjaDEgMB4GA1UEAxMXRWxhc3Rp
Y3NlYXJjaCBUZXN0IE5vZGUwHhcNMTQxMjE2MTcwNDQ1WhcNMTgxMjE1MTcwNDQ1
WjBIMQwwCgYDVQQKEwNvcmcxFjAUBgNVBAsTDWVsYXN0aWNzZWFyY2gxIDAeBgNV
BAMTF0VsYXN0aWNzZWFyY2ggVGVzdCBOb2RlMIIBIjANBgkqhkiG9w0BAQEFAAOC
AQ8AMIIBCgKCAQEAzhpW7iwkm+Og+HP7U00nbmh0Hy9Z2Ldp5i8tJSlSQwTxCCvO
rse6jwJQN98Dk1ApaSzimZrlKOotFyPV1L3fnOzJbTp1Yq/VsYP4zJkjWtID0qUf
8Rg8bLhjKAG+ZlLuai5XZqnLkdmqvQeR61VhpXWFm0Om153tWmAiHL18ywY71gXN
EnkeFo9OW4fDqkz6h7NJziYvU6URSKErZDEixk5GIPv9K9hiIfi0KQM6xaHp0d2w
VCyFVC0OUdugz6untURzJVx4U3X1bQcv/o2BoUotWh/5h8o5eeiiv2OGZ1XlO+33
1tweYI4wFjDwnAyHHRr/rk2ZIBiBYGaSzHnuhQIDAQABo1owWDAJBgNVHRMEAjAA
MB0GA1UdDgQWBBTwGg2LF8+mzsvBBWxJKv6VXv3dMTAsBgNVHREEJTAjgglsb2Nh
bGhvc3SHBH8AAAGHEAAAAAAAAAAAAAAAAAAAAAIwDQYJKoZIhvcNAQELBQADggEB
ABP4ufLToJhcUselVxV9LPD5VGPEHGLdIFqsUEix7DMsiNpR76X6a8qNQbZpdbd6
+qPKqoaMgC7znX7qZtCqRbIXTWbudZPxFkcHdiWx3SiALMQYabeUGetClX3sCndU
SUoV8f34i8dJxfNcqhLcsh4zpgxtmwsvs5OLMTBvm0Xo2zUFUjlmrt41pBrWEuq9
nkObc/cr6Syiz3sy4pYVJO1/YwHaZgE/URqjVlari70DR3ES4YnIUnLQajKx2Q0/
gXVgzjbe68KPOUGCz6GYiWq+d4tcWdHzLv1GsaqQ1MD9P21ArfrX4DpzgPDrO6MP
9Ppq5DQGa2q4mz3kipd5RIs=
-----END CERTIFICATE-----