Centralized xcontent parsing of time values
- Renamed `WatcherDateUtils` to `WatcherDateTimeUtils` Original commit: elastic/x-pack-elasticsearch@6b5557058a
This commit is contained in:
parent
e0a70722e0
commit
575208c338
|
@ -19,7 +19,7 @@ import java.io.IOException;
|
|||
import java.util.Locale;
|
||||
|
||||
import static org.elasticsearch.common.joda.time.DateTimeZone.UTC;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateUtils.dateTimeFormatter;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateTimeUtils.dateTimeFormatter;
|
||||
|
||||
/**
|
||||
*
|
||||
|
|
|
@ -18,6 +18,7 @@ import org.elasticsearch.common.xcontent.json.JsonXContent;
|
|||
import org.elasticsearch.watcher.execution.WatchExecutionContext;
|
||||
import org.elasticsearch.watcher.execution.Wid;
|
||||
import org.elasticsearch.watcher.license.LicenseService;
|
||||
import org.elasticsearch.watcher.support.WatcherDateTimeUtils;
|
||||
import org.elasticsearch.watcher.support.clock.Clock;
|
||||
import org.elasticsearch.watcher.actions.throttler.ActionThrottler;
|
||||
import org.elasticsearch.watcher.actions.throttler.Throttler;
|
||||
|
@ -153,10 +154,10 @@ public class ActionWrapper implements ToXContent {
|
|||
if (Transform.Field.TRANSFORM.match(currentFieldName)) {
|
||||
transform = transformRegistry.parse(watchId, parser);
|
||||
} else if (Throttler.Field.THROTTLE_PERIOD.match(currentFieldName)) {
|
||||
if (token == XContentParser.Token.VALUE_NUMBER) {
|
||||
throttlePeriod = new TimeValue(parser.longValue());
|
||||
} else {
|
||||
throw new ActionException("could not parse action [{}/{}]. expected field [{}] to hold a numeric value, but instead found", watchId, actionId, currentFieldName, token);
|
||||
try {
|
||||
throttlePeriod = WatcherDateTimeUtils.parseTimeValue(parser, null);
|
||||
} catch (WatcherDateTimeUtils.ParseException pe) {
|
||||
throw new ActionException("could not parse action [{}/{}]. failed to parse field [{}] as time value", pe, watchId, actionId, currentFieldName);
|
||||
}
|
||||
} else {
|
||||
// it's the type of the action
|
||||
|
|
|
@ -7,10 +7,9 @@ package org.elasticsearch.watcher.actions.throttler;
|
|||
|
||||
import org.elasticsearch.watcher.actions.ActionStatus;
|
||||
import org.elasticsearch.watcher.actions.ActionStatus.AckStatus;
|
||||
import org.elasticsearch.watcher.actions.throttler.Throttler;
|
||||
import org.elasticsearch.watcher.execution.WatchExecutionContext;
|
||||
|
||||
import static org.elasticsearch.watcher.support.WatcherDateUtils.formatDate;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateTimeUtils.formatDate;
|
||||
|
||||
/**
|
||||
*
|
||||
|
|
|
@ -18,7 +18,7 @@ import org.elasticsearch.watcher.condition.Condition;
|
|||
import org.elasticsearch.watcher.condition.ConditionRegistry;
|
||||
import org.elasticsearch.watcher.input.Input;
|
||||
import org.elasticsearch.watcher.input.InputRegistry;
|
||||
import org.elasticsearch.watcher.support.WatcherDateUtils;
|
||||
import org.elasticsearch.watcher.support.WatcherDateTimeUtils;
|
||||
import org.elasticsearch.watcher.transform.Transform;
|
||||
import org.elasticsearch.watcher.transform.TransformRegistry;
|
||||
|
||||
|
@ -72,7 +72,7 @@ public class WatchExecutionResult implements ToXContent {
|
|||
@Override
|
||||
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
builder.startObject();
|
||||
WatcherDateUtils.writeDate(Field.EXECUTION_TIME.getPreferredName(), builder, executionTime);
|
||||
WatcherDateTimeUtils.writeDate(Field.EXECUTION_TIME.getPreferredName(), builder, executionTime);
|
||||
if (inputResult != null) {
|
||||
builder.startObject(Field.INPUT.getPreferredName())
|
||||
.field(inputResult.type(), inputResult, params)
|
||||
|
@ -109,8 +109,8 @@ public class WatchExecutionResult implements ToXContent {
|
|||
currentFieldName = parser.currentName();
|
||||
} else if (Field.EXECUTION_TIME.match(currentFieldName)) {
|
||||
try {
|
||||
executionTime = WatcherDateUtils.parseDate(currentFieldName, parser, UTC);
|
||||
} catch (WatcherDateUtils.ParseException pe) {
|
||||
executionTime = WatcherDateTimeUtils.parseDate(currentFieldName, parser, UTC);
|
||||
} catch (WatcherDateTimeUtils.ParseException pe) {
|
||||
throw new WatcherException("could not parse watch execution [{}]. failed to parse date field [{}]", pe, wid, currentFieldName);
|
||||
}
|
||||
} else if (Field.ACTIONS.match(currentFieldName)) {
|
||||
|
|
|
@ -12,10 +12,14 @@ import org.elasticsearch.common.joda.DateMathParser;
|
|||
import org.elasticsearch.common.joda.FormatDateTimeFormatter;
|
||||
import org.elasticsearch.common.joda.time.DateTime;
|
||||
import org.elasticsearch.common.joda.time.DateTimeZone;
|
||||
import org.elasticsearch.common.joda.time.PeriodType;
|
||||
import org.elasticsearch.common.unit.TimeValue;
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
import org.elasticsearch.common.xcontent.XContentParser;
|
||||
import org.elasticsearch.index.mapper.core.DateFieldMapper;
|
||||
import org.elasticsearch.watcher.WatcherException;
|
||||
import org.elasticsearch.watcher.actions.ActionException;
|
||||
import org.elasticsearch.watcher.rest.action.RestExecuteWatchAction;
|
||||
import org.elasticsearch.watcher.support.clock.Clock;
|
||||
|
||||
import java.io.IOException;
|
||||
|
@ -24,12 +28,12 @@ import java.util.concurrent.TimeUnit;
|
|||
/**
|
||||
*
|
||||
*/
|
||||
public class WatcherDateUtils {
|
||||
public class WatcherDateTimeUtils {
|
||||
|
||||
public static final FormatDateTimeFormatter dateTimeFormatter = DateFieldMapper.Defaults.DATE_TIME_FORMATTER;
|
||||
public static final DateMathParser dateMathParser = new DateMathParser(dateTimeFormatter, TimeUnit.SECONDS);
|
||||
|
||||
private WatcherDateUtils() {
|
||||
private WatcherDateTimeUtils() {
|
||||
}
|
||||
|
||||
public static DateTime parseDate(String dateAsText) {
|
||||
|
@ -116,6 +120,24 @@ public class WatcherDateUtils {
|
|||
return in.readBoolean() ? new DateTime(in.readLong(), timeZone) : null;
|
||||
}
|
||||
|
||||
public static TimeValue parseTimeValue(XContentParser parser, TimeValue defaultValue) throws IOException {
|
||||
return parseTimeValue(parser, TimeUnit.MILLISECONDS, defaultValue);
|
||||
}
|
||||
|
||||
public static TimeValue parseTimeValue(XContentParser parser, TimeUnit defaultTimeUnit, TimeValue defaultValue) throws IOException {
|
||||
XContentParser.Token token = parser.currentToken();
|
||||
if (token == XContentParser.Token.VALUE_NULL) {
|
||||
return defaultValue;
|
||||
}
|
||||
if (token == XContentParser.Token.VALUE_NUMBER) {
|
||||
return new TimeValue(parser.longValue(), defaultTimeUnit);
|
||||
} else if (token == XContentParser.Token.VALUE_STRING) {
|
||||
return TimeValue.parseTimeValue(parser.text(), defaultValue);
|
||||
} else {
|
||||
throw new ParseException("could not parse time value. expected either a string or a numeric value but found [{}] instead", token);
|
||||
}
|
||||
}
|
||||
|
||||
public static class ParseException extends WatcherException {
|
||||
public ParseException(String msg, Throwable cause, Object... args) {
|
||||
super(msg, cause, args);
|
|
@ -25,7 +25,7 @@ import java.lang.reflect.Array;
|
|||
import java.util.*;
|
||||
|
||||
import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateUtils.formatDate;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateTimeUtils.formatDate;
|
||||
|
||||
/**
|
||||
*/
|
||||
|
|
|
@ -10,7 +10,7 @@ import org.elasticsearch.common.joda.time.DateTime;
|
|||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
import org.elasticsearch.common.xcontent.XContentParser;
|
||||
import org.elasticsearch.watcher.WatcherException;
|
||||
import org.elasticsearch.watcher.support.WatcherDateUtils;
|
||||
import org.elasticsearch.watcher.support.WatcherDateTimeUtils;
|
||||
import org.elasticsearch.watcher.support.clock.Clock;
|
||||
import org.elasticsearch.watcher.trigger.TriggerEvent;
|
||||
|
||||
|
@ -47,8 +47,8 @@ public class ScheduleTriggerEvent extends TriggerEvent {
|
|||
@Override
|
||||
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
builder.startObject();
|
||||
WatcherDateUtils.writeDate(Field.TRIGGERED_TIME.getPreferredName(), builder, triggeredTime);
|
||||
WatcherDateUtils.writeDate(Field.SCHEDULED_TIME.getPreferredName(), builder, scheduledTime);
|
||||
WatcherDateTimeUtils.writeDate(Field.TRIGGERED_TIME.getPreferredName(), builder, triggeredTime);
|
||||
WatcherDateTimeUtils.writeDate(Field.SCHEDULED_TIME.getPreferredName(), builder, scheduledTime);
|
||||
return builder.endObject();
|
||||
}
|
||||
|
||||
|
@ -63,15 +63,15 @@ public class ScheduleTriggerEvent extends TriggerEvent {
|
|||
currentFieldName = parser.currentName();
|
||||
} else if (Field.TRIGGERED_TIME.match(currentFieldName)) {
|
||||
try {
|
||||
triggeredTime = WatcherDateUtils.parseDateMath(currentFieldName, parser, UTC, clock);
|
||||
} catch (WatcherDateUtils.ParseException pe) {
|
||||
triggeredTime = WatcherDateTimeUtils.parseDateMath(currentFieldName, parser, UTC, clock);
|
||||
} catch (WatcherDateTimeUtils.ParseException pe) {
|
||||
//Failed to parse as a date try datemath parsing
|
||||
throw new ParseException("could not parse [{}] trigger event for [{}] for watch [{}]. failed to parse date field [{}]", pe, ScheduleTriggerEngine.TYPE, context, watchId, currentFieldName);
|
||||
}
|
||||
} else if (Field.SCHEDULED_TIME.match(currentFieldName)) {
|
||||
try {
|
||||
scheduledTime = WatcherDateUtils.parseDateMath(currentFieldName, parser, UTC, clock);
|
||||
} catch (WatcherDateUtils.ParseException pe) {
|
||||
scheduledTime = WatcherDateTimeUtils.parseDateMath(currentFieldName, parser, UTC, clock);
|
||||
} catch (WatcherDateTimeUtils.ParseException pe) {
|
||||
throw new ParseException("could not parse [{}] trigger event for [{}] for watch [{}]. failed to parse date field [{}]", pe, ScheduleTriggerEngine.TYPE, context, watchId, currentFieldName);
|
||||
}
|
||||
}else {
|
||||
|
|
|
@ -32,6 +32,7 @@ import org.elasticsearch.watcher.condition.always.ExecutableAlwaysCondition;
|
|||
import org.elasticsearch.watcher.input.ExecutableInput;
|
||||
import org.elasticsearch.watcher.input.InputRegistry;
|
||||
import org.elasticsearch.watcher.input.none.ExecutableNoneInput;
|
||||
import org.elasticsearch.watcher.support.WatcherDateTimeUtils;
|
||||
import org.elasticsearch.watcher.support.clock.Clock;
|
||||
import org.elasticsearch.watcher.support.secret.SecretService;
|
||||
import org.elasticsearch.watcher.support.secret.SensitiveXContentParser;
|
||||
|
@ -286,12 +287,19 @@ public class Watch implements TriggerEngine.Job, ToXContent {
|
|||
} else if (Field.TRANSFORM.match(currentFieldName)) {
|
||||
transform = transformRegistry.parse(id, parser);
|
||||
} else if (Field.THROTTLE_PERIOD.match(currentFieldName)) {
|
||||
<<<<<<< HEAD
|
||||
if (token == XContentParser.Token.VALUE_STRING) {
|
||||
throttlePeriod = TimeValue.parseTimeValue(parser.text(), null);
|
||||
} else if (token == XContentParser.Token.VALUE_NUMBER) {
|
||||
throttlePeriod = TimeValue.timeValueMillis(parser.longValue());
|
||||
} else {
|
||||
throw new ParseException("could not parse watch [{}]. expected field [{}] to either be string or numeric, but found [{}] instead", id, currentFieldName, token);
|
||||
=======
|
||||
try {
|
||||
throttlePeriod = WatcherDateTimeUtils.parseTimeValue(parser, null);
|
||||
} catch (WatcherDateTimeUtils.ParseException pe) {
|
||||
throw new ParseException("could not parse watch [{}]. failed to parse time value for field [{}]", pe, id, currentFieldName);
|
||||
>>>>>>> Centralized xcontent parsing of time values
|
||||
}
|
||||
} else if (Field.ACTIONS.match(currentFieldName)) {
|
||||
actions = actionRegistry.parseActions(id, parser);
|
||||
|
|
|
@ -25,7 +25,7 @@ import java.io.IOException;
|
|||
import java.util.Map;
|
||||
|
||||
import static org.elasticsearch.common.joda.time.DateTimeZone.UTC;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateUtils.*;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateTimeUtils.*;
|
||||
|
||||
/**
|
||||
*
|
||||
|
|
|
@ -13,7 +13,7 @@ import org.elasticsearch.watcher.watch.Watch;
|
|||
import org.elasticsearch.watcher.watch.WatchStatus;
|
||||
import org.junit.Test;
|
||||
|
||||
import static org.elasticsearch.watcher.support.WatcherDateUtils.formatDate;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateTimeUtils.formatDate;
|
||||
import static org.elasticsearch.watcher.test.WatcherTestUtils.EMPTY_PAYLOAD;
|
||||
import static org.elasticsearch.watcher.test.WatcherTestUtils.mockExecutionContext;
|
||||
import static org.hamcrest.CoreMatchers.nullValue;
|
||||
|
|
|
@ -0,0 +1,88 @@
|
|||
/*
|
||||
* 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;
|
||||
|
||||
import com.carrotsearch.randomizedtesting.annotations.Repeat;
|
||||
import org.elasticsearch.common.collect.ImmutableMap;
|
||||
import org.elasticsearch.common.unit.TimeValue;
|
||||
import org.elasticsearch.common.xcontent.XContentParser;
|
||||
import org.elasticsearch.test.ElasticsearchTestCase;
|
||||
import org.junit.Test;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder;
|
||||
import static org.elasticsearch.watcher.test.WatcherTestUtils.xContentParser;
|
||||
import static org.hamcrest.CoreMatchers.nullValue;
|
||||
import static org.hamcrest.CoreMatchers.sameInstance;
|
||||
import static org.hamcrest.Matchers.is;
|
||||
import static org.hamcrest.Matchers.notNullValue;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
public class WatcherDateTimeUtilsTests extends ElasticsearchTestCase {
|
||||
|
||||
@Test @Repeat(iterations = 20)
|
||||
public void testParseTimeValue_Numeric() throws Exception {
|
||||
TimeValue value = new TimeValue(randomInt(100), randomFrom(TimeUnit.values()));
|
||||
|
||||
XContentParser parser = xContentParser(jsonBuilder().startObject().field("value", value.getMillis()).endObject());
|
||||
parser.nextToken(); // start object
|
||||
parser.nextToken(); // field name
|
||||
parser.nextToken(); // value
|
||||
|
||||
TimeValue parsed = WatcherDateTimeUtils.parseTimeValue(parser, null);
|
||||
assertThat(parsed, notNullValue());
|
||||
assertThat(parsed.millis(), is(value.millis()));
|
||||
}
|
||||
|
||||
@Test @Repeat(iterations = 10)
|
||||
public void testParseTimeValue_String() throws Exception {
|
||||
ImmutableMap<String, TimeValue> values = ImmutableMap.<String, TimeValue>builder()
|
||||
.put("5s", TimeValue.timeValueSeconds(5))
|
||||
.put("5m", TimeValue.timeValueMinutes(5))
|
||||
.put("5h", TimeValue.timeValueHours(5))
|
||||
.put("5", TimeValue.timeValueMillis(5))
|
||||
.build();
|
||||
|
||||
String key = randomFrom(values.keySet().toArray(new String[values.size()]));
|
||||
|
||||
XContentParser parser = xContentParser(jsonBuilder().startObject().field("value", key).endObject());
|
||||
parser.nextToken(); // start object
|
||||
parser.nextToken(); // field name
|
||||
parser.nextToken(); // value
|
||||
|
||||
TimeValue parsed = WatcherDateTimeUtils.parseTimeValue(parser, null);
|
||||
assertThat(parsed, notNullValue());
|
||||
assertThat(parsed.millis(), is(values.get(key).millis()));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testParseTimeValue_Null() throws Exception {
|
||||
XContentParser parser = xContentParser(jsonBuilder().startObject().nullField("value").endObject());
|
||||
parser.nextToken(); // start object
|
||||
parser.nextToken(); // field name
|
||||
parser.nextToken(); // value
|
||||
|
||||
TimeValue parsed = WatcherDateTimeUtils.parseTimeValue(parser, null);
|
||||
assertThat(parsed, nullValue());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testParseTimeValue_Null_DefaultValue() throws Exception {
|
||||
XContentParser parser = xContentParser(jsonBuilder().startObject().nullField("value").endObject());
|
||||
parser.nextToken(); // start object
|
||||
parser.nextToken(); // field name
|
||||
parser.nextToken(); // value
|
||||
|
||||
TimeValue defaultValue = new TimeValue(randomInt(100), randomFrom(TimeUnit.values()));
|
||||
|
||||
TimeValue parsed = WatcherDateTimeUtils.parseTimeValue(parser, defaultValue);
|
||||
assertThat(parsed, notNullValue());
|
||||
assertThat(parsed, sameInstance(defaultValue));
|
||||
}
|
||||
}
|
|
@ -27,7 +27,7 @@ import java.io.IOException;
|
|||
import java.util.*;
|
||||
|
||||
import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateUtils.formatDate;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateTimeUtils.formatDate;
|
||||
import static org.elasticsearch.watcher.support.WatcherUtils.DEFAULT_INDICES_OPTIONS;
|
||||
import static org.elasticsearch.watcher.support.WatcherUtils.flattenModel;
|
||||
import static org.elasticsearch.watcher.test.WatcherTestUtils.getRandomSupportedSearchType;
|
||||
|
|
|
@ -16,6 +16,7 @@ import org.elasticsearch.common.logging.ESLogger;
|
|||
import org.elasticsearch.common.settings.ImmutableSettings;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.common.unit.TimeValue;
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
import org.elasticsearch.common.xcontent.XContentHelper;
|
||||
import org.elasticsearch.common.xcontent.XContentParser;
|
||||
import org.elasticsearch.common.xcontent.XContentType;
|
||||
|
@ -89,6 +90,10 @@ public final class WatcherTestUtils {
|
|||
private WatcherTestUtils() {
|
||||
}
|
||||
|
||||
public static XContentParser xContentParser(XContentBuilder builder) throws IOException {
|
||||
return builder.contentType().xContent().createParser(builder.bytes());
|
||||
}
|
||||
|
||||
public static SearchRequest newInputSearchRequest(String... indices) {
|
||||
SearchRequest request = new SearchRequest(indices);
|
||||
request.indicesOptions(WatcherUtils.DEFAULT_INDICES_OPTIONS);
|
||||
|
|
|
@ -57,7 +57,7 @@ import static org.elasticsearch.index.query.FilterBuilders.*;
|
|||
import static org.elasticsearch.index.query.QueryBuilders.*;
|
||||
import static org.elasticsearch.search.builder.SearchSourceBuilder.searchSource;
|
||||
import static org.elasticsearch.test.ElasticsearchIntegrationTest.Scope.SUITE;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateUtils.parseDate;
|
||||
import static org.elasticsearch.watcher.support.WatcherDateTimeUtils.parseDate;
|
||||
import static org.elasticsearch.watcher.test.WatcherTestUtils.*;
|
||||
import static org.hamcrest.Matchers.*;
|
||||
|
||||
|
|
Loading…
Reference in New Issue