Merge branch 'master' into feature/aggs-refactoring
# Conflicts: # core/src/main/java/org/elasticsearch/common/io/stream/StreamInput.java # core/src/main/java/org/elasticsearch/common/io/stream/StreamOutput.java
This commit is contained in:
commit
e6f9cbce8f
|
@ -309,9 +309,10 @@ class BuildPlugin implements Plugin<Project> {
|
|||
/*
|
||||
* -path because gradle will send in paths that don't always exist.
|
||||
* -missing because we have tons of missing @returns and @param.
|
||||
* -serial because we don't use java serialization.
|
||||
*/
|
||||
// don't even think about passing args with -J-xxx, oracle will ask you to submit a bug report :)
|
||||
options.compilerArgs << '-Werror' << '-Xlint:all,-path' << '-Xdoclint:all' << '-Xdoclint:-missing'
|
||||
options.compilerArgs << '-Werror' << '-Xlint:all,-path,-serial' << '-Xdoclint:all' << '-Xdoclint:-missing'
|
||||
// compile with compact 3 profile by default
|
||||
// NOTE: this is just a compile time check: does not replace testing with a compact3 JRE
|
||||
if (project.compactProfile != 'full') {
|
||||
|
|
|
@ -62,6 +62,9 @@ public class ForbiddenPatternsTask extends DefaultTask {
|
|||
patterns.put('nocommit', /nocommit/)
|
||||
patterns.put('tab', /\t/)
|
||||
patterns.put('wildcard imports', /^\s*import.*\.\*/)
|
||||
// We don't use Java serialization so we fail if it looks like we're trying to.
|
||||
patterns.put('declares serialVersionUID', /serialVersionUID/)
|
||||
patterns.put('references Serializable', /java\.io\.Serializable/)
|
||||
|
||||
inputs.property("excludes", filesFilter.excludes)
|
||||
inputs.property("rules", patterns)
|
||||
|
|
|
@ -23,6 +23,8 @@ import org.gradle.api.Project
|
|||
import org.gradle.api.file.FileCollection
|
||||
import org.gradle.api.tasks.Input
|
||||
|
||||
import java.time.LocalDateTime
|
||||
|
||||
/** Configuration for an elasticsearch cluster, used for integration tests. */
|
||||
class ClusterConfiguration {
|
||||
|
||||
|
@ -55,10 +57,12 @@ class ClusterConfiguration {
|
|||
@Input
|
||||
Closure waitCondition = { NodeInfo node, AntBuilder ant ->
|
||||
File tmpFile = new File(node.cwd, 'wait.success')
|
||||
ant.echo(message: "[${LocalDateTime.now()}] Waiting for elasticsearch node ${node.httpUri()}", level: "info")
|
||||
ant.get(src: "http://${node.httpUri()}",
|
||||
dest: tmpFile.toString(),
|
||||
ignoreerrors: true, // do not fail on error, so logging buffers can be flushed by the wait task
|
||||
retries: 10)
|
||||
ant.echo(message: "[${LocalDateTime.now()}] Finished waiting for elasticsearch node ${node.httpUri()}. Reachable? ${tmpFile.exists()}", level: "info")
|
||||
return tmpFile.exists()
|
||||
}
|
||||
|
||||
|
|
|
@ -102,8 +102,8 @@ if (isEclipse) {
|
|||
}
|
||||
}
|
||||
|
||||
compileJava.options.compilerArgs << "-Xlint:-cast,-deprecation,-rawtypes,-serial,-try,-unchecked"
|
||||
compileTestJava.options.compilerArgs << "-Xlint:-cast,-deprecation,-rawtypes,-serial,-try,-unchecked"
|
||||
compileJava.options.compilerArgs << "-Xlint:-cast,-deprecation,-rawtypes,-try,-unchecked"
|
||||
compileTestJava.options.compilerArgs << "-Xlint:-cast,-deprecation,-rawtypes,-try,-unchecked"
|
||||
|
||||
forbiddenPatterns {
|
||||
exclude '**/*.json'
|
||||
|
|
|
@ -36,6 +36,7 @@ import org.apache.lucene.util.InPlaceMergeSorter;
|
|||
import org.apache.lucene.util.ToStringUtils;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
@ -326,7 +327,7 @@ public abstract class BlendedTermQuery extends Query {
|
|||
}
|
||||
if ((maxTermFrequency >= 1f && docFreqs[i] > maxTermFrequency)
|
||||
|| (docFreqs[i] > (int) Math.ceil(maxTermFrequency
|
||||
* (float) maxDoc))) {
|
||||
* maxDoc))) {
|
||||
highBuilder.add(query, BooleanClause.Occur.SHOULD);
|
||||
} else {
|
||||
lowBuilder.add(query, BooleanClause.Occur.SHOULD);
|
||||
|
@ -362,15 +363,15 @@ public abstract class BlendedTermQuery extends Query {
|
|||
return new BlendedTermQuery(terms, boosts) {
|
||||
@Override
|
||||
protected Query topLevelQuery(Term[] terms, TermContext[] ctx, int[] docFreqs, int maxDoc) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(tieBreakerMultiplier);
|
||||
List<Query> queries = new ArrayList<>(ctx.length);
|
||||
for (int i = 0; i < terms.length; i++) {
|
||||
Query query = new TermQuery(terms[i], ctx[i]);
|
||||
if (boosts != null && boosts[i] != 1f) {
|
||||
query = new BoostQuery(query, boosts[i]);
|
||||
}
|
||||
disMaxQuery.add(query);
|
||||
queries.add(query);
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, tieBreakerMultiplier);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
@ -142,19 +142,19 @@ public class MapperQueryParser extends QueryParser {
|
|||
return getFieldQuerySingle(fields.iterator().next(), queryText, quoted);
|
||||
}
|
||||
if (settings.useDisMax()) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(settings.tieBreaker());
|
||||
List<Query> queries = new ArrayList<>();
|
||||
boolean added = false;
|
||||
for (String mField : fields) {
|
||||
Query q = getFieldQuerySingle(mField, queryText, quoted);
|
||||
if (q != null) {
|
||||
added = true;
|
||||
disMaxQuery.add(applyBoost(mField, q));
|
||||
queries.add(applyBoost(mField, q));
|
||||
}
|
||||
}
|
||||
if (!added) {
|
||||
return null;
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, settings.tieBreaker());
|
||||
} else {
|
||||
List<BooleanClause> clauses = new ArrayList<>();
|
||||
for (String mField : fields) {
|
||||
|
@ -242,20 +242,20 @@ public class MapperQueryParser extends QueryParser {
|
|||
Collection<String> fields = extractMultiFields(field);
|
||||
if (fields != null) {
|
||||
if (settings.useDisMax()) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(settings.tieBreaker());
|
||||
List<Query> queries = new ArrayList<>();
|
||||
boolean added = false;
|
||||
for (String mField : fields) {
|
||||
Query q = super.getFieldQuery(mField, queryText, slop);
|
||||
if (q != null) {
|
||||
added = true;
|
||||
q = applySlop(q, slop);
|
||||
disMaxQuery.add(applyBoost(mField, q));
|
||||
queries.add(applyBoost(mField, q));
|
||||
}
|
||||
}
|
||||
if (!added) {
|
||||
return null;
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, settings.tieBreaker());
|
||||
} else {
|
||||
List<BooleanClause> clauses = new ArrayList<>();
|
||||
for (String mField : fields) {
|
||||
|
@ -295,19 +295,19 @@ public class MapperQueryParser extends QueryParser {
|
|||
}
|
||||
|
||||
if (settings.useDisMax()) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(settings.tieBreaker());
|
||||
List<Query> queries = new ArrayList<>();
|
||||
boolean added = false;
|
||||
for (String mField : fields) {
|
||||
Query q = getRangeQuerySingle(mField, part1, part2, startInclusive, endInclusive);
|
||||
if (q != null) {
|
||||
added = true;
|
||||
disMaxQuery.add(applyBoost(mField, q));
|
||||
queries.add(applyBoost(mField, q));
|
||||
}
|
||||
}
|
||||
if (!added) {
|
||||
return null;
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, settings.tieBreaker());
|
||||
} else {
|
||||
List<BooleanClause> clauses = new ArrayList<>();
|
||||
for (String mField : fields) {
|
||||
|
@ -359,19 +359,19 @@ public class MapperQueryParser extends QueryParser {
|
|||
return getFuzzyQuerySingle(fields.iterator().next(), termStr, minSimilarity);
|
||||
}
|
||||
if (settings.useDisMax()) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(settings.tieBreaker());
|
||||
List<Query> queries = new ArrayList<>();
|
||||
boolean added = false;
|
||||
for (String mField : fields) {
|
||||
Query q = getFuzzyQuerySingle(mField, termStr, minSimilarity);
|
||||
if (q != null) {
|
||||
added = true;
|
||||
disMaxQuery.add(applyBoost(mField, q));
|
||||
queries.add(applyBoost(mField, q));
|
||||
}
|
||||
}
|
||||
if (!added) {
|
||||
return null;
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, settings.tieBreaker());
|
||||
} else {
|
||||
List<BooleanClause> clauses = new ArrayList<>();
|
||||
for (String mField : fields) {
|
||||
|
@ -422,19 +422,19 @@ public class MapperQueryParser extends QueryParser {
|
|||
return getPrefixQuerySingle(fields.iterator().next(), termStr);
|
||||
}
|
||||
if (settings.useDisMax()) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(settings.tieBreaker());
|
||||
List<Query> queries = new ArrayList<>();
|
||||
boolean added = false;
|
||||
for (String mField : fields) {
|
||||
Query q = getPrefixQuerySingle(mField, termStr);
|
||||
if (q != null) {
|
||||
added = true;
|
||||
disMaxQuery.add(applyBoost(mField, q));
|
||||
queries.add(applyBoost(mField, q));
|
||||
}
|
||||
}
|
||||
if (!added) {
|
||||
return null;
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, settings.tieBreaker());
|
||||
} else {
|
||||
List<BooleanClause> clauses = new ArrayList<>();
|
||||
for (String mField : fields) {
|
||||
|
@ -552,19 +552,19 @@ public class MapperQueryParser extends QueryParser {
|
|||
return getWildcardQuerySingle(fields.iterator().next(), termStr);
|
||||
}
|
||||
if (settings.useDisMax()) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(settings.tieBreaker());
|
||||
List<Query> queries = new ArrayList<>();
|
||||
boolean added = false;
|
||||
for (String mField : fields) {
|
||||
Query q = getWildcardQuerySingle(mField, termStr);
|
||||
if (q != null) {
|
||||
added = true;
|
||||
disMaxQuery.add(applyBoost(mField, q));
|
||||
queries.add(applyBoost(mField, q));
|
||||
}
|
||||
}
|
||||
if (!added) {
|
||||
return null;
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, settings.tieBreaker());
|
||||
} else {
|
||||
List<BooleanClause> clauses = new ArrayList<>();
|
||||
for (String mField : fields) {
|
||||
|
@ -681,19 +681,19 @@ public class MapperQueryParser extends QueryParser {
|
|||
return getRegexpQuerySingle(fields.iterator().next(), termStr);
|
||||
}
|
||||
if (settings.useDisMax()) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(settings.tieBreaker());
|
||||
List<Query> queries = new ArrayList<>();
|
||||
boolean added = false;
|
||||
for (String mField : fields) {
|
||||
Query q = getRegexpQuerySingle(mField, termStr);
|
||||
if (q != null) {
|
||||
added = true;
|
||||
disMaxQuery.add(applyBoost(mField, q));
|
||||
queries.add(applyBoost(mField, q));
|
||||
}
|
||||
}
|
||||
if (!added) {
|
||||
return null;
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, settings.tieBreaker());
|
||||
} else {
|
||||
List<BooleanClause> clauses = new ArrayList<>();
|
||||
for (String mField : fields) {
|
||||
|
|
|
@ -22,15 +22,15 @@ package org.elasticsearch;
|
|||
import java.security.BasicPermission;
|
||||
|
||||
/**
|
||||
* Elasticsearch-specific permission to check before entering
|
||||
* {@code AccessController.doPrivileged()} blocks.
|
||||
* Elasticsearch-specific permission to check before entering
|
||||
* {@code AccessController.doPrivileged()} blocks.
|
||||
* <p>
|
||||
* We try to avoid these blocks in our code and keep security simple,
|
||||
* but we need them for a few special places to contain hacks for third
|
||||
* We try to avoid these blocks in our code and keep security simple,
|
||||
* but we need them for a few special places to contain hacks for third
|
||||
* party code, or dangerous things used by scripting engines.
|
||||
* <p>
|
||||
* All normal code has this permission, but checking this before truncating the stack
|
||||
* prevents unprivileged code (e.g. scripts), which do not have it, from gaining elevated
|
||||
* prevents unprivileged code (e.g. scripts), which do not have it, from gaining elevated
|
||||
* privileges.
|
||||
* <p>
|
||||
* In other words, don't do this:
|
||||
|
@ -57,9 +57,6 @@ import java.security.BasicPermission;
|
|||
* </code></pre>
|
||||
*/
|
||||
public final class SpecialPermission extends BasicPermission {
|
||||
|
||||
private static final long serialVersionUID = -4129500096157408168L;
|
||||
|
||||
/**
|
||||
* Creates a new SpecialPermision object.
|
||||
*/
|
||||
|
@ -68,11 +65,11 @@ public final class SpecialPermission extends BasicPermission {
|
|||
// but let's just keep it simple if we can.
|
||||
super("*");
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Creates a new SpecialPermission object.
|
||||
* This constructor exists for use by the {@code Policy} object to instantiate new Permission objects.
|
||||
*
|
||||
*
|
||||
* @param name ignored
|
||||
* @param actions ignored
|
||||
*/
|
||||
|
|
|
@ -28,13 +28,13 @@ import java.io.IOException;
|
|||
/**
|
||||
*
|
||||
*/
|
||||
public abstract class ActionRequest<T extends ActionRequest> extends TransportRequest {
|
||||
public abstract class ActionRequest<Request extends ActionRequest<Request>> extends TransportRequest {
|
||||
|
||||
public ActionRequest() {
|
||||
super();
|
||||
}
|
||||
|
||||
protected ActionRequest(ActionRequest request) {
|
||||
protected ActionRequest(ActionRequest<?> request) {
|
||||
super(request);
|
||||
// this does not set the listenerThreaded API, if needed, its up to the caller to set it
|
||||
// since most times, we actually want it to not be threaded...
|
||||
|
|
|
@ -146,7 +146,7 @@ public class TransportNodesSnapshotsStatus extends TransportNodesAction<Transpor
|
|||
public Request() {
|
||||
}
|
||||
|
||||
public Request(ActionRequest request, String[] nodesIds) {
|
||||
public Request(ActionRequest<?> request, String[] nodesIds) {
|
||||
super(request, nodesIds);
|
||||
}
|
||||
|
||||
|
@ -180,6 +180,7 @@ public class TransportNodesSnapshotsStatus extends TransportNodesAction<Transpor
|
|||
this.failures = failures;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FailedNodeException[] failures() {
|
||||
return failures;
|
||||
}
|
||||
|
|
|
@ -35,7 +35,7 @@ public class GetAliasesRequest extends MasterNodeReadRequest<GetAliasesRequest>
|
|||
private String[] indices = Strings.EMPTY_ARRAY;
|
||||
private String[] aliases = Strings.EMPTY_ARRAY;
|
||||
|
||||
private IndicesOptions indicesOptions = IndicesOptions.strictExpandOpen();
|
||||
private IndicesOptions indicesOptions = IndicesOptions.strictExpand();
|
||||
|
||||
public GetAliasesRequest(String[] aliases) {
|
||||
this.aliases = aliases;
|
||||
|
|
|
@ -184,11 +184,10 @@ public class TransportValidateQueryAction extends TransportBroadcastAction<Valid
|
|||
searchContext.preProcess();
|
||||
|
||||
valid = true;
|
||||
if (request.explain()) {
|
||||
explanation = searchContext.parsedQuery().query().toString();
|
||||
}
|
||||
if (request.rewrite()) {
|
||||
explanation = getRewrittenQuery(searcher.searcher(), searchContext.query());
|
||||
} else if (request.explain()) {
|
||||
explanation = searchContext.filteredQuery().query().toString();
|
||||
}
|
||||
} catch (QueryShardException|ParsingException e) {
|
||||
valid = false;
|
||||
|
|
|
@ -432,7 +432,7 @@ public class SearchRequestBuilder extends ActionRequestBuilder<SearchRequest, Se
|
|||
* @return this for chaining
|
||||
*/
|
||||
public SearchRequestBuilder addRescorer(RescoreBuilder.Rescorer rescorer) {
|
||||
sourceBuilder().addRescorer(new RescoreBuilder().rescorer(rescorer));
|
||||
sourceBuilder().addRescorer(new RescoreBuilder(rescorer));
|
||||
return this;
|
||||
}
|
||||
|
||||
|
@ -444,7 +444,7 @@ public class SearchRequestBuilder extends ActionRequestBuilder<SearchRequest, Se
|
|||
* @return this for chaining
|
||||
*/
|
||||
public SearchRequestBuilder addRescorer(RescoreBuilder.Rescorer rescorer, int window) {
|
||||
sourceBuilder().addRescorer(new RescoreBuilder().rescorer(rescorer).windowSize(window));
|
||||
sourceBuilder().addRescorer(new RescoreBuilder(rescorer).windowSize(window));
|
||||
return this;
|
||||
}
|
||||
|
||||
|
|
|
@ -31,7 +31,7 @@ import java.io.IOException;
|
|||
/**
|
||||
*
|
||||
*/
|
||||
public class BroadcastRequest<T extends BroadcastRequest> extends ActionRequest<T> implements IndicesRequest.Replaceable {
|
||||
public class BroadcastRequest<Request extends BroadcastRequest<Request>> extends ActionRequest<Request> implements IndicesRequest.Replaceable {
|
||||
|
||||
protected String[] indices;
|
||||
private IndicesOptions indicesOptions = IndicesOptions.strictExpandOpenAndForbidClosed();
|
||||
|
@ -40,7 +40,7 @@ public class BroadcastRequest<T extends BroadcastRequest> extends ActionRequest<
|
|||
|
||||
}
|
||||
|
||||
protected BroadcastRequest(ActionRequest originalRequest) {
|
||||
protected BroadcastRequest(ActionRequest<?> originalRequest) {
|
||||
super(originalRequest);
|
||||
}
|
||||
|
||||
|
@ -55,9 +55,9 @@ public class BroadcastRequest<T extends BroadcastRequest> extends ActionRequest<
|
|||
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public final T indices(String... indices) {
|
||||
public final Request indices(String... indices) {
|
||||
this.indices = indices;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -71,9 +71,9 @@ public class BroadcastRequest<T extends BroadcastRequest> extends ActionRequest<
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T indicesOptions(IndicesOptions indicesOptions) {
|
||||
public final Request indicesOptions(IndicesOptions indicesOptions) {
|
||||
this.indicesOptions = indicesOptions;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -33,7 +33,7 @@ import static org.elasticsearch.common.unit.TimeValue.timeValueSeconds;
|
|||
* Abstract class that allows to mark action requests that support acknowledgements.
|
||||
* Facilitates consistency across different api.
|
||||
*/
|
||||
public abstract class AcknowledgedRequest<T extends MasterNodeRequest> extends MasterNodeRequest<T> implements AckedRequest {
|
||||
public abstract class AcknowledgedRequest<Request extends MasterNodeRequest<Request>> extends MasterNodeRequest<Request> implements AckedRequest {
|
||||
|
||||
public static final TimeValue DEFAULT_ACK_TIMEOUT = timeValueSeconds(30);
|
||||
|
||||
|
@ -42,7 +42,7 @@ public abstract class AcknowledgedRequest<T extends MasterNodeRequest> extends M
|
|||
protected AcknowledgedRequest() {
|
||||
}
|
||||
|
||||
protected AcknowledgedRequest(ActionRequest request) {
|
||||
protected AcknowledgedRequest(ActionRequest<?> request) {
|
||||
super(request);
|
||||
}
|
||||
|
||||
|
@ -52,9 +52,9 @@ public abstract class AcknowledgedRequest<T extends MasterNodeRequest> extends M
|
|||
* @return the request itself
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(String timeout) {
|
||||
public final Request timeout(String timeout) {
|
||||
this.timeout = TimeValue.parseTimeValue(timeout, this.timeout, getClass().getSimpleName() + ".timeout");
|
||||
return (T)this;
|
||||
return (Request)this;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -63,9 +63,9 @@ public abstract class AcknowledgedRequest<T extends MasterNodeRequest> extends M
|
|||
* @return the request itself
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(TimeValue timeout) {
|
||||
public final Request timeout(TimeValue timeout) {
|
||||
this.timeout = timeout;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -27,14 +27,14 @@ import java.io.IOException;
|
|||
/**
|
||||
* Base request for master based read operations that allows to read the cluster state from the local node if needed
|
||||
*/
|
||||
public abstract class MasterNodeReadRequest<T extends MasterNodeReadRequest> extends MasterNodeRequest<T> {
|
||||
public abstract class MasterNodeReadRequest<Request extends MasterNodeReadRequest<Request>> extends MasterNodeRequest<Request> {
|
||||
|
||||
protected boolean local = false;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T local(boolean local) {
|
||||
public final Request local(boolean local) {
|
||||
this.local = local;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
public final boolean local() {
|
||||
|
|
|
@ -29,7 +29,7 @@ import java.io.IOException;
|
|||
/**
|
||||
* A based request for master based operation.
|
||||
*/
|
||||
public abstract class MasterNodeRequest<T extends MasterNodeRequest> extends ActionRequest<T> {
|
||||
public abstract class MasterNodeRequest<Request extends MasterNodeRequest<Request>> extends ActionRequest<Request> {
|
||||
|
||||
public static final TimeValue DEFAULT_MASTER_NODE_TIMEOUT = TimeValue.timeValueSeconds(30);
|
||||
|
||||
|
@ -39,7 +39,7 @@ public abstract class MasterNodeRequest<T extends MasterNodeRequest> extends Act
|
|||
|
||||
}
|
||||
|
||||
protected MasterNodeRequest(ActionRequest request) {
|
||||
protected MasterNodeRequest(ActionRequest<?> request) {
|
||||
super(request);
|
||||
}
|
||||
|
||||
|
@ -47,15 +47,15 @@ public abstract class MasterNodeRequest<T extends MasterNodeRequest> extends Act
|
|||
* A timeout value in case the master has not been discovered yet or disconnected.
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T masterNodeTimeout(TimeValue timeout) {
|
||||
public final Request masterNodeTimeout(TimeValue timeout) {
|
||||
this.masterNodeTimeout = timeout;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
/**
|
||||
* A timeout value in case the master has not been discovered yet or disconnected.
|
||||
*/
|
||||
public final T masterNodeTimeout(String timeout) {
|
||||
public final Request masterNodeTimeout(String timeout) {
|
||||
return masterNodeTimeout(TimeValue.parseTimeValue(timeout, null, getClass().getSimpleName() + ".masterNodeTimeout"));
|
||||
}
|
||||
|
||||
|
|
|
@ -30,30 +30,30 @@ import java.io.IOException;
|
|||
|
||||
/**
|
||||
*/
|
||||
public abstract class ClusterInfoRequest<T extends ClusterInfoRequest> extends MasterNodeReadRequest<T> implements IndicesRequest.Replaceable {
|
||||
public abstract class ClusterInfoRequest<Request extends ClusterInfoRequest<Request>> extends MasterNodeReadRequest<Request> implements IndicesRequest.Replaceable {
|
||||
|
||||
private String[] indices = Strings.EMPTY_ARRAY;
|
||||
private String[] types = Strings.EMPTY_ARRAY;
|
||||
|
||||
private IndicesOptions indicesOptions = IndicesOptions.strictExpandOpen();
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public T indices(String... indices) {
|
||||
@SuppressWarnings("unchecked")
|
||||
public Request indices(String... indices) {
|
||||
this.indices = indices;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public T types(String... types) {
|
||||
public Request types(String... types) {
|
||||
this.types = types;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public T indicesOptions(IndicesOptions indicesOptions) {
|
||||
public Request indicesOptions(IndicesOptions indicesOptions) {
|
||||
this.indicesOptions = indicesOptions;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -31,7 +31,7 @@ import java.io.IOException;
|
|||
/**
|
||||
*
|
||||
*/
|
||||
public abstract class BaseNodesRequest<T extends BaseNodesRequest> extends ActionRequest<T> {
|
||||
public abstract class BaseNodesRequest<Request extends BaseNodesRequest<Request>> extends ActionRequest<Request> {
|
||||
|
||||
public static String[] ALL_NODES = Strings.EMPTY_ARRAY;
|
||||
|
||||
|
@ -43,7 +43,7 @@ public abstract class BaseNodesRequest<T extends BaseNodesRequest> extends Actio
|
|||
|
||||
}
|
||||
|
||||
protected BaseNodesRequest(ActionRequest request, String... nodesIds) {
|
||||
protected BaseNodesRequest(ActionRequest<?> request, String... nodesIds) {
|
||||
super(request);
|
||||
this.nodesIds = nodesIds;
|
||||
}
|
||||
|
@ -57,9 +57,9 @@ public abstract class BaseNodesRequest<T extends BaseNodesRequest> extends Actio
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T nodesIds(String... nodesIds) {
|
||||
public final Request nodesIds(String... nodesIds) {
|
||||
this.nodesIds = nodesIds;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
public TimeValue timeout() {
|
||||
|
@ -67,15 +67,15 @@ public abstract class BaseNodesRequest<T extends BaseNodesRequest> extends Actio
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(TimeValue timeout) {
|
||||
public final Request timeout(TimeValue timeout) {
|
||||
this.timeout = timeout;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(String timeout) {
|
||||
public final Request timeout(String timeout) {
|
||||
this.timeout = TimeValue.parseTimeValue(timeout, null, getClass().getSimpleName() + ".timeout");
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -38,7 +38,7 @@ import static org.elasticsearch.action.ValidateActions.addValidationError;
|
|||
/**
|
||||
*
|
||||
*/
|
||||
public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequest<T> implements IndicesRequest {
|
||||
public class ReplicationRequest<Request extends ReplicationRequest<Request>> extends ActionRequest<Request> implements IndicesRequest {
|
||||
|
||||
public static final TimeValue DEFAULT_TIMEOUT = new TimeValue(1, TimeUnit.MINUTES);
|
||||
|
||||
|
@ -61,14 +61,14 @@ public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequ
|
|||
/**
|
||||
* Creates a new request that inherits headers and context from the request provided as argument.
|
||||
*/
|
||||
public ReplicationRequest(ActionRequest request) {
|
||||
public ReplicationRequest(ActionRequest<?> request) {
|
||||
super(request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new request with resolved shard id
|
||||
*/
|
||||
public ReplicationRequest(ActionRequest request, ShardId shardId) {
|
||||
public ReplicationRequest(ActionRequest<?> request, ShardId shardId) {
|
||||
super(request);
|
||||
this.index = shardId.getIndex();
|
||||
this.shardId = shardId;
|
||||
|
@ -77,7 +77,7 @@ public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequ
|
|||
/**
|
||||
* Copy constructor that creates a new request that is a copy of the one provided as an argument.
|
||||
*/
|
||||
protected ReplicationRequest(T request) {
|
||||
protected ReplicationRequest(Request request) {
|
||||
this(request, request);
|
||||
}
|
||||
|
||||
|
@ -85,7 +85,7 @@ public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequ
|
|||
* Copy constructor that creates a new request that is a copy of the one provided as an argument.
|
||||
* The new request will inherit though headers and context from the original request that caused it.
|
||||
*/
|
||||
protected ReplicationRequest(T request, ActionRequest originalRequest) {
|
||||
protected ReplicationRequest(Request request, ActionRequest<?> originalRequest) {
|
||||
super(originalRequest);
|
||||
this.timeout = request.timeout();
|
||||
this.index = request.index();
|
||||
|
@ -96,15 +96,15 @@ public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequ
|
|||
* A timeout to wait if the index operation can't be performed immediately. Defaults to <tt>1m</tt>.
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(TimeValue timeout) {
|
||||
public final Request timeout(TimeValue timeout) {
|
||||
this.timeout = timeout;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
/**
|
||||
* A timeout to wait if the index operation can't be performed immediately. Defaults to <tt>1m</tt>.
|
||||
*/
|
||||
public final T timeout(String timeout) {
|
||||
public final Request timeout(String timeout) {
|
||||
return timeout(TimeValue.parseTimeValue(timeout, null, getClass().getSimpleName() + ".timeout"));
|
||||
}
|
||||
|
||||
|
@ -117,9 +117,9 @@ public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequ
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T index(String index) {
|
||||
public final Request index(String index) {
|
||||
this.index = index;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -150,9 +150,9 @@ public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequ
|
|||
* Sets the consistency level of write. Defaults to {@link org.elasticsearch.action.WriteConsistencyLevel#DEFAULT}
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T consistencyLevel(WriteConsistencyLevel consistencyLevel) {
|
||||
public final Request consistencyLevel(WriteConsistencyLevel consistencyLevel) {
|
||||
this.consistencyLevel = consistencyLevel;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -195,9 +195,10 @@ public class ReplicationRequest<T extends ReplicationRequest> extends ActionRequ
|
|||
* Sets the target shard id for the request. The shard id is set when a
|
||||
* index/delete request is resolved by the transport action
|
||||
*/
|
||||
public T setShardId(ShardId shardId) {
|
||||
@SuppressWarnings("unchecked")
|
||||
public Request setShardId(ShardId shardId) {
|
||||
this.shardId = shardId;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -34,7 +34,8 @@ import java.util.concurrent.TimeUnit;
|
|||
/**
|
||||
*
|
||||
*/
|
||||
public abstract class InstanceShardOperationRequest<T extends InstanceShardOperationRequest> extends ActionRequest<T> implements IndicesRequest {
|
||||
public abstract class InstanceShardOperationRequest<Request extends InstanceShardOperationRequest<Request>> extends ActionRequest<Request>
|
||||
implements IndicesRequest {
|
||||
|
||||
public static final TimeValue DEFAULT_TIMEOUT = new TimeValue(1, TimeUnit.MINUTES);
|
||||
|
||||
|
@ -77,9 +78,9 @@ public abstract class InstanceShardOperationRequest<T extends InstanceShardOpera
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T index(String index) {
|
||||
public final Request index(String index) {
|
||||
this.index = index;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
public TimeValue timeout() {
|
||||
|
@ -90,15 +91,15 @@ public abstract class InstanceShardOperationRequest<T extends InstanceShardOpera
|
|||
* A timeout to wait if the index operation can't be performed immediately. Defaults to <tt>1m</tt>.
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(TimeValue timeout) {
|
||||
public final Request timeout(TimeValue timeout) {
|
||||
this.timeout = timeout;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
/**
|
||||
* A timeout to wait if the index operation can't be performed immediately. Defaults to <tt>1m</tt>.
|
||||
*/
|
||||
public final T timeout(String timeout) {
|
||||
public final Request timeout(String timeout) {
|
||||
return timeout(TimeValue.parseTimeValue(timeout, null, getClass().getSimpleName() + ".timeout"));
|
||||
}
|
||||
|
||||
|
|
|
@ -34,7 +34,7 @@ import java.io.IOException;
|
|||
/**
|
||||
*
|
||||
*/
|
||||
public abstract class SingleShardRequest<T extends SingleShardRequest> extends ActionRequest<T> implements IndicesRequest {
|
||||
public abstract class SingleShardRequest<Request extends SingleShardRequest<Request>> extends ActionRequest<Request> implements IndicesRequest {
|
||||
|
||||
public static final IndicesOptions INDICES_OPTIONS = IndicesOptions.strictSingleIndexNoExpandForbidClosed();
|
||||
|
||||
|
@ -56,11 +56,11 @@ public abstract class SingleShardRequest<T extends SingleShardRequest> extends A
|
|||
this.index = index;
|
||||
}
|
||||
|
||||
protected SingleShardRequest(ActionRequest request) {
|
||||
protected SingleShardRequest(ActionRequest<?> request) {
|
||||
super(request);
|
||||
}
|
||||
|
||||
protected SingleShardRequest(ActionRequest request, String index) {
|
||||
protected SingleShardRequest(ActionRequest<?> request, String index) {
|
||||
super(request);
|
||||
this.index = index;
|
||||
}
|
||||
|
@ -91,9 +91,9 @@ public abstract class SingleShardRequest<T extends SingleShardRequest> extends A
|
|||
* Sets the index.
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T index(String index) {
|
||||
public final Request index(String index) {
|
||||
this.index = index;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -117,9 +117,9 @@ public abstract class SingleShardRequest<T extends SingleShardRequest> extends A
|
|||
* Controls if the operation will be executed on a separate thread when executed locally.
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T operationThreaded(boolean threadedOperation) {
|
||||
public final Request operationThreaded(boolean threadedOperation) {
|
||||
this.threadedOperation = threadedOperation;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -34,7 +34,7 @@ import java.io.IOException;
|
|||
/**
|
||||
* A base class for task requests
|
||||
*/
|
||||
public class BaseTasksRequest<T extends BaseTasksRequest> extends ActionRequest<T> {
|
||||
public class BaseTasksRequest<Request extends BaseTasksRequest<Request>> extends ActionRequest<Request> {
|
||||
|
||||
|
||||
public static final String[] ALL_ACTIONS = Strings.EMPTY_ARRAY;
|
||||
|
@ -65,7 +65,7 @@ public class BaseTasksRequest<T extends BaseTasksRequest> extends ActionRequest<
|
|||
* Get information about tasks from nodes based on the nodes ids specified.
|
||||
* If none are passed, information for all nodes will be returned.
|
||||
*/
|
||||
public BaseTasksRequest(ActionRequest request, String... nodesIds) {
|
||||
public BaseTasksRequest(ActionRequest<?> request, String... nodesIds) {
|
||||
super(request);
|
||||
this.nodesIds = nodesIds;
|
||||
}
|
||||
|
@ -82,9 +82,9 @@ public class BaseTasksRequest<T extends BaseTasksRequest> extends ActionRequest<
|
|||
* Sets the list of action masks for the actions that should be returned
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T actions(String... actions) {
|
||||
public final Request actions(String... actions) {
|
||||
this.actions = actions;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -99,9 +99,9 @@ public class BaseTasksRequest<T extends BaseTasksRequest> extends ActionRequest<
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T nodesIds(String... nodesIds) {
|
||||
public final Request nodesIds(String... nodesIds) {
|
||||
this.nodesIds = nodesIds;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -112,9 +112,9 @@ public class BaseTasksRequest<T extends BaseTasksRequest> extends ActionRequest<
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public T parentNode(String parentNode) {
|
||||
public Request parentNode(String parentNode) {
|
||||
this.parentNode = parentNode;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -125,9 +125,9 @@ public class BaseTasksRequest<T extends BaseTasksRequest> extends ActionRequest<
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public T parentTaskId(long parentTaskId) {
|
||||
public Request parentTaskId(long parentTaskId) {
|
||||
this.parentTaskId = parentTaskId;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
|
||||
|
@ -136,15 +136,15 @@ public class BaseTasksRequest<T extends BaseTasksRequest> extends ActionRequest<
|
|||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(TimeValue timeout) {
|
||||
public final Request timeout(TimeValue timeout) {
|
||||
this.timeout = timeout;
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public final T timeout(String timeout) {
|
||||
public final Request timeout(String timeout) {
|
||||
this.timeout = TimeValue.parseTimeValue(timeout, null, getClass().getSimpleName() + ".timeout");
|
||||
return (T) this;
|
||||
return (Request) this;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -639,8 +639,7 @@ public class UpdateRequest extends InstanceShardOperationRequest<UpdateRequest>
|
|||
ScriptParameterParser scriptParameterParser = new ScriptParameterParser();
|
||||
Map<String, Object> scriptParams = null;
|
||||
Script script = null;
|
||||
XContentType xContentType = XContentFactory.xContentType(source);
|
||||
try (XContentParser parser = XContentFactory.xContent(xContentType).createParser(source)) {
|
||||
try (XContentParser parser = XContentFactory.xContent(source).createParser(source)) {
|
||||
XContentParser.Token token = parser.nextToken();
|
||||
if (token == null) {
|
||||
return this;
|
||||
|
@ -657,10 +656,12 @@ public class UpdateRequest extends InstanceShardOperationRequest<UpdateRequest>
|
|||
} else if ("scripted_upsert".equals(currentFieldName)) {
|
||||
scriptedUpsert = parser.booleanValue();
|
||||
} else if ("upsert".equals(currentFieldName)) {
|
||||
XContentType xContentType = XContentFactory.xContentType(source);
|
||||
XContentBuilder builder = XContentFactory.contentBuilder(xContentType);
|
||||
builder.copyCurrentStructure(parser);
|
||||
safeUpsertRequest().source(builder);
|
||||
} else if ("doc".equals(currentFieldName)) {
|
||||
XContentType xContentType = XContentFactory.xContentType(source);
|
||||
XContentBuilder docBuilder = XContentFactory.contentBuilder(xContentType);
|
||||
docBuilder.copyCurrentStructure(parser);
|
||||
safeDoc().source(docBuilder);
|
||||
|
|
|
@ -66,13 +66,11 @@ import org.elasticsearch.common.util.ExtensionPoint;
|
|||
import org.elasticsearch.gateway.GatewayAllocator;
|
||||
import org.elasticsearch.gateway.PrimaryShardAllocator;
|
||||
import org.elasticsearch.index.IndexSettings;
|
||||
import org.elasticsearch.index.engine.EngineConfig;
|
||||
import org.elasticsearch.index.IndexingSlowLog;
|
||||
import org.elasticsearch.index.search.stats.SearchSlowLog;
|
||||
import org.elasticsearch.index.settings.IndexDynamicSettings;
|
||||
import org.elasticsearch.index.shard.IndexShard;
|
||||
import org.elasticsearch.index.shard.MergePolicyConfig;
|
||||
import org.elasticsearch.index.shard.MergeSchedulerConfig;
|
||||
import org.elasticsearch.index.MergePolicyConfig;
|
||||
import org.elasticsearch.index.MergeSchedulerConfig;
|
||||
import org.elasticsearch.index.store.IndexStore;
|
||||
import org.elasticsearch.indices.IndicesWarmer;
|
||||
import org.elasticsearch.indices.cache.request.IndicesRequestCache;
|
||||
|
@ -148,10 +146,9 @@ public class ClusterModule extends AbstractModule {
|
|||
registerIndexDynamicSetting(IndexMetaData.SETTING_SHARED_FS_ALLOW_RECOVERY_ON_ANY_NODE, Validator.EMPTY);
|
||||
registerIndexDynamicSetting(IndexMetaData.SETTING_PRIORITY, Validator.NON_NEGATIVE_INTEGER);
|
||||
registerIndexDynamicSetting(IndicesTTLService.INDEX_TTL_DISABLE_PURGE, Validator.EMPTY);
|
||||
registerIndexDynamicSetting(IndexShard.INDEX_REFRESH_INTERVAL, Validator.TIME);
|
||||
registerIndexDynamicSetting(IndexSettings.INDEX_REFRESH_INTERVAL, Validator.TIME);
|
||||
registerIndexDynamicSetting(PrimaryShardAllocator.INDEX_RECOVERY_INITIAL_SHARDS, Validator.EMPTY);
|
||||
registerIndexDynamicSetting(EngineConfig.INDEX_GC_DELETES_SETTING, Validator.TIME);
|
||||
registerIndexDynamicSetting(IndexShard.INDEX_FLUSH_ON_CLOSE, Validator.BOOLEAN);
|
||||
registerIndexDynamicSetting(IndexSettings.INDEX_GC_DELETES_SETTING, Validator.TIME);
|
||||
registerIndexDynamicSetting(IndexingSlowLog.INDEX_INDEXING_SLOWLOG_THRESHOLD_INDEX_WARN, Validator.TIME);
|
||||
registerIndexDynamicSetting(IndexingSlowLog.INDEX_INDEXING_SLOWLOG_THRESHOLD_INDEX_INFO, Validator.TIME);
|
||||
registerIndexDynamicSetting(IndexingSlowLog.INDEX_INDEXING_SLOWLOG_THRESHOLD_INDEX_DEBUG, Validator.TIME);
|
||||
|
@ -178,7 +175,7 @@ public class ClusterModule extends AbstractModule {
|
|||
registerIndexDynamicSetting(MergePolicyConfig.INDEX_MERGE_POLICY_SEGMENTS_PER_TIER, Validator.DOUBLE_GTE_2);
|
||||
registerIndexDynamicSetting(MergePolicyConfig.INDEX_MERGE_POLICY_RECLAIM_DELETES_WEIGHT, Validator.NON_NEGATIVE_DOUBLE);
|
||||
registerIndexDynamicSetting(MergePolicyConfig.INDEX_COMPOUND_FORMAT, Validator.EMPTY);
|
||||
registerIndexDynamicSetting(IndexShard.INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE, Validator.BYTES_SIZE);
|
||||
registerIndexDynamicSetting(IndexSettings.INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE, Validator.BYTES_SIZE);
|
||||
registerIndexDynamicSetting(IndexSettings.INDEX_TRANSLOG_DURABILITY, Validator.EMPTY);
|
||||
registerIndexDynamicSetting(IndicesWarmer.INDEX_WARMER_ENABLED, Validator.EMPTY);
|
||||
registerIndexDynamicSetting(IndicesRequestCache.INDEX_CACHE_REQUEST_ENABLED, Validator.BOOLEAN);
|
||||
|
|
|
@ -336,7 +336,7 @@ public class Cache<K, V> {
|
|||
* value using the given mapping function and enters it into this map unless null. The load method for a given key
|
||||
* will be invoked at most once.
|
||||
*
|
||||
* @param key the key whose associated value is to be returned or computed for if non-existant
|
||||
* @param key the key whose associated value is to be returned or computed for if non-existent
|
||||
* @param loader the function to compute a value given a key
|
||||
* @return the current (existing or computed) value associated with the specified key, or null if the computed
|
||||
* value is null
|
||||
|
|
|
@ -21,6 +21,7 @@ package org.elasticsearch.common.geo.builders;
|
|||
|
||||
import com.spatial4j.core.shape.Circle;
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
import org.elasticsearch.common.unit.DistanceUnit;
|
||||
|
@ -35,12 +36,20 @@ public class CircleBuilder extends ShapeBuilder {
|
|||
public static final String FIELD_RADIUS = "radius";
|
||||
public static final GeoShapeType TYPE = GeoShapeType.CIRCLE;
|
||||
|
||||
public static final CircleBuilder PROTOTYPE = new CircleBuilder();
|
||||
static final CircleBuilder PROTOTYPE = new CircleBuilder();
|
||||
|
||||
private DistanceUnit unit;
|
||||
private DistanceUnit unit = DistanceUnit.DEFAULT;
|
||||
private double radius;
|
||||
private Coordinate center;
|
||||
|
||||
/**
|
||||
* Creates a circle centered at [0.0, 0.0].
|
||||
* Center can be changed by calling {@link #center(Coordinate)} later.
|
||||
*/
|
||||
public CircleBuilder() {
|
||||
this.center = ZERO_ZERO;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the center of the circle
|
||||
*
|
||||
|
|
|
@ -20,26 +20,32 @@
|
|||
package org.elasticsearch.common.geo.builders;
|
||||
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* The {@link PointCollection} is an abstract base implementation for all GeoShapes. It simply handles a set of points.
|
||||
* The {@link CoordinateCollection} is an abstract base implementation for {@link LineStringBuilder} and {@link MultiPointBuilder}.
|
||||
* It holds a common list of {@link Coordinate}, provides setters for adding elements to the list and can render this to XContent.
|
||||
*/
|
||||
public abstract class PointCollection<E extends PointCollection<E>> extends ShapeBuilder {
|
||||
public abstract class CoordinateCollection<E extends CoordinateCollection<E>> extends ShapeBuilder {
|
||||
|
||||
protected final ArrayList<Coordinate> points;
|
||||
protected final List<Coordinate> coordinates;
|
||||
|
||||
protected PointCollection() {
|
||||
this(new ArrayList<Coordinate>());
|
||||
}
|
||||
|
||||
protected PointCollection(ArrayList<Coordinate> points) {
|
||||
this.points = points;
|
||||
/**
|
||||
* Construct a new collection of coordinates.
|
||||
* @param coordinates an initial list of coordinates
|
||||
* @throws IllegalArgumentException if coordinates is <tt>null</tt> or empty
|
||||
*/
|
||||
protected CoordinateCollection(List<Coordinate> coordinates) {
|
||||
if (coordinates == null || coordinates.size() == 0) {
|
||||
throw new IllegalArgumentException("cannot create point collection with empty set of points");
|
||||
}
|
||||
this.coordinates = coordinates;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
|
@ -48,54 +54,54 @@ public abstract class PointCollection<E extends PointCollection<E>> extends Shap
|
|||
}
|
||||
|
||||
/**
|
||||
* Add a new point to the collection
|
||||
* Add a new coordinate to the collection
|
||||
* @param longitude longitude of the coordinate
|
||||
* @param latitude latitude of the coordinate
|
||||
* @return this
|
||||
*/
|
||||
public E point(double longitude, double latitude) {
|
||||
return this.point(coordinate(longitude, latitude));
|
||||
public E coordinate(double longitude, double latitude) {
|
||||
return this.coordinate(new Coordinate(longitude, latitude));
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a new point to the collection
|
||||
* Add a new coordinate to the collection
|
||||
* @param coordinate coordinate of the point
|
||||
* @return this
|
||||
*/
|
||||
public E point(Coordinate coordinate) {
|
||||
this.points.add(coordinate);
|
||||
public E coordinate(Coordinate coordinate) {
|
||||
this.coordinates.add(coordinate);
|
||||
return thisRef();
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a array of points to the collection
|
||||
* Add a array of coordinates to the collection
|
||||
*
|
||||
* @param coordinates array of {@link Coordinate}s to add
|
||||
* @return this
|
||||
*/
|
||||
public E points(Coordinate...coordinates) {
|
||||
return this.points(Arrays.asList(coordinates));
|
||||
public E coordinates(Coordinate...coordinates) {
|
||||
return this.coordinates(Arrays.asList(coordinates));
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a collection of points to the collection
|
||||
* Add a collection of coordinates to the collection
|
||||
*
|
||||
* @param coordinates array of {@link Coordinate}s to add
|
||||
* @return this
|
||||
*/
|
||||
public E points(Collection<? extends Coordinate> coordinates) {
|
||||
this.points.addAll(coordinates);
|
||||
public E coordinates(Collection<? extends Coordinate> coordinates) {
|
||||
this.coordinates.addAll(coordinates);
|
||||
return thisRef();
|
||||
}
|
||||
|
||||
/**
|
||||
* Copy all points to a new Array
|
||||
* Copy all coordinate to a new Array
|
||||
*
|
||||
* @param closed if set to true the first point of the array is repeated as last element
|
||||
* @return Array of coordinates
|
||||
*/
|
||||
protected Coordinate[] coordinates(boolean closed) {
|
||||
Coordinate[] result = points.toArray(new Coordinate[points.size() + (closed?1:0)]);
|
||||
Coordinate[] result = coordinates.toArray(new Coordinate[coordinates.size() + (closed?1:0)]);
|
||||
if(closed) {
|
||||
result[result.length-1] = result[0];
|
||||
}
|
||||
|
@ -111,14 +117,14 @@ public abstract class PointCollection<E extends PointCollection<E>> extends Shap
|
|||
*/
|
||||
protected XContentBuilder coordinatesToXcontent(XContentBuilder builder, boolean closed) throws IOException {
|
||||
builder.startArray();
|
||||
for(Coordinate point : points) {
|
||||
toXContent(builder, point);
|
||||
for(Coordinate coord : coordinates) {
|
||||
toXContent(builder, coord);
|
||||
}
|
||||
if(closed) {
|
||||
Coordinate start = points.get(0);
|
||||
Coordinate end = points.get(points.size()-1);
|
||||
Coordinate start = coordinates.get(0);
|
||||
Coordinate end = coordinates.get(coordinates.size()-1);
|
||||
if(start.x != end.x || start.y != end.y) {
|
||||
toXContent(builder, points.get(0));
|
||||
toXContent(builder, coordinates.get(0));
|
||||
}
|
||||
}
|
||||
builder.endArray();
|
|
@ -0,0 +1,98 @@
|
|||
/*
|
||||
* 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.common.geo.builders;
|
||||
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* A builder for a list of coordinates.
|
||||
* Enables chaining of individual coordinates either as long/lat pairs
|
||||
* or as {@link Coordinate} elements, arrays or collections.
|
||||
*/
|
||||
public class CoordinatesBuilder {
|
||||
|
||||
private final List<Coordinate> points = new ArrayList<>();
|
||||
|
||||
/**
|
||||
* Add a new coordinate to the collection
|
||||
* @param coordinate the coordinate to add
|
||||
* @return this
|
||||
*/
|
||||
public CoordinatesBuilder coordinate(Coordinate coordinate) {
|
||||
this.points.add(coordinate);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a new coordinate to the collection
|
||||
* @param longitude longitude of the coordinate
|
||||
* @param latitude latitude of the coordinate
|
||||
* @return this
|
||||
*/
|
||||
public CoordinatesBuilder coordinate(double longitude, double latitude) {
|
||||
return this.coordinate(new Coordinate(longitude, latitude));
|
||||
}
|
||||
|
||||
/**
|
||||
* Add an array of coordinates to the current coordinates
|
||||
*
|
||||
* @param coordinates array of {@link Coordinate}s to add
|
||||
* @return this
|
||||
*/
|
||||
public CoordinatesBuilder coordinates(Coordinate...coordinates) {
|
||||
return this.coordinates(Arrays.asList(coordinates));
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a collection of coordinates to the current coordinates
|
||||
*
|
||||
* @param coordinates collection of {@link Coordinate}s to add
|
||||
* @return this
|
||||
*/
|
||||
public CoordinatesBuilder coordinates(Collection<? extends Coordinate> coordinates) {
|
||||
this.points.addAll(coordinates);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Makes a closed ring out of the current coordinates by adding the starting point as the end point.
|
||||
* Will have no effect of starting and end point are already the same coordinate.
|
||||
*/
|
||||
public CoordinatesBuilder close() {
|
||||
Coordinate start = points.get(0);
|
||||
Coordinate end = points.get(points.size()-1);
|
||||
if(start.x != end.x || start.y != end.y) {
|
||||
points.add(start);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a list containing the current coordinates
|
||||
*/
|
||||
public List<Coordinate> build() {
|
||||
return new ArrayList<>(this.points);
|
||||
}
|
||||
}
|
|
@ -21,6 +21,7 @@ package org.elasticsearch.common.geo.builders;
|
|||
|
||||
import com.spatial4j.core.shape.Rectangle;
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
|
@ -32,33 +33,22 @@ public class EnvelopeBuilder extends ShapeBuilder {
|
|||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.ENVELOPE;
|
||||
|
||||
public static final EnvelopeBuilder PROTOTYPE = new EnvelopeBuilder();
|
||||
static final EnvelopeBuilder PROTOTYPE = new EnvelopeBuilder(new Coordinate(-1.0, 1.0), new Coordinate(1.0, -1.0));
|
||||
|
||||
private Coordinate topLeft;
|
||||
private Coordinate bottomRight;
|
||||
|
||||
public EnvelopeBuilder topLeft(Coordinate topLeft) {
|
||||
public EnvelopeBuilder(Coordinate topLeft, Coordinate bottomRight) {
|
||||
Objects.requireNonNull(topLeft, "topLeft of envelope cannot be null");
|
||||
Objects.requireNonNull(bottomRight, "bottomRight of envelope cannot be null");
|
||||
this.topLeft = topLeft;
|
||||
return this;
|
||||
}
|
||||
|
||||
public EnvelopeBuilder topLeft(double longitude, double latitude) {
|
||||
return topLeft(coordinate(longitude, latitude));
|
||||
this.bottomRight = bottomRight;
|
||||
}
|
||||
|
||||
public Coordinate topLeft() {
|
||||
return this.topLeft;
|
||||
}
|
||||
|
||||
public EnvelopeBuilder bottomRight(Coordinate bottomRight) {
|
||||
this.bottomRight = bottomRight;
|
||||
return this;
|
||||
}
|
||||
|
||||
public EnvelopeBuilder bottomRight(double longitude, double latitude) {
|
||||
return bottomRight(coordinate(longitude, latitude));
|
||||
}
|
||||
|
||||
public Coordinate bottomRight() {
|
||||
return this.bottomRight;
|
||||
}
|
||||
|
@ -110,8 +100,6 @@ public class EnvelopeBuilder extends ShapeBuilder {
|
|||
|
||||
@Override
|
||||
public EnvelopeBuilder readFrom(StreamInput in) throws IOException {
|
||||
return new EnvelopeBuilder()
|
||||
.topLeft(readCoordinateFrom(in))
|
||||
.bottomRight(readCoordinateFrom(in));
|
||||
return new EnvelopeBuilder(readCoordinateFrom(in), readCoordinateFrom(in));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,6 +20,7 @@
|
|||
package org.elasticsearch.common.geo.builders;
|
||||
|
||||
import com.spatial4j.core.shape.Shape;
|
||||
|
||||
import org.elasticsearch.ElasticsearchException;
|
||||
import org.elasticsearch.common.geo.XShapeCollection;
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
|
@ -35,7 +36,7 @@ public class GeometryCollectionBuilder extends ShapeBuilder {
|
|||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.GEOMETRYCOLLECTION;
|
||||
|
||||
public static final GeometryCollectionBuilder PROTOTYPE = new GeometryCollectionBuilder();
|
||||
static final GeometryCollectionBuilder PROTOTYPE = new GeometryCollectionBuilder();
|
||||
|
||||
protected final ArrayList<ShapeBuilder> shapes = new ArrayList<>();
|
||||
|
||||
|
|
|
@ -24,6 +24,7 @@ import com.vividsolutions.jts.geom.Coordinate;
|
|||
import com.vividsolutions.jts.geom.Geometry;
|
||||
import com.vividsolutions.jts.geom.GeometryFactory;
|
||||
import com.vividsolutions.jts.geom.LineString;
|
||||
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
|
@ -31,13 +32,32 @@ import org.elasticsearch.common.xcontent.XContentBuilder;
|
|||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
public class LineStringBuilder extends PointCollection<LineStringBuilder> {
|
||||
public class LineStringBuilder extends CoordinateCollection<LineStringBuilder> {
|
||||
|
||||
/**
|
||||
* Construct a new LineString.
|
||||
* Per GeoJSON spec (http://geojson.org/geojson-spec.html#linestring)
|
||||
* a LineString must contain two or more coordinates
|
||||
* @param coordinates the initial list of coordinates
|
||||
* @throws IllegalArgumentException if there are less then two coordinates defined
|
||||
*/
|
||||
public LineStringBuilder(List<Coordinate> coordinates) {
|
||||
super(coordinates);
|
||||
if (coordinates.size() < 2) {
|
||||
throw new IllegalArgumentException("invalid number of points in LineString (found [" + coordinates.size()+ "] - must be >= 2)");
|
||||
}
|
||||
}
|
||||
|
||||
public LineStringBuilder(CoordinatesBuilder coordinates) {
|
||||
this(coordinates.build());
|
||||
}
|
||||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.LINESTRING;
|
||||
|
||||
public static final LineStringBuilder PROTOTYPE = new LineStringBuilder();
|
||||
static final LineStringBuilder PROTOTYPE = new LineStringBuilder(new CoordinatesBuilder().coordinate(0.0, 0.0).coordinate(1.0, 1.0));
|
||||
|
||||
@Override
|
||||
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
|
@ -50,13 +70,14 @@ public class LineStringBuilder extends PointCollection<LineStringBuilder> {
|
|||
}
|
||||
|
||||
/**
|
||||
* Closes the current lineString by adding the starting point as the end point
|
||||
* Closes the current lineString by adding the starting point as the end point.
|
||||
* This will have no effect if starting and end point are already the same.
|
||||
*/
|
||||
public LineStringBuilder close() {
|
||||
Coordinate start = points.get(0);
|
||||
Coordinate end = points.get(points.size()-1);
|
||||
Coordinate start = coordinates.get(0);
|
||||
Coordinate end = coordinates.get(coordinates.size() - 1);
|
||||
if(start.x != end.x || start.y != end.y) {
|
||||
points.add(start);
|
||||
coordinates.add(start);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
@ -68,7 +89,7 @@ public class LineStringBuilder extends PointCollection<LineStringBuilder> {
|
|||
|
||||
@Override
|
||||
public Shape build() {
|
||||
Coordinate[] coordinates = points.toArray(new Coordinate[points.size()]);
|
||||
Coordinate[] coordinates = this.coordinates.toArray(new Coordinate[this.coordinates.size()]);
|
||||
Geometry geometry;
|
||||
if(wrapdateline) {
|
||||
ArrayList<LineString> strings = decompose(FACTORY, coordinates, new ArrayList<LineString>());
|
||||
|
@ -147,7 +168,7 @@ public class LineStringBuilder extends PointCollection<LineStringBuilder> {
|
|||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(points);
|
||||
return Objects.hash(coordinates);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -159,24 +180,25 @@ public class LineStringBuilder extends PointCollection<LineStringBuilder> {
|
|||
return false;
|
||||
}
|
||||
LineStringBuilder other = (LineStringBuilder) obj;
|
||||
return Objects.equals(points, other.points);
|
||||
return Objects.equals(coordinates, other.coordinates);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(StreamOutput out) throws IOException {
|
||||
out.writeVInt(points.size());
|
||||
for (Coordinate point : points) {
|
||||
out.writeVInt(coordinates.size());
|
||||
for (Coordinate point : coordinates) {
|
||||
writeCoordinateTo(point, out);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public LineStringBuilder readFrom(StreamInput in) throws IOException {
|
||||
LineStringBuilder lineStringBuilder = new LineStringBuilder();
|
||||
CoordinatesBuilder coordinates = new CoordinatesBuilder();
|
||||
int size = in.readVInt();
|
||||
for (int i=0; i < size; i++) {
|
||||
lineStringBuilder.point(readCoordinateFrom(in));
|
||||
coordinates.coordinate(readCoordinateFrom(in));
|
||||
}
|
||||
LineStringBuilder lineStringBuilder = new LineStringBuilder(coordinates);
|
||||
return lineStringBuilder;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -23,6 +23,7 @@ import com.spatial4j.core.shape.Shape;
|
|||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
import com.vividsolutions.jts.geom.Geometry;
|
||||
import com.vividsolutions.jts.geom.LineString;
|
||||
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
|
@ -36,7 +37,7 @@ public class MultiLineStringBuilder extends ShapeBuilder {
|
|||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.MULTILINESTRING;
|
||||
|
||||
public static final MultiLineStringBuilder PROTOTYPE = new MultiLineStringBuilder();
|
||||
static final MultiLineStringBuilder PROTOTYPE = new MultiLineStringBuilder();
|
||||
|
||||
private final ArrayList<LineStringBuilder> lines = new ArrayList<>();
|
||||
|
||||
|
@ -45,10 +46,6 @@ public class MultiLineStringBuilder extends ShapeBuilder {
|
|||
return this;
|
||||
}
|
||||
|
||||
public MultiLineStringBuilder linestring(Coordinate[] coordinates) {
|
||||
return this.linestring(new LineStringBuilder().points(coordinates));
|
||||
}
|
||||
|
||||
public Coordinate[][] coordinates() {
|
||||
Coordinate[][] result = new Coordinate[lines.size()][];
|
||||
for (int i = 0; i < result.length; i++) {
|
||||
|
|
|
@ -22,6 +22,7 @@ package org.elasticsearch.common.geo.builders;
|
|||
import com.spatial4j.core.shape.Point;
|
||||
import com.spatial4j.core.shape.Shape;
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import org.elasticsearch.common.geo.XShapeCollection;
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
|
@ -32,11 +33,19 @@ import java.util.ArrayList;
|
|||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
public class MultiPointBuilder extends PointCollection<MultiPointBuilder> {
|
||||
public class MultiPointBuilder extends CoordinateCollection<MultiPointBuilder> {
|
||||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.MULTIPOINT;
|
||||
|
||||
public final static MultiPointBuilder PROTOTYPE = new MultiPointBuilder();
|
||||
final static MultiPointBuilder PROTOTYPE = new MultiPointBuilder(new CoordinatesBuilder().coordinate(0.0, 0.0).build());
|
||||
|
||||
/**
|
||||
* Create a new {@link MultiPointBuilder}.
|
||||
* @param coordinates needs at least two coordinates to be valid, otherwise will throw an exception
|
||||
*/
|
||||
public MultiPointBuilder(List<Coordinate> coordinates) {
|
||||
super(coordinates);
|
||||
}
|
||||
|
||||
@Override
|
||||
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
|
@ -52,8 +61,8 @@ public class MultiPointBuilder extends PointCollection<MultiPointBuilder> {
|
|||
public Shape build() {
|
||||
//Could wrap JtsGeometry but probably slower due to conversions to/from JTS in relate()
|
||||
//MultiPoint geometry = FACTORY.createMultiPoint(points.toArray(new Coordinate[points.size()]));
|
||||
List<Point> shapes = new ArrayList<>(points.size());
|
||||
for (Coordinate coord : points) {
|
||||
List<Point> shapes = new ArrayList<>(coordinates.size());
|
||||
for (Coordinate coord : coordinates) {
|
||||
shapes.add(SPATIAL_CONTEXT.makePoint(coord.x, coord.y));
|
||||
}
|
||||
XShapeCollection<Point> multiPoints = new XShapeCollection<>(shapes, SPATIAL_CONTEXT);
|
||||
|
@ -68,7 +77,7 @@ public class MultiPointBuilder extends PointCollection<MultiPointBuilder> {
|
|||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(points);
|
||||
return Objects.hash(coordinates);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -80,24 +89,26 @@ public class MultiPointBuilder extends PointCollection<MultiPointBuilder> {
|
|||
return false;
|
||||
}
|
||||
MultiPointBuilder other = (MultiPointBuilder) obj;
|
||||
return Objects.equals(points, other.points);
|
||||
return Objects.equals(coordinates, other.coordinates);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(StreamOutput out) throws IOException {
|
||||
out.writeVInt(points.size());
|
||||
for (Coordinate point : points) {
|
||||
out.writeVInt(coordinates.size());
|
||||
for (Coordinate point : coordinates) {
|
||||
writeCoordinateTo(point, out);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public MultiPointBuilder readFrom(StreamInput in) throws IOException {
|
||||
MultiPointBuilder multiPointBuilder = new MultiPointBuilder();
|
||||
int size = in.readVInt();
|
||||
List<Coordinate> points = new ArrayList<Coordinate>(size);
|
||||
for (int i=0; i < size; i++) {
|
||||
multiPointBuilder.point(readCoordinateFrom(in));
|
||||
points.add(readCoordinateFrom(in));
|
||||
}
|
||||
MultiPointBuilder multiPointBuilder = new MultiPointBuilder(points);
|
||||
|
||||
return multiPointBuilder;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,6 +21,7 @@ package org.elasticsearch.common.geo.builders;
|
|||
|
||||
import com.spatial4j.core.shape.Shape;
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import org.elasticsearch.common.geo.XShapeCollection;
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
|
@ -35,7 +36,7 @@ import java.util.Objects;
|
|||
public class MultiPolygonBuilder extends ShapeBuilder {
|
||||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.MULTIPOLYGON;
|
||||
public static final MultiPolygonBuilder PROTOTYPE = new MultiPolygonBuilder();
|
||||
static final MultiPolygonBuilder PROTOTYPE = new MultiPolygonBuilder();
|
||||
|
||||
private final ArrayList<PolygonBuilder> polygons = new ArrayList<>();
|
||||
|
||||
|
@ -58,8 +59,7 @@ public class MultiPolygonBuilder extends ShapeBuilder {
|
|||
* {@link MultiPolygonBuilder} to the polygon if polygon has different orientation.
|
||||
*/
|
||||
public MultiPolygonBuilder polygon(PolygonBuilder polygon) {
|
||||
PolygonBuilder pb = new PolygonBuilder(this.orientation);
|
||||
pb.points(polygon.shell().coordinates(false));
|
||||
PolygonBuilder pb = new PolygonBuilder(new CoordinatesBuilder().coordinates(polygon.shell().coordinates(false)), this.orientation);
|
||||
for (LineStringBuilder hole : polygon.holes()) {
|
||||
pb.hole(hole);
|
||||
}
|
||||
|
|
|
@ -21,6 +21,7 @@ package org.elasticsearch.common.geo.builders;
|
|||
|
||||
import com.spatial4j.core.shape.Point;
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
|
@ -31,10 +32,17 @@ import java.util.Objects;
|
|||
public class PointBuilder extends ShapeBuilder {
|
||||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.POINT;
|
||||
public static final PointBuilder PROTOTYPE = new PointBuilder();
|
||||
static final PointBuilder PROTOTYPE = new PointBuilder();
|
||||
|
||||
private Coordinate coordinate;
|
||||
|
||||
/**
|
||||
* Create a point at [0.0,0.0]
|
||||
*/
|
||||
public PointBuilder() {
|
||||
this.coordinate = ZERO_ZERO;
|
||||
}
|
||||
|
||||
public PointBuilder coordinate(Coordinate coordinate) {
|
||||
this.coordinate = coordinate;
|
||||
return this;
|
||||
|
|
|
@ -27,6 +27,7 @@ import com.vividsolutions.jts.geom.GeometryFactory;
|
|||
import com.vividsolutions.jts.geom.LinearRing;
|
||||
import com.vividsolutions.jts.geom.MultiPolygon;
|
||||
import com.vividsolutions.jts.geom.Polygon;
|
||||
|
||||
import org.elasticsearch.common.collect.Tuple;
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
|
@ -52,7 +53,8 @@ import java.util.concurrent.atomic.AtomicBoolean;
|
|||
public class PolygonBuilder extends ShapeBuilder {
|
||||
|
||||
public static final GeoShapeType TYPE = GeoShapeType.POLYGON;
|
||||
public static final PolygonBuilder PROTOTYPE = new PolygonBuilder();
|
||||
static final PolygonBuilder PROTOTYPE = new PolygonBuilder(new CoordinatesBuilder().coordinate(0.0, 0.0).coordinate(0.0, 1.0)
|
||||
.coordinate(1.0, 0.0).coordinate(0.0, 0.0));
|
||||
|
||||
private static final Coordinate[][] EMPTY = new Coordinate[0][];
|
||||
|
||||
|
@ -64,54 +66,51 @@ public class PolygonBuilder extends ShapeBuilder {
|
|||
// List of line strings defining the holes of the polygon
|
||||
private final ArrayList<LineStringBuilder> holes = new ArrayList<>();
|
||||
|
||||
public PolygonBuilder() {
|
||||
this(Orientation.RIGHT);
|
||||
}
|
||||
|
||||
public PolygonBuilder(Orientation orientation) {
|
||||
this(new ArrayList<Coordinate>(), orientation);
|
||||
}
|
||||
|
||||
public PolygonBuilder(ArrayList<Coordinate> points, Orientation orientation) {
|
||||
public PolygonBuilder(LineStringBuilder lineString, Orientation orientation, boolean coerce) {
|
||||
this.orientation = orientation;
|
||||
this.shell = new LineStringBuilder().points(points);
|
||||
if (coerce) {
|
||||
lineString.close();
|
||||
}
|
||||
validateLinearRing(lineString);
|
||||
this.shell = lineString;
|
||||
}
|
||||
|
||||
public PolygonBuilder(LineStringBuilder lineString, Orientation orientation) {
|
||||
this(lineString, orientation, false);
|
||||
}
|
||||
|
||||
public PolygonBuilder(CoordinatesBuilder coordinates, Orientation orientation) {
|
||||
this(new LineStringBuilder(coordinates), orientation, false);
|
||||
}
|
||||
|
||||
public PolygonBuilder(CoordinatesBuilder coordinates) {
|
||||
this(coordinates, Orientation.RIGHT);
|
||||
}
|
||||
|
||||
public Orientation orientation() {
|
||||
return this.orientation;
|
||||
}
|
||||
|
||||
public PolygonBuilder point(double longitude, double latitude) {
|
||||
shell.point(longitude, latitude);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a point to the shell of the polygon
|
||||
* @param coordinate coordinate of the new point
|
||||
* @return this
|
||||
*/
|
||||
public PolygonBuilder point(Coordinate coordinate) {
|
||||
shell.point(coordinate);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add an array of points to the shell of the polygon
|
||||
* @param coordinates coordinates of the new points to add
|
||||
* @return this
|
||||
*/
|
||||
public PolygonBuilder points(Coordinate...coordinates) {
|
||||
shell.points(coordinates);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a new hole to the polygon
|
||||
* @param hole linear ring defining the hole
|
||||
* @return this
|
||||
*/
|
||||
public PolygonBuilder hole(LineStringBuilder hole) {
|
||||
return this.hole(hole, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a new hole to the polygon
|
||||
* @param hole linear ring defining the hole
|
||||
* @param coerce if set to true, it will try to close the hole by adding starting point as end point
|
||||
* @return this
|
||||
*/
|
||||
public PolygonBuilder hole(LineStringBuilder hole, boolean coerce) {
|
||||
if (coerce) {
|
||||
hole.close();
|
||||
}
|
||||
validateLinearRing(hole);
|
||||
holes.add(hole);
|
||||
return this;
|
||||
}
|
||||
|
@ -138,12 +137,30 @@ public class PolygonBuilder extends ShapeBuilder {
|
|||
return this;
|
||||
}
|
||||
|
||||
private static void validateLinearRing(LineStringBuilder lineString) {
|
||||
/**
|
||||
* Per GeoJSON spec (http://geojson.org/geojson-spec.html#linestring)
|
||||
* A LinearRing is closed LineString with 4 or more positions. The first and last positions
|
||||
* are equivalent (they represent equivalent points). Though a LinearRing is not explicitly
|
||||
* represented as a GeoJSON geometry type, it is referred to in the Polygon geometry type definition.
|
||||
*/
|
||||
List<Coordinate> points = lineString.coordinates;
|
||||
if (points.size() < 4) {
|
||||
throw new IllegalArgumentException(
|
||||
"invalid number of points in LinearRing (found [" + points.size() + "] - must be >= 4)");
|
||||
}
|
||||
|
||||
if (!points.get(0).equals(points.get(points.size() - 1))) {
|
||||
throw new IllegalArgumentException("invalid LinearRing found (coordinates are not closed)");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates only 1 vertex is tangential (shared) between the interior and exterior of a polygon
|
||||
*/
|
||||
protected void validateHole(LineStringBuilder shell, LineStringBuilder hole) {
|
||||
HashSet<Coordinate> exterior = Sets.newHashSet(shell.points);
|
||||
HashSet<Coordinate> interior = Sets.newHashSet(hole.points);
|
||||
HashSet<Coordinate> exterior = Sets.newHashSet(shell.coordinates);
|
||||
HashSet<Coordinate> interior = Sets.newHashSet(hole.coordinates);
|
||||
exterior.retainAll(interior);
|
||||
if (exterior.size() >= 2) {
|
||||
throw new InvalidShapeException("Invalid polygon, interior cannot share more than one point with the exterior");
|
||||
|
@ -161,9 +178,9 @@ public class PolygonBuilder extends ShapeBuilder {
|
|||
* @return coordinates of the polygon
|
||||
*/
|
||||
public Coordinate[][][] coordinates() {
|
||||
int numEdges = shell.points.size()-1; // Last point is repeated
|
||||
int numEdges = shell.coordinates.size()-1; // Last point is repeated
|
||||
for (int i = 0; i < holes.size(); i++) {
|
||||
numEdges += holes.get(i).points.size()-1;
|
||||
numEdges += holes.get(i).coordinates.size()-1;
|
||||
validateHole(shell, this.holes.get(i));
|
||||
}
|
||||
|
||||
|
@ -226,16 +243,16 @@ public class PolygonBuilder extends ShapeBuilder {
|
|||
}
|
||||
|
||||
protected Polygon toPolygon(GeometryFactory factory) {
|
||||
final LinearRing shell = linearRing(factory, this.shell.points);
|
||||
final LinearRing shell = linearRing(factory, this.shell.coordinates);
|
||||
final LinearRing[] holes = new LinearRing[this.holes.size()];
|
||||
Iterator<LineStringBuilder> iterator = this.holes.iterator();
|
||||
for (int i = 0; iterator.hasNext(); i++) {
|
||||
holes[i] = linearRing(factory, iterator.next().points);
|
||||
holes[i] = linearRing(factory, iterator.next().coordinates);
|
||||
}
|
||||
return factory.createPolygon(shell, holes);
|
||||
}
|
||||
|
||||
protected static LinearRing linearRing(GeometryFactory factory, ArrayList<Coordinate> coordinates) {
|
||||
protected static LinearRing linearRing(GeometryFactory factory, List<Coordinate> coordinates) {
|
||||
return factory.createLinearRing(coordinates.toArray(new Coordinate[coordinates.size()]));
|
||||
}
|
||||
|
||||
|
@ -711,8 +728,8 @@ public class PolygonBuilder extends ShapeBuilder {
|
|||
|
||||
@Override
|
||||
public void writeTo(StreamOutput out) throws IOException {
|
||||
orientation.writeTo(out);
|
||||
shell.writeTo(out);
|
||||
orientation.writeTo(out);
|
||||
out.writeVInt(holes.size());
|
||||
for (LineStringBuilder hole : holes) {
|
||||
hole.writeTo(out);
|
||||
|
@ -721,8 +738,9 @@ public class PolygonBuilder extends ShapeBuilder {
|
|||
|
||||
@Override
|
||||
public PolygonBuilder readFrom(StreamInput in) throws IOException {
|
||||
PolygonBuilder polyBuilder = new PolygonBuilder(Orientation.readFrom(in));
|
||||
polyBuilder.shell = LineStringBuilder.PROTOTYPE.readFrom(in);
|
||||
LineStringBuilder shell = LineStringBuilder.PROTOTYPE.readFrom(in);
|
||||
Orientation orientation = Orientation.readFrom(in);
|
||||
PolygonBuilder polyBuilder = new PolygonBuilder(shell, orientation);
|
||||
int holes = in.readVInt();
|
||||
for (int i = 0; i < holes; i++) {
|
||||
polyBuilder.hole(LineStringBuilder.PROTOTYPE.readFrom(in));
|
||||
|
|
|
@ -26,6 +26,7 @@ import com.spatial4j.core.shape.jts.JtsGeometry;
|
|||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
import com.vividsolutions.jts.geom.Geometry;
|
||||
import com.vividsolutions.jts.geom.GeometryFactory;
|
||||
|
||||
import org.elasticsearch.ElasticsearchParseException;
|
||||
import org.elasticsearch.action.support.ToXContentToBytes;
|
||||
import org.elasticsearch.common.io.stream.NamedWriteable;
|
||||
|
@ -64,6 +65,11 @@ public abstract class ShapeBuilder extends ToXContentToBytes implements NamedWri
|
|||
}
|
||||
|
||||
public static final double DATELINE = 180;
|
||||
|
||||
/**
|
||||
* coordinate at [0.0, 0.0]
|
||||
*/
|
||||
public static final Coordinate ZERO_ZERO = new Coordinate(0.0, 0.0);
|
||||
// TODO how might we use JtsSpatialContextFactory to configure the context (esp. for non-geo)?
|
||||
public static final JtsSpatialContext SPATIAL_CONTEXT = JtsSpatialContext.GEO;
|
||||
public static final GeometryFactory FACTORY = SPATIAL_CONTEXT.getGeometryFactory();
|
||||
|
@ -81,11 +87,6 @@ public abstract class ShapeBuilder extends ToXContentToBytes implements NamedWri
|
|||
protected final boolean autoIndexJtsGeometry = true;//may want to turn off once SpatialStrategy impls do it.
|
||||
|
||||
protected ShapeBuilder() {
|
||||
|
||||
}
|
||||
|
||||
protected static Coordinate coordinate(double longitude, double latitude) {
|
||||
return new Coordinate(longitude, latitude);
|
||||
}
|
||||
|
||||
protected JtsGeometry jtsGeometry(Geometry geom) {
|
||||
|
@ -569,7 +570,7 @@ public abstract class ShapeBuilder extends ToXContentToBytes implements NamedWri
|
|||
uL = new Coordinate(Math.min(uL.x, lR.x), Math.max(uL.y, lR.y));
|
||||
lR = new Coordinate(Math.max(uLtmp.x, lR.x), Math.min(uLtmp.y, lR.y));
|
||||
}
|
||||
return ShapeBuilders.newEnvelope().topLeft(uL).bottomRight(lR);
|
||||
return ShapeBuilders.newEnvelope(uL, lR);
|
||||
}
|
||||
|
||||
protected static void validateMultiPointNode(CoordinateNode coordinates) {
|
||||
|
@ -589,12 +590,11 @@ public abstract class ShapeBuilder extends ToXContentToBytes implements NamedWri
|
|||
|
||||
protected static MultiPointBuilder parseMultiPoint(CoordinateNode coordinates) {
|
||||
validateMultiPointNode(coordinates);
|
||||
|
||||
MultiPointBuilder points = new MultiPointBuilder();
|
||||
CoordinatesBuilder points = new CoordinatesBuilder();
|
||||
for (CoordinateNode node : coordinates.children) {
|
||||
points.point(node.coordinate);
|
||||
points.coordinate(node.coordinate);
|
||||
}
|
||||
return points;
|
||||
return new MultiPointBuilder(points.build());
|
||||
}
|
||||
|
||||
protected static LineStringBuilder parseLineString(CoordinateNode coordinates) {
|
||||
|
@ -607,11 +607,11 @@ public abstract class ShapeBuilder extends ToXContentToBytes implements NamedWri
|
|||
throw new ElasticsearchParseException("invalid number of points in LineString (found [{}] - must be >= 2)", coordinates.children.size());
|
||||
}
|
||||
|
||||
LineStringBuilder line = ShapeBuilders.newLineString();
|
||||
CoordinatesBuilder line = new CoordinatesBuilder();
|
||||
for (CoordinateNode node : coordinates.children) {
|
||||
line.point(node.coordinate);
|
||||
line.coordinate(node.coordinate);
|
||||
}
|
||||
return line;
|
||||
return ShapeBuilders.newLineString(line);
|
||||
}
|
||||
|
||||
protected static MultiLineStringBuilder parseMultiLine(CoordinateNode coordinates) {
|
||||
|
@ -659,7 +659,7 @@ public abstract class ShapeBuilder extends ToXContentToBytes implements NamedWri
|
|||
}
|
||||
|
||||
LineStringBuilder shell = parseLinearRing(coordinates.children.get(0), coerce);
|
||||
PolygonBuilder polygon = new PolygonBuilder(shell.points, orientation);
|
||||
PolygonBuilder polygon = new PolygonBuilder(shell, orientation);
|
||||
for (int i = 1; i < coordinates.children.size(); i++) {
|
||||
polygon.hole(parseLinearRing(coordinates.children.get(i), coerce));
|
||||
}
|
||||
|
|
|
@ -21,6 +21,8 @@ package org.elasticsearch.common.geo.builders;
|
|||
|
||||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* A collection of static methods for creating ShapeBuilders.
|
||||
*/
|
||||
|
@ -50,16 +52,24 @@ public class ShapeBuilders {
|
|||
* Create a new set of points
|
||||
* @return new {@link MultiPointBuilder}
|
||||
*/
|
||||
public static MultiPointBuilder newMultiPoint() {
|
||||
return new MultiPointBuilder();
|
||||
public static MultiPointBuilder newMultiPoint(List<Coordinate> points) {
|
||||
return new MultiPointBuilder(points);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new lineString
|
||||
* @return a new {@link LineStringBuilder}
|
||||
*/
|
||||
public static LineStringBuilder newLineString() {
|
||||
return new LineStringBuilder();
|
||||
public static LineStringBuilder newLineString(List<Coordinate> list) {
|
||||
return new LineStringBuilder(list);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new lineString
|
||||
* @return a new {@link LineStringBuilder}
|
||||
*/
|
||||
public static LineStringBuilder newLineString(CoordinatesBuilder coordinates) {
|
||||
return new LineStringBuilder(coordinates);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -71,19 +81,19 @@ public class ShapeBuilders {
|
|||
}
|
||||
|
||||
/**
|
||||
* Create a new Polygon
|
||||
* @return a new {@link PointBuilder}
|
||||
* Create a new PolygonBuilder
|
||||
* @return a new {@link PolygonBuilder}
|
||||
*/
|
||||
public static PolygonBuilder newPolygon() {
|
||||
return new PolygonBuilder();
|
||||
public static PolygonBuilder newPolygon(List<Coordinate> shell) {
|
||||
return new PolygonBuilder(new CoordinatesBuilder().coordinates(shell));
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new Polygon
|
||||
* @return a new {@link PointBuilder}
|
||||
* Create a new PolygonBuilder
|
||||
* @return a new {@link PolygonBuilder}
|
||||
*/
|
||||
public static PolygonBuilder newPolygon(ShapeBuilder.Orientation orientation) {
|
||||
return new PolygonBuilder(orientation);
|
||||
public static PolygonBuilder newPolygon(CoordinatesBuilder shell) {
|
||||
return new PolygonBuilder(shell);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -124,7 +134,7 @@ public class ShapeBuilders {
|
|||
*
|
||||
* @return a new {@link EnvelopeBuilder}
|
||||
*/
|
||||
public static EnvelopeBuilder newEnvelope() {
|
||||
return new EnvelopeBuilder();
|
||||
public static EnvelopeBuilder newEnvelope(Coordinate topLeft, Coordinate bottomRight) {
|
||||
return new EnvelopeBuilder(topLeft, bottomRight);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -81,6 +81,4 @@ public final class ConfigurationException extends RuntimeException {
|
|||
public String getMessage() {
|
||||
return Errors.format("Guice configuration errors", messages);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
|
@ -52,6 +52,4 @@ public class CreationException extends RuntimeException {
|
|||
public String getMessage() {
|
||||
return Errors.format("Guice creation errors", messages);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
|
|
@ -68,6 +68,4 @@ public final class ProvisionException extends RuntimeException {
|
|||
public String getMessage() {
|
||||
return Errors.format("Guice provision errors", messages);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
|
|
@ -32,7 +32,6 @@ import org.elasticsearch.common.inject.spi.Message;
|
|||
import org.elasticsearch.common.inject.spi.TypeListenerBinding;
|
||||
|
||||
import java.io.PrintWriter;
|
||||
import java.io.Serializable;
|
||||
import java.io.StringWriter;
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.lang.reflect.Constructor;
|
||||
|
@ -66,7 +65,7 @@ import static java.util.Collections.unmodifiableList;
|
|||
*
|
||||
* @author jessewilson@google.com (Jesse Wilson)
|
||||
*/
|
||||
public final class Errors implements Serializable {
|
||||
public final class Errors {
|
||||
|
||||
/**
|
||||
* The root errors object. Used to access the list of error messages.
|
||||
|
|
|
@ -313,7 +313,5 @@ public final class Join {
|
|||
private JoinException(IOException cause) {
|
||||
super(cause);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,7 +21,6 @@ import org.elasticsearch.common.inject.ConfigurationException;
|
|||
import org.elasticsearch.common.inject.TypeLiteral;
|
||||
import org.elasticsearch.common.inject.spi.Message;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.lang.reflect.Constructor;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.GenericArrayType;
|
||||
|
@ -108,8 +107,7 @@ public class MoreTypes {
|
|||
|
||||
/**
|
||||
* Returns a type that is functionally equal but not necessarily equal
|
||||
* according to {@link Object#equals(Object) Object.equals()}. The returned
|
||||
* type is {@link Serializable}.
|
||||
* according to {@link Object#equals(Object) Object.equals()}.
|
||||
*/
|
||||
public static Type canonicalize(Type type) {
|
||||
if (type instanceof ParameterizedTypeImpl
|
||||
|
@ -140,17 +138,6 @@ public class MoreTypes {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a type that's functionally equal but not necessarily equal
|
||||
* according to {@link Object#equals(Object) Object.equals}. The returned
|
||||
* member is {@link Serializable}.
|
||||
*/
|
||||
public static Member serializableCopy(Member member) {
|
||||
return member instanceof MemberImpl
|
||||
? member
|
||||
: new MemberImpl(member);
|
||||
}
|
||||
|
||||
public static Class<?> getRawType(Type type) {
|
||||
if (type instanceof Class<?>) {
|
||||
// type is a normal class.
|
||||
|
@ -450,7 +437,7 @@ public class MoreTypes {
|
|||
}
|
||||
|
||||
public static class ParameterizedTypeImpl
|
||||
implements ParameterizedType, Serializable, CompositeType {
|
||||
implements ParameterizedType, CompositeType {
|
||||
private final Type ownerType;
|
||||
private final Type rawType;
|
||||
private final Type[] typeArguments;
|
||||
|
@ -527,12 +514,10 @@ public class MoreTypes {
|
|||
public String toString() {
|
||||
return MoreTypes.toString(this);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
public static class GenericArrayTypeImpl
|
||||
implements GenericArrayType, Serializable, CompositeType {
|
||||
implements GenericArrayType, CompositeType {
|
||||
private final Type componentType;
|
||||
|
||||
public GenericArrayTypeImpl(Type componentType) {
|
||||
|
@ -564,8 +549,6 @@ public class MoreTypes {
|
|||
public String toString() {
|
||||
return MoreTypes.toString(this);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -573,7 +556,7 @@ public class MoreTypes {
|
|||
* lower bounds. We only support what the Java 6 language needs - at most one
|
||||
* bound. If a lower bound is set, the upper bound must be Object.class.
|
||||
*/
|
||||
public static class WildcardTypeImpl implements WildcardType, Serializable, CompositeType {
|
||||
public static class WildcardTypeImpl implements WildcardType, CompositeType {
|
||||
private final Type upperBound;
|
||||
private final Type lowerBound;
|
||||
|
||||
|
@ -632,8 +615,6 @@ public class MoreTypes {
|
|||
public String toString() {
|
||||
return MoreTypes.toString(this);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
private static void checkNotPrimitive(Type type, String use) {
|
||||
|
@ -647,7 +628,7 @@ public class MoreTypes {
|
|||
* our exception types. We workaround this with this serializable implementation. It includes all
|
||||
* of the API methods, plus everything we use for line numbers and messaging.
|
||||
*/
|
||||
public static class MemberImpl implements Member, Serializable {
|
||||
public static class MemberImpl implements Member {
|
||||
private final Class<?> declaringClass;
|
||||
private final String name;
|
||||
private final int modifiers;
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
|
||||
package org.elasticsearch.common.inject.matcher;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* Implements {@code and()} and {@code or()}.
|
||||
*
|
||||
|
@ -35,7 +33,7 @@ public abstract class AbstractMatcher<T> implements Matcher<T> {
|
|||
return new OrMatcher<>(this, other);
|
||||
}
|
||||
|
||||
private static class AndMatcher<T> extends AbstractMatcher<T> implements Serializable {
|
||||
private static class AndMatcher<T> extends AbstractMatcher<T> {
|
||||
private final Matcher<? super T> a, b;
|
||||
|
||||
public AndMatcher(Matcher<? super T> a, Matcher<? super T> b) {
|
||||
|
@ -64,11 +62,9 @@ public abstract class AbstractMatcher<T> implements Matcher<T> {
|
|||
public String toString() {
|
||||
return "and(" + a + ", " + b + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
private static class OrMatcher<T> extends AbstractMatcher<T> implements Serializable {
|
||||
private static class OrMatcher<T> extends AbstractMatcher<T> {
|
||||
private final Matcher<? super T> a, b;
|
||||
|
||||
public OrMatcher(Matcher<? super T> a, Matcher<? super T> b) {
|
||||
|
@ -97,7 +93,5 @@ public abstract class AbstractMatcher<T> implements Matcher<T> {
|
|||
public String toString() {
|
||||
return "or(" + a + ", " + b + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,7 +16,6 @@
|
|||
|
||||
package org.elasticsearch.common.inject.matcher;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
|
@ -42,7 +41,7 @@ public class Matchers {
|
|||
|
||||
private static final Matcher<Object> ANY = new Any();
|
||||
|
||||
private static class Any extends AbstractMatcher<Object> implements Serializable {
|
||||
private static class Any extends AbstractMatcher<Object> {
|
||||
@Override
|
||||
public boolean matches(Object o) {
|
||||
return true;
|
||||
|
@ -56,8 +55,6 @@ public class Matchers {
|
|||
public Object readResolve() {
|
||||
return any();
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -67,7 +64,7 @@ public class Matchers {
|
|||
return new Not<>(p);
|
||||
}
|
||||
|
||||
private static class Not<T> extends AbstractMatcher<T> implements Serializable {
|
||||
private static class Not<T> extends AbstractMatcher<T> {
|
||||
final Matcher<? super T> delegate;
|
||||
|
||||
private Not(Matcher<? super T> delegate) {
|
||||
|
@ -94,8 +91,6 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "not(" + delegate + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
private static void checkForRuntimeRetention(
|
||||
|
@ -115,8 +110,7 @@ public class Matchers {
|
|||
return new AnnotatedWithType(annotationType);
|
||||
}
|
||||
|
||||
private static class AnnotatedWithType extends AbstractMatcher<AnnotatedElement>
|
||||
implements Serializable {
|
||||
private static class AnnotatedWithType extends AbstractMatcher<AnnotatedElement> {
|
||||
private final Class<? extends Annotation> annotationType;
|
||||
|
||||
public AnnotatedWithType(Class<? extends Annotation> annotationType) {
|
||||
|
@ -144,8 +138,6 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "annotatedWith(" + annotationType.getSimpleName() + ".class)";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -157,8 +149,7 @@ public class Matchers {
|
|||
return new AnnotatedWith(annotation);
|
||||
}
|
||||
|
||||
private static class AnnotatedWith extends AbstractMatcher<AnnotatedElement>
|
||||
implements Serializable {
|
||||
private static class AnnotatedWith extends AbstractMatcher<AnnotatedElement> {
|
||||
private final Annotation annotation;
|
||||
|
||||
public AnnotatedWith(Annotation annotation) {
|
||||
|
@ -187,8 +178,6 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "annotatedWith(" + annotation + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -199,8 +188,7 @@ public class Matchers {
|
|||
return new SubclassesOf(superclass);
|
||||
}
|
||||
|
||||
private static class SubclassesOf extends AbstractMatcher<Class>
|
||||
implements Serializable {
|
||||
private static class SubclassesOf extends AbstractMatcher<Class> {
|
||||
private final Class<?> superclass;
|
||||
|
||||
public SubclassesOf(Class<?> superclass) {
|
||||
|
@ -227,8 +215,6 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "subclassesOf(" + superclass.getSimpleName() + ".class)";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -238,8 +224,7 @@ public class Matchers {
|
|||
return new Only(value);
|
||||
}
|
||||
|
||||
private static class Only extends AbstractMatcher<Object>
|
||||
implements Serializable {
|
||||
private static class Only extends AbstractMatcher<Object> {
|
||||
private final Object value;
|
||||
|
||||
public Only(Object value) {
|
||||
|
@ -266,8 +251,6 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "only(" + value + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -277,8 +260,7 @@ public class Matchers {
|
|||
return new IdenticalTo(value);
|
||||
}
|
||||
|
||||
private static class IdenticalTo extends AbstractMatcher<Object>
|
||||
implements Serializable {
|
||||
private static class IdenticalTo extends AbstractMatcher<Object> {
|
||||
private final Object value;
|
||||
|
||||
public IdenticalTo(Object value) {
|
||||
|
@ -305,8 +287,6 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "identicalTo(" + value + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -317,7 +297,7 @@ public class Matchers {
|
|||
return new InPackage(targetPackage);
|
||||
}
|
||||
|
||||
private static class InPackage extends AbstractMatcher<Class> implements Serializable {
|
||||
private static class InPackage extends AbstractMatcher<Class> {
|
||||
private final transient Package targetPackage;
|
||||
private final String packageName;
|
||||
|
||||
|
@ -350,8 +330,6 @@ public class Matchers {
|
|||
public Object readResolve() {
|
||||
return inPackage(Package.getPackage(packageName));
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -364,7 +342,7 @@ public class Matchers {
|
|||
return new InSubpackage(targetPackageName);
|
||||
}
|
||||
|
||||
private static class InSubpackage extends AbstractMatcher<Class> implements Serializable {
|
||||
private static class InSubpackage extends AbstractMatcher<Class> {
|
||||
private final String targetPackageName;
|
||||
|
||||
public InSubpackage(String targetPackageName) {
|
||||
|
@ -393,8 +371,6 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "inSubpackage(" + targetPackageName + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -405,7 +381,7 @@ public class Matchers {
|
|||
return new Returns(returnType);
|
||||
}
|
||||
|
||||
private static class Returns extends AbstractMatcher<Method> implements Serializable {
|
||||
private static class Returns extends AbstractMatcher<Method> {
|
||||
private final Matcher<? super Class<?>> returnType;
|
||||
|
||||
public Returns(Matcher<? super Class<?>> returnType) {
|
||||
|
@ -432,7 +408,5 @@ public class Matchers {
|
|||
public String toString() {
|
||||
return "returns(" + returnType + ")";
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,11 +16,10 @@
|
|||
|
||||
package org.elasticsearch.common.inject.name;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.util.Objects;
|
||||
|
||||
class NamedImpl implements Named, Serializable {
|
||||
class NamedImpl implements Named {
|
||||
|
||||
private final String value;
|
||||
|
||||
|
@ -58,6 +57,4 @@ class NamedImpl implements Named, Serializable {
|
|||
public Class<? extends Annotation> annotationType() {
|
||||
return Named.class;
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
||||
|
|
|
@ -20,9 +20,6 @@ import org.elasticsearch.common.inject.Binder;
|
|||
import org.elasticsearch.common.inject.internal.Errors;
|
||||
import org.elasticsearch.common.inject.internal.SourceProvider;
|
||||
|
||||
import java.io.ObjectStreamException;
|
||||
import java.io.Serializable;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
@ -40,7 +37,7 @@ import java.util.Objects;
|
|||
*
|
||||
* @author crazybob@google.com (Bob Lee)
|
||||
*/
|
||||
public final class Message implements Serializable, Element {
|
||||
public final class Message implements Element {
|
||||
private final String message;
|
||||
private final Throwable cause;
|
||||
private final List<Object> sources;
|
||||
|
@ -131,18 +128,4 @@ public final class Message implements Serializable, Element {
|
|||
public void applyTo(Binder binder) {
|
||||
binder.withSource(getSource()).addError(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* When serialized, we eagerly convert sources to strings. This hurts our formatting, but it
|
||||
* guarantees that the receiving end will be able to read the message.
|
||||
*/
|
||||
private Object writeReplace() throws ObjectStreamException {
|
||||
Object[] sourcesAsStrings = sources.toArray();
|
||||
for (int i = 0; i < sourcesAsStrings.length; i++) {
|
||||
sourcesAsStrings[i] = Errors.convert(sourcesAsStrings[i]).toString();
|
||||
}
|
||||
return new Message(Arrays.asList(sourcesAsStrings), message, cause);
|
||||
}
|
||||
|
||||
private static final long serialVersionUID = 0;
|
||||
}
|
|
@ -45,7 +45,7 @@ public final class Types {
|
|||
* Returns a new parameterized type, applying {@code typeArguments} to
|
||||
* {@code rawType}. The returned type does not have an owner type.
|
||||
*
|
||||
* @return a {@link java.io.Serializable serializable} parameterized type.
|
||||
* @return a parameterized type.
|
||||
*/
|
||||
public static ParameterizedType newParameterizedType(Type rawType, Type... typeArguments) {
|
||||
return newParameterizedTypeWithOwner(null, rawType, typeArguments);
|
||||
|
@ -55,7 +55,7 @@ public final class Types {
|
|||
* Returns a new parameterized type, applying {@code typeArguments} to
|
||||
* {@code rawType} and enclosed by {@code ownerType}.
|
||||
*
|
||||
* @return a {@link java.io.Serializable serializable} parameterized type.
|
||||
* @return a parameterized type.
|
||||
*/
|
||||
public static ParameterizedType newParameterizedTypeWithOwner(
|
||||
Type ownerType, Type rawType, Type... typeArguments) {
|
||||
|
@ -66,7 +66,7 @@ public final class Types {
|
|||
* Returns an array type whose elements are all instances of
|
||||
* {@code componentType}.
|
||||
*
|
||||
* @return a {@link java.io.Serializable serializable} generic array type.
|
||||
* @return a generic array type.
|
||||
*/
|
||||
public static GenericArrayType arrayOf(Type componentType) {
|
||||
return new GenericArrayTypeImpl(componentType);
|
||||
|
@ -95,7 +95,7 @@ public final class Types {
|
|||
* Returns a type modelling a {@link List} whose elements are of type
|
||||
* {@code elementType}.
|
||||
*
|
||||
* @return a {@link java.io.Serializable serializable} parameterized type.
|
||||
* @return a parameterized type.
|
||||
*/
|
||||
public static ParameterizedType listOf(Type elementType) {
|
||||
return newParameterizedType(List.class, elementType);
|
||||
|
@ -105,7 +105,7 @@ public final class Types {
|
|||
* Returns a type modelling a {@link Set} whose elements are of type
|
||||
* {@code elementType}.
|
||||
*
|
||||
* @return a {@link java.io.Serializable serializable} parameterized type.
|
||||
* @return a parameterized type.
|
||||
*/
|
||||
public static ParameterizedType setOf(Type elementType) {
|
||||
return newParameterizedType(Set.class, elementType);
|
||||
|
@ -115,7 +115,7 @@ public final class Types {
|
|||
* Returns a type modelling a {@link Map} whose keys are of type
|
||||
* {@code keyType} and whose values are of type {@code valueType}.
|
||||
*
|
||||
* @return a {@link java.io.Serializable serializable} parameterized type.
|
||||
* @return a parameterized type.
|
||||
*/
|
||||
public static ParameterizedType mapOf(Type keyType, Type valueType) {
|
||||
return newParameterizedType(Map.class, keyType, valueType);
|
||||
|
@ -127,7 +127,7 @@ public final class Types {
|
|||
* Returns a type modelling a {@link Provider} that provides elements of type
|
||||
* {@code elementType}.
|
||||
*
|
||||
* @return a {@link java.io.Serializable serializable} parameterized type.
|
||||
* @return a parameterized type.
|
||||
*/
|
||||
public static ParameterizedType providerOf(Type providedType) {
|
||||
return newParameterizedType(Provider.class, providedType);
|
||||
|
|
|
@ -37,6 +37,7 @@ import org.elasticsearch.common.geo.builders.ShapeBuilder;
|
|||
import org.elasticsearch.common.text.Text;
|
||||
import org.elasticsearch.index.query.QueryBuilder;
|
||||
import org.elasticsearch.index.query.functionscore.ScoreFunctionBuilder;
|
||||
import org.elasticsearch.search.rescore.RescoreBuilder.Rescorer;
|
||||
import org.elasticsearch.search.aggregations.AggregatorFactory;
|
||||
import org.elasticsearch.search.aggregations.pipeline.PipelineAggregatorFactory;
|
||||
import org.joda.time.DateTime;
|
||||
|
@ -692,6 +693,13 @@ public abstract class StreamInput extends InputStream {
|
|||
return readNamedWriteable(ShapeBuilder.class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads a {@link QueryBuilder} from the current stream
|
||||
*/
|
||||
public Rescorer readRescorer() throws IOException {
|
||||
return readNamedWriteable(Rescorer.class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads a {@link org.elasticsearch.index.query.functionscore.ScoreFunctionBuilder} from the current stream
|
||||
*/
|
||||
|
|
|
@ -36,6 +36,7 @@ import org.elasticsearch.common.geo.builders.ShapeBuilder;
|
|||
import org.elasticsearch.common.text.Text;
|
||||
import org.elasticsearch.index.query.QueryBuilder;
|
||||
import org.elasticsearch.index.query.functionscore.ScoreFunctionBuilder;
|
||||
import org.elasticsearch.search.rescore.RescoreBuilder.Rescorer;
|
||||
import org.elasticsearch.search.aggregations.AggregatorFactory;
|
||||
import org.elasticsearch.search.aggregations.pipeline.PipelineAggregatorFactory;
|
||||
import org.joda.time.ReadableInstant;
|
||||
|
@ -44,7 +45,6 @@ import java.io.EOFException;
|
|||
import java.io.FileNotFoundException;
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.nio.channels.ClosedChannelException;
|
||||
import java.nio.file.AccessDeniedException;
|
||||
import java.nio.file.AtomicMoveNotSupportedException;
|
||||
import java.nio.file.DirectoryNotEmptyException;
|
||||
|
@ -693,4 +693,11 @@ public abstract class StreamOutput extends OutputStream {
|
|||
obj.writeTo(this);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Writes a {@link Rescorer} to the current stream
|
||||
*/
|
||||
public void writeRescorer(Rescorer rescorer) throws IOException {
|
||||
writeNamedWriteable(rescorer);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -296,8 +296,6 @@ public class Joda {
|
|||
|
||||
|
||||
public static final DurationFieldType Quarters = new DurationFieldType("quarters") {
|
||||
private static final long serialVersionUID = -8167713675442491871L;
|
||||
|
||||
@Override
|
||||
public DurationField getField(Chronology chronology) {
|
||||
return new ScaledDurationField(chronology.months(), Quarters, 3);
|
||||
|
@ -305,8 +303,6 @@ public class Joda {
|
|||
};
|
||||
|
||||
public static final DateTimeFieldType QuarterOfYear = new DateTimeFieldType("quarterOfYear") {
|
||||
private static final long serialVersionUID = -5677872459807379123L;
|
||||
|
||||
@Override
|
||||
public DurationFieldType getDurationType() {
|
||||
return Quarters;
|
||||
|
|
|
@ -30,8 +30,6 @@ import java.util.logging.LogRecord;
|
|||
* information of the code calling the logger
|
||||
*/
|
||||
public class ESLogRecord extends LogRecord {
|
||||
|
||||
private static final long serialVersionUID = 1107741560233585726L;
|
||||
private static final String FQCN = AbstractESLogger.class.getName();
|
||||
private String sourceClassName;
|
||||
private String sourceMethodName;
|
||||
|
|
|
@ -656,7 +656,7 @@ public final class XMoreLikeThis {
|
|||
}
|
||||
}
|
||||
// term selection is per field, then appended to a single boolean query
|
||||
BooleanQuery bq = new BooleanQuery();
|
||||
BooleanQuery.Builder bq = new BooleanQuery.Builder();
|
||||
for (String fieldName : fieldNames) {
|
||||
Map<String, Int> termFreqMap = new HashMap<>();
|
||||
for (Fields fields : likeFields) {
|
||||
|
@ -667,22 +667,22 @@ public final class XMoreLikeThis {
|
|||
}
|
||||
addToQuery(createQueue(termFreqMap, fieldName), bq);
|
||||
}
|
||||
return bq;
|
||||
return bq.build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Create the More like query from a PriorityQueue
|
||||
*/
|
||||
private Query createQuery(PriorityQueue<ScoreTerm> q) {
|
||||
BooleanQuery query = new BooleanQuery();
|
||||
BooleanQuery.Builder query = new BooleanQuery.Builder();
|
||||
addToQuery(q, query);
|
||||
return query;
|
||||
return query.build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Add to an existing boolean query the More Like This query from this PriorityQueue
|
||||
*/
|
||||
private void addToQuery(PriorityQueue<ScoreTerm> q, BooleanQuery query) {
|
||||
private void addToQuery(PriorityQueue<ScoreTerm> q, BooleanQuery.Builder query) {
|
||||
ScoreTerm scoreTerm;
|
||||
float bestScore = -1;
|
||||
|
||||
|
|
|
@ -76,19 +76,6 @@ public final class Settings implements ToXContent {
|
|||
public static final Settings EMPTY = new Builder().build();
|
||||
private static final Pattern ARRAY_PATTERN = Pattern.compile("(.*)\\.\\d+$");
|
||||
|
||||
/** Name of the setting to use to disable required units for byte size, time settings. */
|
||||
public static final String SETTINGS_REQUIRE_UNITS = "settings_require_units";
|
||||
|
||||
private static boolean settingsRequireUnits = true;
|
||||
|
||||
public static void setSettingsRequireUnits(boolean v) {
|
||||
settingsRequireUnits = v;
|
||||
}
|
||||
|
||||
public static boolean getSettingsRequireUnits() {
|
||||
return settingsRequireUnits;
|
||||
}
|
||||
|
||||
private final Map<String, String> forcedUnderscoreSettings;
|
||||
private SortedMap<String, String> settings;
|
||||
|
||||
|
|
|
@ -213,12 +213,7 @@ public class ByteSizeValue implements Streamable {
|
|||
bytes = 0;
|
||||
} else {
|
||||
// Missing units:
|
||||
if (Settings.getSettingsRequireUnits()) {
|
||||
throw new ElasticsearchParseException("failed to parse setting [{}] with value [{}] as a size in bytes: unit is missing or unrecognized", settingName, sValue);
|
||||
} else {
|
||||
// Leniency default to bytes:
|
||||
bytes = Long.parseLong(sValue);
|
||||
}
|
||||
throw new ElasticsearchParseException("failed to parse setting [{}] with value [{}] as a size in bytes: unit is missing or unrecognized", settingName, sValue);
|
||||
}
|
||||
} catch (NumberFormatException e) {
|
||||
throw new ElasticsearchParseException("failed to parse [{}]", e, sValue);
|
||||
|
|
|
@ -280,13 +280,8 @@ public class TimeValue implements Streamable {
|
|||
// Allow this special value to be unit-less:
|
||||
millis = 0;
|
||||
} else {
|
||||
if (Settings.getSettingsRequireUnits()) {
|
||||
// Missing units:
|
||||
throw new ElasticsearchParseException("Failed to parse setting [{}] with value [{}] as a time value: unit is missing or unrecognized", settingName, sValue);
|
||||
} else {
|
||||
// Leniency default to msec for bwc:
|
||||
millis = Long.parseLong(sValue);
|
||||
}
|
||||
// Missing units:
|
||||
throw new ElasticsearchParseException("Failed to parse setting [{}] with value [{}] as a time value: unit is missing or unrecognized", settingName, sValue);
|
||||
}
|
||||
return new TimeValue(millis, TimeUnit.MILLISECONDS);
|
||||
} catch (NumberFormatException e) {
|
||||
|
|
|
@ -180,9 +180,6 @@ public abstract class BaseFuture<V> implements Future<V> {
|
|||
* pass around a -1 everywhere.
|
||||
*/
|
||||
static final class Sync<V> extends AbstractQueuedSynchronizer {
|
||||
|
||||
private static final long serialVersionUID = 0L;
|
||||
|
||||
/* Valid states. */
|
||||
static final int RUNNING = 0;
|
||||
static final int COMPLETING = 1;
|
||||
|
|
|
@ -133,6 +133,9 @@ public class XContentFactory {
|
|||
* Returns the {@link org.elasticsearch.common.xcontent.XContent} for the provided content type.
|
||||
*/
|
||||
public static XContent xContent(XContentType type) {
|
||||
if (type == null) {
|
||||
throw new IllegalArgumentException("Cannot get xcontent for unknown type");
|
||||
}
|
||||
return type.xContent();
|
||||
}
|
||||
|
||||
|
|
|
@ -22,11 +22,11 @@ package org.elasticsearch.index;
|
|||
import java.io.Closeable;
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Path;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.ScheduledFuture;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
|
||||
|
@ -42,6 +42,8 @@ import org.elasticsearch.cluster.routing.ShardRouting;
|
|||
import org.elasticsearch.common.Nullable;
|
||||
import org.elasticsearch.common.collect.ImmutableOpenMap;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.common.unit.TimeValue;
|
||||
import org.elasticsearch.common.util.concurrent.FutureUtils;
|
||||
import org.elasticsearch.common.xcontent.XContentFactory;
|
||||
import org.elasticsearch.common.xcontent.XContentParser;
|
||||
import org.elasticsearch.env.NodeEnvironment;
|
||||
|
@ -59,6 +61,7 @@ import org.elasticsearch.index.fielddata.IndexFieldDataService;
|
|||
import org.elasticsearch.index.mapper.MapperService;
|
||||
import org.elasticsearch.index.query.ParsedQuery;
|
||||
import org.elasticsearch.index.query.QueryShardContext;
|
||||
import org.elasticsearch.index.search.stats.SearchSlowLog;
|
||||
import org.elasticsearch.index.shard.IndexEventListener;
|
||||
import org.elasticsearch.index.shard.IndexSearcherWrapper;
|
||||
import org.elasticsearch.index.shard.IndexShard;
|
||||
|
@ -104,6 +107,9 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
private final IndexSettings indexSettings;
|
||||
private final IndexingSlowLog slowLog;
|
||||
private final IndexingOperationListener[] listeners;
|
||||
private volatile AsyncRefreshTask refreshTask;
|
||||
private final AsyncTranslogFSync fsyncTask;
|
||||
private final SearchSlowLog searchSlowLog;
|
||||
|
||||
public IndexService(IndexSettings indexSettings, NodeEnvironment nodeEnv,
|
||||
SimilarityService similarityService,
|
||||
|
@ -140,6 +146,14 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
this.listeners = new IndexingOperationListener[1+listenersIn.length];
|
||||
this.listeners[0] = slowLog;
|
||||
System.arraycopy(listenersIn, 0, this.listeners, 1, listenersIn.length);
|
||||
// kick off async ops for the first shard in this index
|
||||
if (this.indexSettings.getTranslogSyncInterval().millis() != 0) {
|
||||
this.fsyncTask = new AsyncTranslogFSync(this);
|
||||
} else {
|
||||
this.fsyncTask = null;
|
||||
}
|
||||
this.refreshTask = new AsyncRefreshTask(this);
|
||||
searchSlowLog = new SearchSlowLog(indexSettings.getSettings());
|
||||
}
|
||||
|
||||
public int numberOfShards() {
|
||||
|
@ -215,7 +229,7 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
}
|
||||
}
|
||||
} finally {
|
||||
IOUtils.close(bitsetFilterCache, indexCache, mapperService, indexFieldData, analysisService);
|
||||
IOUtils.close(bitsetFilterCache, indexCache, mapperService, indexFieldData, analysisService, refreshTask, fsyncTask);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -302,18 +316,13 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
(primary && IndexMetaData.isOnSharedFilesystem(indexSettings));
|
||||
store = new Store(shardId, this.indexSettings, indexStore.newDirectoryService(path), lock, new StoreCloseListener(shardId, canDeleteShardContent, () -> nodeServicesProvider.getIndicesQueryCache().onClose(shardId)));
|
||||
if (useShadowEngine(primary, indexSettings)) {
|
||||
indexShard = new ShadowIndexShard(shardId, this.indexSettings, path, store, indexCache, mapperService, similarityService, indexFieldData, engineFactory, eventListener, searcherWrapper, nodeServicesProvider); // no indexing listeners - shadow engines don't index
|
||||
indexShard = new ShadowIndexShard(shardId, this.indexSettings, path, store, indexCache, mapperService, similarityService, indexFieldData, engineFactory, eventListener, searcherWrapper, nodeServicesProvider, searchSlowLog); // no indexing listeners - shadow engines don't index
|
||||
} else {
|
||||
indexShard = new IndexShard(shardId, this.indexSettings, path, store, indexCache, mapperService, similarityService, indexFieldData, engineFactory, eventListener, searcherWrapper, nodeServicesProvider, listeners);
|
||||
indexShard = new IndexShard(shardId, this.indexSettings, path, store, indexCache, mapperService, similarityService, indexFieldData, engineFactory, eventListener, searcherWrapper, nodeServicesProvider, searchSlowLog, listeners);
|
||||
}
|
||||
|
||||
eventListener.indexShardStateChanged(indexShard, null, indexShard.state(), "shard created");
|
||||
eventListener.afterIndexShardCreated(indexShard);
|
||||
indexShard.updateRoutingEntry(routing, true);
|
||||
if (shards.isEmpty() && this.indexSettings.getTranslogSyncInterval().millis() != 0) {
|
||||
ThreadPool threadPool = nodeServicesProvider.getThreadPool();
|
||||
new AsyncTranslogFSync(this, threadPool).schedule(); // kick this off if we are the first shard in this service.
|
||||
}
|
||||
shards = newMapBuilder(shards).put(shardId.id(), indexShard).immutableMap();
|
||||
success = true;
|
||||
return indexShard;
|
||||
|
@ -404,6 +413,14 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
return new QueryShardContext(indexSettings, nodeServicesProvider.getClient(), indexCache.bitsetFilterCache(), indexFieldData, mapperService(), similarityService(), nodeServicesProvider.getScriptService(), nodeServicesProvider.getIndicesQueriesRegistry());
|
||||
}
|
||||
|
||||
ThreadPool getThreadPool() {
|
||||
return nodeServicesProvider.getThreadPool();
|
||||
}
|
||||
|
||||
public SearchSlowLog getSearchSlowLog() {
|
||||
return searchSlowLog;
|
||||
}
|
||||
|
||||
private class StoreCloseListener implements Store.OnClose {
|
||||
private final ShardId shardId;
|
||||
private final boolean ownsShard;
|
||||
|
@ -552,9 +569,9 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
final Settings settings = indexSettings.getSettings();
|
||||
for (final IndexShard shard : this.shards.values()) {
|
||||
try {
|
||||
shard.onRefreshSettings(settings);
|
||||
shard.onSettingsChanged();
|
||||
} catch (Exception e) {
|
||||
logger.warn("[{}] failed to refresh shard settings", e, shard.shardId().id());
|
||||
logger.warn("[{}] failed to notify shard about setting change", e, shard.shardId().id());
|
||||
}
|
||||
}
|
||||
try {
|
||||
|
@ -567,9 +584,27 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
} catch (Exception e) {
|
||||
logger.warn("failed to refresh slowlog settings", e);
|
||||
}
|
||||
|
||||
try {
|
||||
searchSlowLog.onRefreshSettings(settings); // this will be refactored soon anyway so duplication is ok here
|
||||
} catch (Exception e) {
|
||||
logger.warn("failed to refresh slowlog settings", e);
|
||||
}
|
||||
if (refreshTask.getInterval().equals(indexSettings.getRefreshInterval()) == false) {
|
||||
rescheduleRefreshTasks();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void rescheduleRefreshTasks() {
|
||||
try {
|
||||
refreshTask.close();
|
||||
} finally {
|
||||
refreshTask = new AsyncRefreshTask(this);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public interface ShardStoreDeleter {
|
||||
void deleteShardStore(String reason, ShardLock lock, IndexSettings indexSettings) throws IOException;
|
||||
|
||||
|
@ -605,40 +640,170 @@ public final class IndexService extends AbstractIndexComponent implements IndexC
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* FSyncs the translog for all shards of this index in a defined interval.
|
||||
*/
|
||||
final static class AsyncTranslogFSync implements Runnable {
|
||||
private final IndexService indexService;
|
||||
private final ThreadPool threadPool;
|
||||
|
||||
AsyncTranslogFSync(IndexService indexService, ThreadPool threadPool) {
|
||||
this.indexService = indexService;
|
||||
this.threadPool = threadPool;
|
||||
}
|
||||
|
||||
boolean mustRun() {
|
||||
// don't re-schedule if its closed or if we dont' have a single shard here..., we are done
|
||||
return (indexService.closed.get() || indexService.shards.isEmpty()) == false;
|
||||
}
|
||||
|
||||
void schedule() {
|
||||
threadPool.schedule(indexService.getIndexSettings().getTranslogSyncInterval(), ThreadPool.Names.SAME, AsyncTranslogFSync.this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
if (mustRun()) {
|
||||
threadPool.executor(ThreadPool.Names.FLUSH).execute(() -> {
|
||||
indexService.maybeFSyncTranslogs();
|
||||
if (mustRun()) {
|
||||
schedule();
|
||||
}
|
||||
});
|
||||
private void maybeRefreshEngine() {
|
||||
if (indexSettings.getRefreshInterval().millis() > 0) {
|
||||
for (IndexShard shard : this.shards.values()) {
|
||||
switch (shard.state()) {
|
||||
case CREATED:
|
||||
case RECOVERING:
|
||||
case CLOSED:
|
||||
continue;
|
||||
case POST_RECOVERY:
|
||||
case STARTED:
|
||||
case RELOCATED:
|
||||
try {
|
||||
shard.refresh("schedule");
|
||||
} catch (EngineClosedException | AlreadyClosedException ex) {
|
||||
// fine - continue;
|
||||
}
|
||||
continue;
|
||||
default:
|
||||
throw new IllegalStateException("unknown state: " + shard.state());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static abstract class BaseAsyncTask implements Runnable, Closeable {
|
||||
protected final IndexService indexService;
|
||||
protected final ThreadPool threadPool;
|
||||
private final TimeValue interval;
|
||||
private ScheduledFuture<?> scheduledFuture;
|
||||
private final AtomicBoolean closed = new AtomicBoolean(false);
|
||||
private volatile Exception lastThrownException;
|
||||
|
||||
BaseAsyncTask(IndexService indexService, TimeValue interval) {
|
||||
this.indexService = indexService;
|
||||
this.threadPool = indexService.getThreadPool();
|
||||
this.interval = interval;
|
||||
onTaskCompletion();
|
||||
}
|
||||
|
||||
boolean mustReschedule() {
|
||||
// don't re-schedule if its closed or if we dont' have a single shard here..., we are done
|
||||
return indexService.closed.get() == false
|
||||
&& closed.get() == false && interval.millis() > 0;
|
||||
}
|
||||
|
||||
private synchronized void onTaskCompletion() {
|
||||
if (mustReschedule()) {
|
||||
indexService.logger.debug("scheduling {} every {}", toString(), interval);
|
||||
this.scheduledFuture = threadPool.schedule(interval, getThreadPool(), BaseAsyncTask.this);
|
||||
} else {
|
||||
indexService.logger.debug("scheduled {} disabled", toString());
|
||||
this.scheduledFuture = null;
|
||||
}
|
||||
}
|
||||
|
||||
boolean isScheduled() {
|
||||
return scheduledFuture != null;
|
||||
}
|
||||
|
||||
public final void run() {
|
||||
try {
|
||||
runInternal();
|
||||
} catch (Exception ex) {
|
||||
if (lastThrownException == null || sameException(lastThrownException, ex) == false) {
|
||||
// prevent the annoying fact of logging the same stuff all the time with an interval of 1 sec will spam all your logs
|
||||
indexService.logger.warn("failed to run task {} - suppressing re-occurring exceptions unless the exception changes", ex, toString());
|
||||
lastThrownException = ex;
|
||||
}
|
||||
} finally {
|
||||
onTaskCompletion();
|
||||
}
|
||||
}
|
||||
|
||||
private static boolean sameException(Exception left, Exception right) {
|
||||
if (left.getClass() == right.getClass()) {
|
||||
if ((left.getMessage() != null && left.getMessage().equals(right.getMessage()))
|
||||
|| left.getMessage() == right.getMessage()) {
|
||||
StackTraceElement[] stackTraceLeft = left.getStackTrace();
|
||||
StackTraceElement[] stackTraceRight = right.getStackTrace();
|
||||
if (stackTraceLeft.length == stackTraceRight.length) {
|
||||
for (int i = 0; i < stackTraceLeft.length; i++) {
|
||||
if (stackTraceLeft[i].equals(stackTraceRight[i]) == false) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
protected abstract void runInternal();
|
||||
|
||||
protected String getThreadPool() {
|
||||
return ThreadPool.Names.SAME;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() {
|
||||
if (closed.compareAndSet(false, true)) {
|
||||
FutureUtils.cancel(scheduledFuture);
|
||||
scheduledFuture = null;
|
||||
}
|
||||
}
|
||||
|
||||
TimeValue getInterval() {
|
||||
return interval;
|
||||
}
|
||||
|
||||
boolean isClosed() {
|
||||
return this.closed.get();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* FSyncs the translog for all shards of this index in a defined interval.
|
||||
*/
|
||||
final static class AsyncTranslogFSync extends BaseAsyncTask {
|
||||
|
||||
AsyncTranslogFSync(IndexService indexService) {
|
||||
super(indexService, indexService.getIndexSettings().getTranslogSyncInterval());
|
||||
}
|
||||
|
||||
protected String getThreadPool() {
|
||||
return ThreadPool.Names.FLUSH;
|
||||
}
|
||||
@Override
|
||||
protected void runInternal() {
|
||||
indexService.maybeFSyncTranslogs();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "translog_sync";
|
||||
}
|
||||
}
|
||||
|
||||
final class AsyncRefreshTask extends BaseAsyncTask {
|
||||
|
||||
AsyncRefreshTask(IndexService indexService) {
|
||||
super(indexService, indexService.getIndexSettings().getRefreshInterval());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void runInternal() {
|
||||
indexService.maybeRefreshEngine();
|
||||
}
|
||||
|
||||
protected String getThreadPool() {
|
||||
return ThreadPool.Names.REFRESH;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "refresh";
|
||||
}
|
||||
}
|
||||
|
||||
AsyncRefreshTask getRefreshTask() { // for tests
|
||||
return refreshTask;
|
||||
}
|
||||
|
||||
AsyncTranslogFSync getFsyncTask() { // for tests
|
||||
return fsyncTask;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
*/
|
||||
package org.elasticsearch.index;
|
||||
|
||||
import org.apache.lucene.index.MergePolicy;
|
||||
import org.elasticsearch.Version;
|
||||
import org.elasticsearch.cluster.metadata.IndexMetaData;
|
||||
import org.elasticsearch.common.ParseFieldMatcher;
|
||||
|
@ -25,6 +26,8 @@ import org.elasticsearch.common.logging.ESLogger;
|
|||
import org.elasticsearch.common.logging.Loggers;
|
||||
import org.elasticsearch.common.regex.Regex;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.common.unit.ByteSizeUnit;
|
||||
import org.elasticsearch.common.unit.ByteSizeValue;
|
||||
import org.elasticsearch.common.unit.TimeValue;
|
||||
import org.elasticsearch.index.mapper.internal.AllFieldMapper;
|
||||
import org.elasticsearch.index.translog.Translog;
|
||||
|
@ -35,6 +38,7 @@ import java.util.Collection;
|
|||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Predicate;
|
||||
|
||||
|
@ -54,6 +58,16 @@ public final class IndexSettings {
|
|||
public static final String ALLOW_UNMAPPED = "index.query.parse.allow_unmapped_fields";
|
||||
public static final String INDEX_TRANSLOG_SYNC_INTERVAL = "index.translog.sync_interval";
|
||||
public static final String INDEX_TRANSLOG_DURABILITY = "index.translog.durability";
|
||||
public static final String INDEX_REFRESH_INTERVAL = "index.refresh_interval";
|
||||
public static final TimeValue DEFAULT_REFRESH_INTERVAL = new TimeValue(1, TimeUnit.SECONDS);
|
||||
public static final String INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE = "index.translog.flush_threshold_size";
|
||||
public static final TimeValue DEFAULT_GC_DELETES = TimeValue.timeValueSeconds(60);
|
||||
|
||||
/**
|
||||
* Index setting to enable / disable deletes garbage collection.
|
||||
* This setting is realtime updateable
|
||||
*/
|
||||
public static final String INDEX_GC_DELETES_SETTING = "index.gc_deletes";
|
||||
|
||||
private final String uuid;
|
||||
private final List<Consumer<Settings>> updateListeners;
|
||||
|
@ -76,6 +90,13 @@ public final class IndexSettings {
|
|||
private final Predicate<String> indexNameMatcher;
|
||||
private volatile Translog.Durability durability;
|
||||
private final TimeValue syncInterval;
|
||||
private volatile TimeValue refreshInterval;
|
||||
private volatile ByteSizeValue flushThresholdSize;
|
||||
private final MergeSchedulerConfig mergeSchedulerConfig;
|
||||
private final MergePolicyConfig mergePolicyConfig;
|
||||
|
||||
private long gcDeletesInMillis = DEFAULT_GC_DELETES.millis();
|
||||
|
||||
|
||||
/**
|
||||
* Returns the default search field for this index.
|
||||
|
@ -156,7 +177,11 @@ public final class IndexSettings {
|
|||
final String value = settings.get(INDEX_TRANSLOG_DURABILITY, Translog.Durability.REQUEST.name());
|
||||
this.durability = getFromSettings(settings, Translog.Durability.REQUEST);
|
||||
syncInterval = settings.getAsTime(INDEX_TRANSLOG_SYNC_INTERVAL, TimeValue.timeValueSeconds(5));
|
||||
|
||||
refreshInterval = settings.getAsTime(INDEX_REFRESH_INTERVAL, DEFAULT_REFRESH_INTERVAL);
|
||||
flushThresholdSize = settings.getAsBytesSize(INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE, new ByteSizeValue(512, ByteSizeUnit.MB));
|
||||
mergeSchedulerConfig = new MergeSchedulerConfig(settings);
|
||||
gcDeletesInMillis = settings.getAsTime(IndexSettings.INDEX_GC_DELETES_SETTING, DEFAULT_GC_DELETES).getMillis();
|
||||
this.mergePolicyConfig = new MergePolicyConfig(logger, settings);
|
||||
assert indexNameMatcher.test(indexMetaData.getIndex());
|
||||
}
|
||||
|
||||
|
@ -346,10 +371,83 @@ public final class IndexSettings {
|
|||
logger.info("updating durability from [{}] to [{}]", this.durability, durability);
|
||||
this.durability = durability;
|
||||
}
|
||||
|
||||
TimeValue refreshInterval = settings.getAsTime(IndexSettings.INDEX_REFRESH_INTERVAL, this.refreshInterval);
|
||||
if (!refreshInterval.equals(this.refreshInterval)) {
|
||||
logger.info("updating refresh_interval from [{}] to [{}]", this.refreshInterval, refreshInterval);
|
||||
this.refreshInterval = refreshInterval;
|
||||
}
|
||||
|
||||
ByteSizeValue flushThresholdSize = settings.getAsBytesSize(IndexSettings.INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE, this.flushThresholdSize);
|
||||
if (!flushThresholdSize.equals(this.flushThresholdSize)) {
|
||||
logger.info("updating flush_threshold_size from [{}] to [{}]", this.flushThresholdSize, flushThresholdSize);
|
||||
this.flushThresholdSize = flushThresholdSize;
|
||||
}
|
||||
|
||||
final int maxThreadCount = settings.getAsInt(MergeSchedulerConfig.MAX_THREAD_COUNT, mergeSchedulerConfig.getMaxThreadCount());
|
||||
if (maxThreadCount != mergeSchedulerConfig.getMaxThreadCount()) {
|
||||
logger.info("updating [{}] from [{}] to [{}]", MergeSchedulerConfig.MAX_THREAD_COUNT, mergeSchedulerConfig.getMaxMergeCount(), maxThreadCount);
|
||||
mergeSchedulerConfig.setMaxThreadCount(maxThreadCount);
|
||||
}
|
||||
|
||||
final int maxMergeCount = settings.getAsInt(MergeSchedulerConfig.MAX_MERGE_COUNT, mergeSchedulerConfig.getMaxMergeCount());
|
||||
if (maxMergeCount != mergeSchedulerConfig.getMaxMergeCount()) {
|
||||
logger.info("updating [{}] from [{}] to [{}]", MergeSchedulerConfig.MAX_MERGE_COUNT, mergeSchedulerConfig.getMaxMergeCount(), maxMergeCount);
|
||||
mergeSchedulerConfig.setMaxMergeCount(maxMergeCount);
|
||||
}
|
||||
|
||||
final boolean autoThrottle = settings.getAsBoolean(MergeSchedulerConfig.AUTO_THROTTLE, mergeSchedulerConfig.isAutoThrottle());
|
||||
if (autoThrottle != mergeSchedulerConfig.isAutoThrottle()) {
|
||||
logger.info("updating [{}] from [{}] to [{}]", MergeSchedulerConfig.AUTO_THROTTLE, mergeSchedulerConfig.isAutoThrottle(), autoThrottle);
|
||||
mergeSchedulerConfig.setAutoThrottle(autoThrottle);
|
||||
}
|
||||
|
||||
long gcDeletesInMillis = settings.getAsTime(IndexSettings.INDEX_GC_DELETES_SETTING, TimeValue.timeValueMillis(this.gcDeletesInMillis)).getMillis();
|
||||
if (gcDeletesInMillis != this.gcDeletesInMillis) {
|
||||
logger.info("updating {} from [{}] to [{}]", IndexSettings.INDEX_GC_DELETES_SETTING, TimeValue.timeValueMillis(this.gcDeletesInMillis), TimeValue.timeValueMillis(gcDeletesInMillis));
|
||||
this.gcDeletesInMillis = gcDeletesInMillis;
|
||||
}
|
||||
|
||||
mergePolicyConfig.onRefreshSettings(settings);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the translog sync interval. This is the interval in which the transaction log is asynchronously fsynced unless
|
||||
* the transaction log is fsyncing on every operations
|
||||
*/
|
||||
public TimeValue getTranslogSyncInterval() {
|
||||
return syncInterval;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns this interval in which the shards of this index are asynchronously refreshed. <tt>-1</tt> means async refresh is disabled.
|
||||
*/
|
||||
public TimeValue getRefreshInterval() {
|
||||
return refreshInterval;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the transaction log threshold size when to forcefully flush the index and clear the transaction log.
|
||||
*/
|
||||
public ByteSizeValue getFlushThresholdSize() { return flushThresholdSize; }
|
||||
|
||||
/**
|
||||
* Returns the {@link MergeSchedulerConfig}
|
||||
*/
|
||||
public MergeSchedulerConfig getMergeSchedulerConfig() { return mergeSchedulerConfig; }
|
||||
|
||||
/**
|
||||
* Returns the GC deletes cycle in milliseconds.
|
||||
*/
|
||||
public long getGcDeletesInMillis() {
|
||||
return gcDeletesInMillis;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the merge policy that should be used for this index.
|
||||
*/
|
||||
public MergePolicy getMergePolicy() {
|
||||
return mergePolicyConfig.getMergePolicy();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
package org.elasticsearch.index.shard;
|
||||
package org.elasticsearch.index;
|
||||
|
||||
import org.apache.lucene.index.MergePolicy;
|
||||
import org.apache.lucene.index.NoMergePolicy;
|
||||
|
@ -33,61 +33,61 @@ import org.elasticsearch.common.unit.ByteSizeValue;
|
|||
* where the index data is stored, and are immutable up to delete markers.
|
||||
* Segments are, periodically, merged into larger segments to keep the
|
||||
* index size at bay and expunge deletes.
|
||||
*
|
||||
*
|
||||
* <p>
|
||||
* Merges select segments of approximately equal size, subject to an allowed
|
||||
* number of segments per tier. The merge policy is able to merge
|
||||
* non-adjacent segments, and separates how many segments are merged at once from how many
|
||||
* segments are allowed per tier. It also does not over-merge (i.e., cascade merges).
|
||||
*
|
||||
*
|
||||
* <p>
|
||||
* All merge policy settings are <b>dynamic</b> and can be updated on a live index.
|
||||
* The merge policy has the following settings:
|
||||
*
|
||||
*
|
||||
* <ul>
|
||||
* <li><code>index.merge.policy.expunge_deletes_allowed</code>:
|
||||
*
|
||||
*
|
||||
* When expungeDeletes is called, we only merge away a segment if its delete
|
||||
* percentage is over this threshold. Default is <code>10</code>.
|
||||
*
|
||||
*
|
||||
* <li><code>index.merge.policy.floor_segment</code>:
|
||||
*
|
||||
*
|
||||
* Segments smaller than this are "rounded up" to this size, i.e. treated as
|
||||
* equal (floor) size for merge selection. This is to prevent frequent
|
||||
* flushing of tiny segments, thus preventing a long tail in the index. Default
|
||||
* is <code>2mb</code>.
|
||||
*
|
||||
*
|
||||
* <li><code>index.merge.policy.max_merge_at_once</code>:
|
||||
*
|
||||
*
|
||||
* Maximum number of segments to be merged at a time during "normal" merging.
|
||||
* Default is <code>10</code>.
|
||||
*
|
||||
*
|
||||
* <li><code>index.merge.policy.max_merge_at_once_explicit</code>:
|
||||
*
|
||||
*
|
||||
* Maximum number of segments to be merged at a time, during force merge or
|
||||
* expungeDeletes. Default is <code>30</code>.
|
||||
*
|
||||
*
|
||||
* <li><code>index.merge.policy.max_merged_segment</code>:
|
||||
*
|
||||
*
|
||||
* Maximum sized segment to produce during normal merging (not explicit
|
||||
* force merge). This setting is approximate: the estimate of the merged
|
||||
* segment size is made by summing sizes of to-be-merged segments
|
||||
* (compensating for percent deleted docs). Default is <code>5gb</code>.
|
||||
*
|
||||
*
|
||||
* <li><code>index.merge.policy.segments_per_tier</code>:
|
||||
*
|
||||
*
|
||||
* Sets the allowed number of segments per tier. Smaller values mean more
|
||||
* merging but fewer segments. Default is <code>10</code>. Note, this value needs to be
|
||||
* >= than the <code>max_merge_at_once</code> otherwise you'll force too many merges to
|
||||
* occur.
|
||||
*
|
||||
*
|
||||
* <li><code>index.merge.policy.reclaim_deletes_weight</code>:
|
||||
*
|
||||
*
|
||||
* Controls how aggressively merges that reclaim more deletions are favored.
|
||||
* Higher values favor selecting merges that reclaim deletions. A value of
|
||||
* <code>0.0</code> means deletions don't impact merge selection. Defaults to <code>2.0</code>.
|
||||
* </ul>
|
||||
*
|
||||
*
|
||||
* <p>
|
||||
* For normal merging, the policy first computes a "budget" of how many
|
||||
* segments are allowed to be in the index. If the index is over-budget,
|
||||
|
@ -97,13 +97,13 @@ import org.elasticsearch.common.unit.ByteSizeValue;
|
|||
* smallest seg), total merge size and pct deletes reclaimed, so that
|
||||
* merges with lower skew, smaller size and those reclaiming more deletes,
|
||||
* are favored.
|
||||
*
|
||||
*
|
||||
* <p>
|
||||
* If a merge will produce a segment that's larger than
|
||||
* <code>max_merged_segment</code> then the policy will merge fewer segments (down to
|
||||
* 1 at once, if that one has deletions) to keep the segment size under
|
||||
* budget.
|
||||
*
|
||||
*
|
||||
* <p>
|
||||
* Note, this can mean that for large shards that holds many gigabytes of
|
||||
* data, the default of <code>max_merged_segment</code> (<code>5gb</code>) can cause for many
|
||||
|
@ -138,7 +138,7 @@ public final class MergePolicyConfig {
|
|||
public static final String INDEX_MERGE_ENABLED = "index.merge.enabled";
|
||||
|
||||
|
||||
public MergePolicyConfig(ESLogger logger, Settings indexSettings) {
|
||||
MergePolicyConfig(ESLogger logger, Settings indexSettings) {
|
||||
this.logger = logger;
|
||||
this.noCFSRatio = parseNoCFSRatio(indexSettings.get(INDEX_COMPOUND_FORMAT, Double.toString(TieredMergePolicy.DEFAULT_NO_CFS_RATIO)));
|
||||
double forceMergeDeletesPctAllowed = indexSettings.getAsDouble("index.merge.policy.expunge_deletes_allowed", DEFAULT_EXPUNGE_DELETES_ALLOWED); // percentage
|
||||
|
@ -180,11 +180,11 @@ public final class MergePolicyConfig {
|
|||
return maxMergeAtOnce;
|
||||
}
|
||||
|
||||
public MergePolicy getMergePolicy() {
|
||||
MergePolicy getMergePolicy() {
|
||||
return mergesEnabled ? mergePolicy : NoMergePolicy.INSTANCE;
|
||||
}
|
||||
|
||||
public void onRefreshSettings(Settings settings) {
|
||||
void onRefreshSettings(Settings settings) {
|
||||
final double oldExpungeDeletesPctAllowed = mergePolicy.getForceMergeDeletesPctAllowed();
|
||||
final double expungeDeletesPctAllowed = settings.getAsDouble(INDEX_MERGE_POLICY_EXPUNGE_DELETES_ALLOWED, oldExpungeDeletesPctAllowed);
|
||||
if (expungeDeletesPctAllowed != oldExpungeDeletesPctAllowed) {
|
||||
|
@ -243,7 +243,7 @@ public final class MergePolicyConfig {
|
|||
}
|
||||
}
|
||||
|
||||
public static double parseNoCFSRatio(String noCFSRatio) {
|
||||
private static double parseNoCFSRatio(String noCFSRatio) {
|
||||
noCFSRatio = noCFSRatio.trim();
|
||||
if (noCFSRatio.equalsIgnoreCase("true")) {
|
||||
return 1.0d;
|
||||
|
@ -262,7 +262,7 @@ public final class MergePolicyConfig {
|
|||
}
|
||||
}
|
||||
|
||||
public static String formatNoCFSRatio(double ratio) {
|
||||
private static String formatNoCFSRatio(double ratio) {
|
||||
if (ratio == 1.0) {
|
||||
return Boolean.TRUE.toString();
|
||||
} else if (ratio == 0.0) {
|
|
@ -17,7 +17,7 @@
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
package org.elasticsearch.index.shard;
|
||||
package org.elasticsearch.index;
|
||||
|
||||
import org.apache.lucene.index.ConcurrentMergeScheduler;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
|
@ -60,8 +60,7 @@ public final class MergeSchedulerConfig {
|
|||
private volatile int maxThreadCount;
|
||||
private volatile int maxMergeCount;
|
||||
|
||||
public MergeSchedulerConfig(IndexSettings indexSettings) {
|
||||
final Settings settings = indexSettings.getSettings();
|
||||
MergeSchedulerConfig(Settings settings) {
|
||||
maxThreadCount = settings.getAsInt(MAX_THREAD_COUNT, Math.max(1, Math.min(4, EsExecutors.boundedNumberOfProcessors(settings) / 2)));
|
||||
maxMergeCount = settings.getAsInt(MAX_MERGE_COUNT, maxThreadCount + 5);
|
||||
this.autoThrottle = settings.getAsBoolean(AUTO_THROTTLE, true);
|
||||
|
@ -78,7 +77,7 @@ public final class MergeSchedulerConfig {
|
|||
/**
|
||||
* Enables / disables auto throttling on the {@link ConcurrentMergeScheduler}
|
||||
*/
|
||||
public void setAutoThrottle(boolean autoThrottle) {
|
||||
void setAutoThrottle(boolean autoThrottle) {
|
||||
this.autoThrottle = autoThrottle;
|
||||
}
|
||||
|
||||
|
@ -93,7 +92,7 @@ public final class MergeSchedulerConfig {
|
|||
* Expert: directly set the maximum number of merge threads and
|
||||
* simultaneous merges allowed.
|
||||
*/
|
||||
public void setMaxThreadCount(int maxThreadCount) {
|
||||
void setMaxThreadCount(int maxThreadCount) {
|
||||
this.maxThreadCount = maxThreadCount;
|
||||
}
|
||||
|
||||
|
@ -108,7 +107,7 @@ public final class MergeSchedulerConfig {
|
|||
*
|
||||
* Expert: set the maximum number of simultaneous merges allowed.
|
||||
*/
|
||||
public void setMaxMergeCount(int maxMergeCount) {
|
||||
void setMaxMergeCount(int maxMergeCount) {
|
||||
this.maxMergeCount = maxMergeCount;
|
||||
}
|
||||
}
|
|
@ -36,7 +36,7 @@ import org.elasticsearch.common.util.concurrent.EsExecutors;
|
|||
import org.elasticsearch.index.IndexSettings;
|
||||
import org.elasticsearch.index.merge.MergeStats;
|
||||
import org.elasticsearch.index.merge.OnGoingMerge;
|
||||
import org.elasticsearch.index.shard.MergeSchedulerConfig;
|
||||
import org.elasticsearch.index.MergeSchedulerConfig;
|
||||
import org.elasticsearch.index.shard.ShardId;
|
||||
|
||||
import java.io.IOException;
|
||||
|
@ -67,8 +67,8 @@ class ElasticsearchConcurrentMergeScheduler extends ConcurrentMergeScheduler {
|
|||
private final Set<OnGoingMerge> readOnlyOnGoingMerges = Collections.unmodifiableSet(onGoingMerges);
|
||||
private final MergeSchedulerConfig config;
|
||||
|
||||
public ElasticsearchConcurrentMergeScheduler(ShardId shardId, IndexSettings indexSettings, MergeSchedulerConfig config) {
|
||||
this.config = config;
|
||||
public ElasticsearchConcurrentMergeScheduler(ShardId shardId, IndexSettings indexSettings) {
|
||||
this.config = indexSettings.getMergeSchedulerConfig();
|
||||
this.shardId = shardId;
|
||||
this.indexSettings = indexSettings.getSettings();
|
||||
this.logger = Loggers.getLogger(getClass(), this.indexSettings, shardId);
|
||||
|
|
|
@ -31,7 +31,6 @@ import org.elasticsearch.common.unit.ByteSizeValue;
|
|||
import org.elasticsearch.common.unit.TimeValue;
|
||||
import org.elasticsearch.index.IndexSettings;
|
||||
import org.elasticsearch.index.codec.CodecService;
|
||||
import org.elasticsearch.index.shard.MergeSchedulerConfig;
|
||||
import org.elasticsearch.index.shard.ShardId;
|
||||
import org.elasticsearch.index.shard.TranslogRecoveryPerformer;
|
||||
import org.elasticsearch.index.store.Store;
|
||||
|
@ -39,8 +38,6 @@ import org.elasticsearch.index.translog.TranslogConfig;
|
|||
import org.elasticsearch.indices.IndexingMemoryController;
|
||||
import org.elasticsearch.threadpool.ThreadPool;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
/*
|
||||
* Holds all the configuration that is used to create an {@link Engine}.
|
||||
* Once {@link Engine} has been created with this object, changes to this
|
||||
|
@ -51,7 +48,6 @@ public final class EngineConfig {
|
|||
private final TranslogRecoveryPerformer translogRecoveryPerformer;
|
||||
private final IndexSettings indexSettings;
|
||||
private final ByteSizeValue indexingBufferSize;
|
||||
private long gcDeletesInMillis = DEFAULT_GC_DELETES.millis();
|
||||
private volatile boolean enableGcDeletes = true;
|
||||
private final TimeValue flushMergesAfter;
|
||||
private final String codecName;
|
||||
|
@ -60,7 +56,6 @@ public final class EngineConfig {
|
|||
private final Store store;
|
||||
private final SnapshotDeletionPolicy deletionPolicy;
|
||||
private final MergePolicy mergePolicy;
|
||||
private final MergeSchedulerConfig mergeSchedulerConfig;
|
||||
private final Analyzer analyzer;
|
||||
private final Similarity similarity;
|
||||
private final CodecService codecService;
|
||||
|
@ -69,12 +64,6 @@ public final class EngineConfig {
|
|||
private final QueryCache queryCache;
|
||||
private final QueryCachingPolicy queryCachingPolicy;
|
||||
|
||||
/**
|
||||
* Index setting to enable / disable deletes garbage collection.
|
||||
* This setting is realtime updateable
|
||||
*/
|
||||
public static final String INDEX_GC_DELETES_SETTING = "index.gc_deletes";
|
||||
|
||||
/**
|
||||
* Index setting to change the low level lucene codec used for writing new segments.
|
||||
* This setting is <b>not</b> realtime updateable.
|
||||
|
@ -84,9 +73,6 @@ public final class EngineConfig {
|
|||
/** if set to true the engine will start even if the translog id in the commit point can not be found */
|
||||
public static final String INDEX_FORCE_NEW_TRANSLOG = "index.engine.force_new_translog";
|
||||
|
||||
public static final TimeValue DEFAULT_REFRESH_INTERVAL = new TimeValue(1, TimeUnit.SECONDS);
|
||||
public static final TimeValue DEFAULT_GC_DELETES = TimeValue.timeValueSeconds(60);
|
||||
|
||||
private static final String DEFAULT_CODEC_NAME = "default";
|
||||
private TranslogConfig translogConfig;
|
||||
private boolean create = false;
|
||||
|
@ -96,7 +82,7 @@ public final class EngineConfig {
|
|||
*/
|
||||
public EngineConfig(ShardId shardId, ThreadPool threadPool,
|
||||
IndexSettings indexSettings, Engine.Warmer warmer, Store store, SnapshotDeletionPolicy deletionPolicy,
|
||||
MergePolicy mergePolicy, MergeSchedulerConfig mergeSchedulerConfig, Analyzer analyzer,
|
||||
MergePolicy mergePolicy,Analyzer analyzer,
|
||||
Similarity similarity, CodecService codecService, Engine.EventListener eventListener,
|
||||
TranslogRecoveryPerformer translogRecoveryPerformer, QueryCache queryCache, QueryCachingPolicy queryCachingPolicy, TranslogConfig translogConfig, TimeValue flushMergesAfter) {
|
||||
this.shardId = shardId;
|
||||
|
@ -107,7 +93,6 @@ public final class EngineConfig {
|
|||
this.store = store;
|
||||
this.deletionPolicy = deletionPolicy;
|
||||
this.mergePolicy = mergePolicy;
|
||||
this.mergeSchedulerConfig = mergeSchedulerConfig;
|
||||
this.analyzer = analyzer;
|
||||
this.similarity = similarity;
|
||||
this.codecService = codecService;
|
||||
|
@ -117,7 +102,6 @@ public final class EngineConfig {
|
|||
// there are not too many shards allocated to this node. Instead, IndexingMemoryController periodically checks
|
||||
// and refreshes the most heap-consuming shards when total indexing heap usage across all shards is too high:
|
||||
indexingBufferSize = new ByteSizeValue(256, ByteSizeUnit.MB);
|
||||
gcDeletesInMillis = settings.getAsTime(INDEX_GC_DELETES_SETTING, EngineConfig.DEFAULT_GC_DELETES).millis();
|
||||
this.translogRecoveryPerformer = translogRecoveryPerformer;
|
||||
this.forceNewTranslog = settings.getAsBoolean(INDEX_FORCE_NEW_TRANSLOG, false);
|
||||
this.queryCache = queryCache;
|
||||
|
@ -147,19 +131,12 @@ public final class EngineConfig {
|
|||
return indexingBufferSize;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the GC deletes cycle in milliseconds.
|
||||
*/
|
||||
public long getGcDeletesInMillis() {
|
||||
return gcDeletesInMillis;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns <code>true</code> iff delete garbage collection in the engine should be enabled. This setting is updateable
|
||||
* in realtime and forces a volatile read. Consumers can safely read this value directly go fetch it's latest value. The default is <code>true</code>
|
||||
* <p>
|
||||
* Engine GC deletion if enabled collects deleted documents from in-memory realtime data structures after a certain amount of
|
||||
* time ({@link #getGcDeletesInMillis()} if enabled. Before deletes are GCed they will cause re-adding the document that was deleted
|
||||
* time ({@link IndexSettings#getGcDeletesInMillis()} if enabled. Before deletes are GCed they will cause re-adding the document that was deleted
|
||||
* to fail.
|
||||
* </p>
|
||||
*/
|
||||
|
@ -219,13 +196,6 @@ public final class EngineConfig {
|
|||
return mergePolicy;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the {@link MergeSchedulerConfig}
|
||||
*/
|
||||
public MergeSchedulerConfig getMergeSchedulerConfig() {
|
||||
return mergeSchedulerConfig;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a listener that should be called on engine failure
|
||||
*/
|
||||
|
@ -259,13 +229,6 @@ public final class EngineConfig {
|
|||
return similarity;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the GC deletes cycle in milliseconds.
|
||||
*/
|
||||
public void setGcDeletesInMillis(long gcDeletesInMillis) {
|
||||
this.gcDeletesInMillis = gcDeletesInMillis;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the {@link org.elasticsearch.index.shard.TranslogRecoveryPerformer} for this engine. This class is used
|
||||
* to apply transaction log operations to the engine. It encapsulates all the logic to transfer the translog entry into
|
||||
|
|
|
@ -57,14 +57,12 @@ import org.elasticsearch.common.lucene.uid.Versions;
|
|||
import org.elasticsearch.common.math.MathUtils;
|
||||
import org.elasticsearch.common.unit.ByteSizeValue;
|
||||
import org.elasticsearch.common.util.concurrent.AbstractRunnable;
|
||||
import org.elasticsearch.common.util.concurrent.EsRejectedExecutionException;
|
||||
import org.elasticsearch.common.util.concurrent.ReleasableLock;
|
||||
import org.elasticsearch.index.IndexSettings;
|
||||
import org.elasticsearch.index.mapper.Uid;
|
||||
import org.elasticsearch.index.merge.MergeStats;
|
||||
import org.elasticsearch.index.merge.OnGoingMerge;
|
||||
import org.elasticsearch.index.shard.ElasticsearchMergePolicy;
|
||||
import org.elasticsearch.index.shard.MergeSchedulerConfig;
|
||||
import org.elasticsearch.index.shard.ShardId;
|
||||
import org.elasticsearch.index.shard.TranslogRecoveryPerformer;
|
||||
import org.elasticsearch.index.translog.Translog;
|
||||
|
@ -136,7 +134,7 @@ public class InternalEngine extends Engine {
|
|||
try {
|
||||
this.lastDeleteVersionPruneTimeMSec = engineConfig.getThreadPool().estimatedTimeInMillis();
|
||||
this.warmer = engineConfig.getWarmer();
|
||||
mergeScheduler = scheduler = new EngineMergeScheduler(engineConfig.getShardId(), engineConfig.getIndexSettings(), engineConfig.getMergeSchedulerConfig());
|
||||
mergeScheduler = scheduler = new EngineMergeScheduler(engineConfig.getShardId(), engineConfig.getIndexSettings());
|
||||
this.dirtyLocks = new Object[Runtime.getRuntime().availableProcessors() * 10]; // we multiply it to have enough...
|
||||
for (int i = 0; i < dirtyLocks.length; i++) {
|
||||
dirtyLocks[i] = new Object();
|
||||
|
@ -370,7 +368,7 @@ public class InternalEngine extends Engine {
|
|||
deleted = currentVersion == Versions.NOT_FOUND;
|
||||
} else {
|
||||
deleted = versionValue.delete();
|
||||
if (engineConfig.isEnableGcDeletes() && versionValue.delete() && (engineConfig.getThreadPool().estimatedTimeInMillis() - versionValue.time()) > engineConfig.getGcDeletesInMillis()) {
|
||||
if (engineConfig.isEnableGcDeletes() && versionValue.delete() && (engineConfig.getThreadPool().estimatedTimeInMillis() - versionValue.time()) > getGcDeletesInMillis()) {
|
||||
currentVersion = Versions.NOT_FOUND; // deleted, and GC
|
||||
} else {
|
||||
currentVersion = versionValue.version();
|
||||
|
@ -436,7 +434,7 @@ public class InternalEngine extends Engine {
|
|||
private void maybePruneDeletedTombstones() {
|
||||
// It's expensive to prune because we walk the deletes map acquiring dirtyLock for each uid so we only do it
|
||||
// every 1/4 of gcDeletesInMillis:
|
||||
if (engineConfig.isEnableGcDeletes() && engineConfig.getThreadPool().estimatedTimeInMillis() - lastDeleteVersionPruneTimeMSec > engineConfig.getGcDeletesInMillis() * 0.25) {
|
||||
if (engineConfig.isEnableGcDeletes() && engineConfig.getThreadPool().estimatedTimeInMillis() - lastDeleteVersionPruneTimeMSec > getGcDeletesInMillis() * 0.25) {
|
||||
pruneDeletedTombstones();
|
||||
}
|
||||
}
|
||||
|
@ -452,7 +450,7 @@ public class InternalEngine extends Engine {
|
|||
deleted = currentVersion == Versions.NOT_FOUND;
|
||||
} else {
|
||||
deleted = versionValue.delete();
|
||||
if (engineConfig.isEnableGcDeletes() && versionValue.delete() && (engineConfig.getThreadPool().estimatedTimeInMillis() - versionValue.time()) > engineConfig.getGcDeletesInMillis()) {
|
||||
if (engineConfig.isEnableGcDeletes() && versionValue.delete() && (engineConfig.getThreadPool().estimatedTimeInMillis() - versionValue.time()) > getGcDeletesInMillis()) {
|
||||
currentVersion = Versions.NOT_FOUND; // deleted, and GC
|
||||
} else {
|
||||
currentVersion = versionValue.version();
|
||||
|
@ -701,7 +699,7 @@ public class InternalEngine extends Engine {
|
|||
// Must re-get it here, vs using entry.getValue(), in case the uid was indexed/deleted since we pulled the iterator:
|
||||
VersionValue versionValue = versionMap.getTombstoneUnderLock(uid);
|
||||
if (versionValue != null) {
|
||||
if (timeMSec - versionValue.time() > engineConfig.getGcDeletesInMillis()) {
|
||||
if (timeMSec - versionValue.time() > getGcDeletesInMillis()) {
|
||||
versionMap.removeTombstoneUnderLock(uid);
|
||||
}
|
||||
}
|
||||
|
@ -1072,7 +1070,7 @@ public class InternalEngine extends Engine {
|
|||
}
|
||||
|
||||
long getGcDeletesInMillis() {
|
||||
return engineConfig.getGcDeletesInMillis();
|
||||
return engineConfig.getIndexSettings().getGcDeletesInMillis();
|
||||
}
|
||||
|
||||
LiveIndexWriterConfig getCurrentIndexWriterConfig() {
|
||||
|
@ -1083,8 +1081,8 @@ public class InternalEngine extends Engine {
|
|||
private final AtomicInteger numMergesInFlight = new AtomicInteger(0);
|
||||
private final AtomicBoolean isThrottling = new AtomicBoolean();
|
||||
|
||||
EngineMergeScheduler(ShardId shardId, IndexSettings indexSettings, MergeSchedulerConfig config) {
|
||||
super(shardId, indexSettings, config);
|
||||
EngineMergeScheduler(ShardId shardId, IndexSettings indexSettings) {
|
||||
super(shardId, indexSettings);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -19,193 +19,29 @@
|
|||
|
||||
package org.elasticsearch.index.fielddata;
|
||||
|
||||
import org.apache.lucene.index.TermsEnum;
|
||||
import org.apache.lucene.search.SortField;
|
||||
import org.apache.lucene.util.BytesRef;
|
||||
import org.apache.lucene.util.BytesRefBuilder;
|
||||
import org.apache.lucene.util.NumericUtils;
|
||||
import org.elasticsearch.index.fielddata.ordinals.OrdinalsBuilder;
|
||||
import org.elasticsearch.index.mapper.core.BooleanFieldMapper;
|
||||
|
||||
/**
|
||||
*/
|
||||
public interface IndexNumericFieldData extends IndexFieldData<AtomicNumericFieldData> {
|
||||
|
||||
public static enum NumericType {
|
||||
BOOLEAN(1, false, SortField.Type.INT, 0, 1) {
|
||||
@Override
|
||||
public long toLong(BytesRef indexForm) {
|
||||
if (indexForm.equals(BooleanFieldMapper.Values.FALSE)) {
|
||||
return 0;
|
||||
} else if (indexForm.equals(BooleanFieldMapper.Values.TRUE)) {
|
||||
return 1;
|
||||
} else {
|
||||
throw new IllegalArgumentException("Cannot convert " + indexForm + " to a boolean");
|
||||
}
|
||||
}
|
||||
BOOLEAN(false),
|
||||
BYTE(false),
|
||||
SHORT(false),
|
||||
INT(false),
|
||||
LONG(false),
|
||||
FLOAT(true),
|
||||
DOUBLE(true);
|
||||
|
||||
@Override
|
||||
public void toIndexForm(Number number, BytesRefBuilder bytes) {
|
||||
bytes.append(number.intValue() != 0 ? BooleanFieldMapper.Values.TRUE : BooleanFieldMapper.Values.FALSE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Number toNumber(BytesRef indexForm) {
|
||||
return toLong(indexForm);
|
||||
}
|
||||
|
||||
},
|
||||
BYTE(8, false, SortField.Type.INT, Byte.MIN_VALUE, Byte.MAX_VALUE) {
|
||||
@Override
|
||||
public long toLong(BytesRef indexForm) {
|
||||
return INT.toLong(indexForm);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void toIndexForm(Number number, BytesRefBuilder bytes) {
|
||||
INT.toIndexForm(number, bytes);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Number toNumber(BytesRef indexForm) {
|
||||
return INT.toNumber(indexForm);
|
||||
}
|
||||
},
|
||||
SHORT(16, false, SortField.Type.INT, Short.MIN_VALUE, Short.MAX_VALUE) {
|
||||
@Override
|
||||
public long toLong(BytesRef indexForm) {
|
||||
return INT.toLong(indexForm);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void toIndexForm(Number number, BytesRefBuilder bytes) {
|
||||
INT.toIndexForm(number, bytes);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Number toNumber(BytesRef indexForm) {
|
||||
return INT.toNumber(indexForm);
|
||||
}
|
||||
},
|
||||
INT(32, false, SortField.Type.INT, Integer.MIN_VALUE, Integer.MAX_VALUE) {
|
||||
@Override
|
||||
public long toLong(BytesRef indexForm) {
|
||||
return NumericUtils.prefixCodedToInt(indexForm);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void toIndexForm(Number number, BytesRefBuilder bytes) {
|
||||
NumericUtils.intToPrefixCodedBytes(number.intValue(), 0, bytes);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Number toNumber(BytesRef indexForm) {
|
||||
return NumericUtils.prefixCodedToInt(indexForm);
|
||||
}
|
||||
},
|
||||
LONG(64, false, SortField.Type.LONG, Long.MIN_VALUE, Long.MAX_VALUE) {
|
||||
@Override
|
||||
public long toLong(BytesRef indexForm) {
|
||||
return NumericUtils.prefixCodedToLong(indexForm);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void toIndexForm(Number number, BytesRefBuilder bytes) {
|
||||
NumericUtils.longToPrefixCodedBytes(number.longValue(), 0, bytes);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Number toNumber(BytesRef indexForm) {
|
||||
return NumericUtils.prefixCodedToLong(indexForm);
|
||||
}
|
||||
},
|
||||
FLOAT(32, true, SortField.Type.FLOAT, Float.NEGATIVE_INFINITY, Float.POSITIVE_INFINITY) {
|
||||
@Override
|
||||
public double toDouble(BytesRef indexForm) {
|
||||
return NumericUtils.sortableIntToFloat(NumericUtils.prefixCodedToInt(indexForm));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void toIndexForm(Number number, BytesRefBuilder bytes) {
|
||||
NumericUtils.intToPrefixCodedBytes(NumericUtils.floatToSortableInt(number.floatValue()), 0, bytes);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Number toNumber(BytesRef indexForm) {
|
||||
return NumericUtils.sortableIntToFloat(NumericUtils.prefixCodedToInt(indexForm));
|
||||
}
|
||||
},
|
||||
DOUBLE(64, true, SortField.Type.DOUBLE, Double.NEGATIVE_INFINITY, Double.POSITIVE_INFINITY) {
|
||||
@Override
|
||||
public double toDouble(BytesRef indexForm) {
|
||||
return NumericUtils.sortableLongToDouble(NumericUtils.prefixCodedToLong(indexForm));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void toIndexForm(Number number, BytesRefBuilder bytes) {
|
||||
NumericUtils.longToPrefixCodedBytes(NumericUtils.doubleToSortableLong(number.doubleValue()), 0, bytes);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Number toNumber(BytesRef indexForm) {
|
||||
return NumericUtils.sortableLongToDouble(NumericUtils.prefixCodedToLong(indexForm));
|
||||
}
|
||||
};
|
||||
|
||||
private final int requiredBits;
|
||||
private final boolean floatingPoint;
|
||||
private final SortField.Type type;
|
||||
private final Number minValue, maxValue;
|
||||
|
||||
private NumericType(int requiredBits, boolean floatingPoint, SortField.Type type, Number minValue, Number maxValue) {
|
||||
this.requiredBits = requiredBits;
|
||||
private NumericType(boolean floatingPoint) {
|
||||
this.floatingPoint = floatingPoint;
|
||||
this.type = type;
|
||||
this.minValue = minValue;
|
||||
this.maxValue = maxValue;
|
||||
}
|
||||
|
||||
public final SortField.Type sortFieldType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
public final Number minValue() {
|
||||
return minValue;
|
||||
}
|
||||
|
||||
public final Number maxValue() {
|
||||
return maxValue;
|
||||
}
|
||||
|
||||
public final boolean isFloatingPoint() {
|
||||
return floatingPoint;
|
||||
}
|
||||
|
||||
public final int requiredBits() {
|
||||
return requiredBits;
|
||||
}
|
||||
|
||||
public abstract void toIndexForm(Number number, BytesRefBuilder bytes);
|
||||
|
||||
public long toLong(BytesRef indexForm) {
|
||||
return (long) toDouble(indexForm);
|
||||
}
|
||||
|
||||
public double toDouble(BytesRef indexForm) {
|
||||
return (double) toLong(indexForm);
|
||||
}
|
||||
|
||||
public abstract Number toNumber(BytesRef indexForm);
|
||||
|
||||
public final TermsEnum wrapTermsEnum(TermsEnum termsEnum) {
|
||||
if (requiredBits() == 1) { // boolean, no prefix-terms
|
||||
return termsEnum;
|
||||
} else if (requiredBits() > 32) {
|
||||
return OrdinalsBuilder.wrapNumeric64Bit(termsEnum);
|
||||
} else {
|
||||
return OrdinalsBuilder.wrapNumeric32Bit(termsEnum);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
NumericType getNumericType();
|
||||
|
|
|
@ -519,16 +519,17 @@ public class MapperService extends AbstractIndexComponent implements Closeable {
|
|||
return termsFilter;
|
||||
}
|
||||
} else {
|
||||
// Current bool filter requires that at least one should clause matches, even with a must clause.
|
||||
BooleanQuery.Builder bool = new BooleanQuery.Builder();
|
||||
BooleanQuery.Builder typesBool = new BooleanQuery.Builder();
|
||||
for (String type : types) {
|
||||
DocumentMapper docMapper = documentMapper(type);
|
||||
if (docMapper == null) {
|
||||
bool.add(new TermQuery(new Term(TypeFieldMapper.NAME, type)), BooleanClause.Occur.SHOULD);
|
||||
typesBool.add(new TermQuery(new Term(TypeFieldMapper.NAME, type)), BooleanClause.Occur.SHOULD);
|
||||
} else {
|
||||
bool.add(docMapper.typeFilter(), BooleanClause.Occur.SHOULD);
|
||||
typesBool.add(docMapper.typeFilter(), BooleanClause.Occur.SHOULD);
|
||||
}
|
||||
}
|
||||
BooleanQuery.Builder bool = new BooleanQuery.Builder();
|
||||
bool.add(typesBool.build(), Occur.MUST);
|
||||
if (filterPercolateType) {
|
||||
bool.add(percolatorType, BooleanClause.Occur.MUST_NOT);
|
||||
}
|
||||
|
|
|
@ -875,14 +875,14 @@ public class MoreLikeThisQueryBuilder extends AbstractQueryBuilder<MoreLikeThisQ
|
|||
}
|
||||
}
|
||||
|
||||
BooleanQuery boolQuery = new BooleanQuery();
|
||||
BooleanQuery.Builder boolQuery = new BooleanQuery.Builder();
|
||||
boolQuery.add(mltQuery, BooleanClause.Occur.SHOULD);
|
||||
|
||||
// exclude the items from the search
|
||||
if (!include) {
|
||||
handleExclude(boolQuery, likeItems);
|
||||
}
|
||||
return boolQuery;
|
||||
return boolQuery.build();
|
||||
}
|
||||
|
||||
private static void setDefaultIndexTypeFields(QueryShardContext context, Item item, List<String> moreLikeFields,
|
||||
|
@ -949,7 +949,7 @@ public class MoreLikeThisQueryBuilder extends AbstractQueryBuilder<MoreLikeThisQ
|
|||
return selectedItems.contains(new Item(response.getIndex(), response.getType(), response.getId()));
|
||||
}
|
||||
|
||||
private static void handleExclude(BooleanQuery boolQuery, Item[] likeItems) {
|
||||
private static void handleExclude(BooleanQuery.Builder boolQuery, Item[] likeItems) {
|
||||
// artificial docs get assigned a random id and should be disregarded
|
||||
List<BytesRef> uids = new ArrayList<>();
|
||||
for (Item item : likeItems) {
|
||||
|
|
|
@ -43,17 +43,12 @@ public class SpanNearQueryBuilder extends AbstractQueryBuilder<SpanNearQueryBuil
|
|||
/** Default for flag controlling whether matches are required to be in-order */
|
||||
public static boolean DEFAULT_IN_ORDER = true;
|
||||
|
||||
/** Default for flag controlling whether payloads are collected */
|
||||
public static boolean DEFAULT_COLLECT_PAYLOADS = true;
|
||||
|
||||
private final List<SpanQueryBuilder> clauses = new ArrayList<>();
|
||||
|
||||
private final int slop;
|
||||
|
||||
private boolean inOrder = DEFAULT_IN_ORDER;
|
||||
|
||||
private boolean collectPayloads = DEFAULT_COLLECT_PAYLOADS;
|
||||
|
||||
static final SpanNearQueryBuilder PROTOTYPE = new SpanNearQueryBuilder(SpanTermQueryBuilder.PROTOTYPE, 0);
|
||||
|
||||
/**
|
||||
|
@ -107,21 +102,6 @@ public class SpanNearQueryBuilder extends AbstractQueryBuilder<SpanNearQueryBuil
|
|||
return this.inOrder;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param collectPayloads flag controlling whether payloads are collected
|
||||
*/
|
||||
public SpanNearQueryBuilder collectPayloads(boolean collectPayloads) {
|
||||
this.collectPayloads = collectPayloads;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @see SpanNearQueryBuilder#collectPayloads(boolean)
|
||||
*/
|
||||
public boolean collectPayloads() {
|
||||
return this.collectPayloads;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
builder.startObject(NAME);
|
||||
|
@ -132,7 +112,6 @@ public class SpanNearQueryBuilder extends AbstractQueryBuilder<SpanNearQueryBuil
|
|||
builder.endArray();
|
||||
builder.field(SpanNearQueryParser.SLOP_FIELD.getPreferredName(), slop);
|
||||
builder.field(SpanNearQueryParser.IN_ORDER_FIELD.getPreferredName(), inOrder);
|
||||
builder.field(SpanNearQueryParser.COLLECT_PAYLOADS_FIELD.getPreferredName(), collectPayloads);
|
||||
printBoostAndQueryName(builder);
|
||||
builder.endObject();
|
||||
}
|
||||
|
@ -145,7 +124,7 @@ public class SpanNearQueryBuilder extends AbstractQueryBuilder<SpanNearQueryBuil
|
|||
assert query instanceof SpanQuery;
|
||||
spanQueries[i] = (SpanQuery) query;
|
||||
}
|
||||
return new SpanNearQuery(spanQueries, slop, inOrder, collectPayloads);
|
||||
return new SpanNearQuery(spanQueries, slop, inOrder);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -155,7 +134,6 @@ public class SpanNearQueryBuilder extends AbstractQueryBuilder<SpanNearQueryBuil
|
|||
for (int i = 1; i < clauses.size(); i++) {
|
||||
queryBuilder.clauses.add((SpanQueryBuilder)clauses.get(i));
|
||||
}
|
||||
queryBuilder.collectPayloads = in.readBoolean();
|
||||
queryBuilder.inOrder = in.readBoolean();
|
||||
return queryBuilder;
|
||||
|
||||
|
@ -165,20 +143,18 @@ public class SpanNearQueryBuilder extends AbstractQueryBuilder<SpanNearQueryBuil
|
|||
protected void doWriteTo(StreamOutput out) throws IOException {
|
||||
writeQueries(out, clauses);
|
||||
out.writeVInt(slop);
|
||||
out.writeBoolean(collectPayloads);
|
||||
out.writeBoolean(inOrder);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected int doHashCode() {
|
||||
return Objects.hash(clauses, slop, collectPayloads, inOrder);
|
||||
return Objects.hash(clauses, slop, inOrder);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected boolean doEquals(SpanNearQueryBuilder other) {
|
||||
return Objects.equals(clauses, other.clauses) &&
|
||||
Objects.equals(slop, other.slop) &&
|
||||
Objects.equals(collectPayloads, other.collectPayloads) &&
|
||||
Objects.equals(inOrder, other.inOrder);
|
||||
}
|
||||
|
||||
|
|
|
@ -34,10 +34,10 @@ import java.util.List;
|
|||
public class SpanNearQueryParser implements QueryParser<SpanNearQueryBuilder> {
|
||||
|
||||
public static final ParseField SLOP_FIELD = new ParseField("slop");
|
||||
public static final ParseField COLLECT_PAYLOADS_FIELD = new ParseField("collect_payloads");
|
||||
public static final ParseField COLLECT_PAYLOADS_FIELD = new ParseField("collect_payloads").withAllDeprecated("no longer supported");
|
||||
public static final ParseField CLAUSES_FIELD = new ParseField("clauses");
|
||||
public static final ParseField IN_ORDER_FIELD = new ParseField("in_order");
|
||||
|
||||
|
||||
@Override
|
||||
public String[] names() {
|
||||
return new String[]{SpanNearQueryBuilder.NAME, Strings.toCamelCase(SpanNearQueryBuilder.NAME)};
|
||||
|
@ -50,7 +50,6 @@ public class SpanNearQueryParser implements QueryParser<SpanNearQueryBuilder> {
|
|||
float boost = AbstractQueryBuilder.DEFAULT_BOOST;
|
||||
Integer slop = null;
|
||||
boolean inOrder = SpanNearQueryBuilder.DEFAULT_IN_ORDER;
|
||||
boolean collectPayloads = SpanNearQueryBuilder.DEFAULT_COLLECT_PAYLOADS;
|
||||
String queryName = null;
|
||||
|
||||
List<SpanQueryBuilder> clauses = new ArrayList<>();
|
||||
|
@ -76,7 +75,7 @@ public class SpanNearQueryParser implements QueryParser<SpanNearQueryBuilder> {
|
|||
if (parseContext.parseFieldMatcher().match(currentFieldName, IN_ORDER_FIELD)) {
|
||||
inOrder = parser.booleanValue();
|
||||
} else if (parseContext.parseFieldMatcher().match(currentFieldName, COLLECT_PAYLOADS_FIELD)) {
|
||||
collectPayloads = parser.booleanValue();
|
||||
// Deprecated in 3.0.0
|
||||
} else if (parseContext.parseFieldMatcher().match(currentFieldName, SLOP_FIELD)) {
|
||||
slop = parser.intValue();
|
||||
} else if (parseContext.parseFieldMatcher().match(currentFieldName, AbstractQueryBuilder.BOOST_FIELD)) {
|
||||
|
@ -104,7 +103,6 @@ public class SpanNearQueryParser implements QueryParser<SpanNearQueryBuilder> {
|
|||
queryBuilder.clause(clauses.get(i));
|
||||
}
|
||||
queryBuilder.inOrder(inOrder);
|
||||
queryBuilder.collectPayloads(collectPayloads);
|
||||
queryBuilder.boost(boost);
|
||||
queryBuilder.queryName(queryName);
|
||||
return queryBuilder;
|
||||
|
|
|
@ -128,11 +128,11 @@ public class MultiMatchQuery extends MatchQuery {
|
|||
return groupQuery.get(0);
|
||||
}
|
||||
if (groupDismax) {
|
||||
DisjunctionMaxQuery disMaxQuery = new DisjunctionMaxQuery(tieBreaker);
|
||||
List<Query> queries = new ArrayList<>();
|
||||
for (Query query : groupQuery) {
|
||||
disMaxQuery.add(query);
|
||||
queries.add(query);
|
||||
}
|
||||
return disMaxQuery;
|
||||
return new DisjunctionMaxQuery(queries, tieBreaker);
|
||||
} else {
|
||||
final BooleanQuery.Builder booleanQuery = new BooleanQuery.Builder();
|
||||
for (Query query : groupQuery) {
|
||||
|
|
|
@ -31,7 +31,7 @@ import java.util.concurrent.TimeUnit;
|
|||
|
||||
/**
|
||||
*/
|
||||
public final class SearchSlowLog{
|
||||
public final class SearchSlowLog {
|
||||
|
||||
private boolean reformat;
|
||||
|
||||
|
@ -62,7 +62,7 @@ public final class SearchSlowLog{
|
|||
public static final String INDEX_SEARCH_SLOWLOG_REFORMAT = INDEX_SEARCH_SLOWLOG_PREFIX + ".reformat";
|
||||
public static final String INDEX_SEARCH_SLOWLOG_LEVEL = INDEX_SEARCH_SLOWLOG_PREFIX + ".level";
|
||||
|
||||
SearchSlowLog(Settings indexSettings) {
|
||||
public SearchSlowLog(Settings indexSettings) {
|
||||
|
||||
this.reformat = indexSettings.getAsBoolean(INDEX_SEARCH_SLOWLOG_REFORMAT, true);
|
||||
|
||||
|
@ -109,7 +109,7 @@ public final class SearchSlowLog{
|
|||
}
|
||||
}
|
||||
|
||||
synchronized void onRefreshSettings(Settings settings) {
|
||||
public void onRefreshSettings(Settings settings) {
|
||||
long queryWarnThreshold = settings.getAsTime(INDEX_SEARCH_SLOWLOG_THRESHOLD_QUERY_WARN, TimeValue.timeValueNanos(this.queryWarnThreshold)).nanos();
|
||||
if (queryWarnThreshold != this.queryWarnThreshold) {
|
||||
this.queryWarnThreshold = queryWarnThreshold;
|
||||
|
|
|
@ -41,8 +41,8 @@ public final class ShardSearchStats {
|
|||
private final CounterMetric openContexts = new CounterMetric();
|
||||
private volatile Map<String, StatsHolder> groupsStats = emptyMap();
|
||||
|
||||
public ShardSearchStats(Settings indexSettings) {
|
||||
this.slowLogSearchService = new SearchSlowLog(indexSettings);
|
||||
public ShardSearchStats(SearchSlowLog searchSlowLog) {
|
||||
this.slowLogSearchService = searchSlowLog;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -44,11 +44,9 @@ import org.elasticsearch.common.Nullable;
|
|||
import org.elasticsearch.common.io.stream.BytesStreamOutput;
|
||||
import org.elasticsearch.common.lease.Releasables;
|
||||
import org.elasticsearch.common.logging.ESLogger;
|
||||
import org.elasticsearch.common.logging.support.LoggerMessageFormat;
|
||||
import org.elasticsearch.common.lucene.Lucene;
|
||||
import org.elasticsearch.common.metrics.MeanMetric;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.common.unit.ByteSizeUnit;
|
||||
import org.elasticsearch.common.unit.ByteSizeValue;
|
||||
import org.elasticsearch.common.unit.TimeValue;
|
||||
import org.elasticsearch.common.util.Callback;
|
||||
|
@ -93,6 +91,7 @@ import org.elasticsearch.index.percolator.PercolatorQueriesRegistry;
|
|||
import org.elasticsearch.index.query.QueryShardContext;
|
||||
import org.elasticsearch.index.recovery.RecoveryStats;
|
||||
import org.elasticsearch.index.refresh.RefreshStats;
|
||||
import org.elasticsearch.index.search.stats.SearchSlowLog;
|
||||
import org.elasticsearch.index.search.stats.SearchStats;
|
||||
import org.elasticsearch.index.search.stats.ShardSearchStats;
|
||||
import org.elasticsearch.index.similarity.SimilarityService;
|
||||
|
@ -142,7 +141,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
private final MapperService mapperService;
|
||||
private final IndexCache indexCache;
|
||||
private final Store store;
|
||||
private final MergeSchedulerConfig mergeSchedulerConfig;
|
||||
private final InternalIndexingStats internalIndexingStats;
|
||||
private final ShardSearchStats searchService;
|
||||
private final ShardGetService getService;
|
||||
|
@ -162,7 +160,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
private final SimilarityService similarityService;
|
||||
private final EngineConfig engineConfig;
|
||||
private final TranslogConfig translogConfig;
|
||||
private final MergePolicyConfig mergePolicyConfig;
|
||||
private final IndicesQueryCache indicesQueryCache;
|
||||
private final IndexEventListener indexEventListener;
|
||||
private final IndexSettings idxSettings;
|
||||
|
@ -173,8 +170,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
* being indexed/deleted. */
|
||||
private final AtomicLong writingBytes = new AtomicLong();
|
||||
|
||||
private TimeValue refreshInterval;
|
||||
|
||||
private volatile ScheduledFuture<?> refreshScheduledFuture;
|
||||
protected volatile ShardRouting shardRouting;
|
||||
protected volatile IndexShardState state;
|
||||
|
@ -191,16 +186,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
private final MeanMetric flushMetric = new MeanMetric();
|
||||
|
||||
private final ShardEventListener shardEventListener = new ShardEventListener();
|
||||
private volatile boolean flushOnClose = true;
|
||||
private volatile ByteSizeValue flushThresholdSize;
|
||||
|
||||
/**
|
||||
* Index setting to control if a flush is executed before engine is closed
|
||||
* This setting is realtime updateable.
|
||||
*/
|
||||
public static final String INDEX_FLUSH_ON_CLOSE = "index.flush_on_close";
|
||||
public static final String INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE = "index.translog.flush_threshold_size";
|
||||
public static final String INDEX_REFRESH_INTERVAL = "index.refresh_interval";
|
||||
|
||||
private final ShardPath path;
|
||||
|
||||
|
@ -219,7 +204,7 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
public IndexShard(ShardId shardId, IndexSettings indexSettings, ShardPath path, Store store, IndexCache indexCache,
|
||||
MapperService mapperService, SimilarityService similarityService, IndexFieldDataService indexFieldDataService,
|
||||
@Nullable EngineFactory engineFactory,
|
||||
IndexEventListener indexEventListener, IndexSearcherWrapper indexSearcherWrapper, NodeServicesProvider provider, IndexingOperationListener... listeners) {
|
||||
IndexEventListener indexEventListener, IndexSearcherWrapper indexSearcherWrapper, NodeServicesProvider provider, SearchSlowLog slowLog, IndexingOperationListener... listeners) {
|
||||
super(shardId, indexSettings);
|
||||
final Settings settings = indexSettings.getSettings();
|
||||
this.idxSettings = indexSettings;
|
||||
|
@ -231,7 +216,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
this.engineFactory = engineFactory == null ? new InternalEngineFactory() : engineFactory;
|
||||
this.store = store;
|
||||
this.indexEventListener = indexEventListener;
|
||||
this.mergeSchedulerConfig = new MergeSchedulerConfig(indexSettings);
|
||||
this.threadPool = provider.getThreadPool();
|
||||
this.mapperService = mapperService;
|
||||
this.indexCache = indexCache;
|
||||
|
@ -241,7 +225,7 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
this.indexingOperationListeners = new IndexingOperationListener.CompositeListener(listenersList, logger);
|
||||
this.getService = new ShardGetService(indexSettings, this, mapperService);
|
||||
this.termVectorsService = provider.getTermVectorsService();
|
||||
this.searchService = new ShardSearchStats(settings);
|
||||
this.searchService = new ShardSearchStats(slowLog);
|
||||
this.shardWarmerService = new ShardIndexWarmerService(shardId, indexSettings);
|
||||
this.indicesQueryCache = provider.getIndicesQueryCache();
|
||||
this.shardQueryCache = new ShardRequestCache(shardId, indexSettings);
|
||||
|
@ -249,10 +233,7 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
this.indexFieldDataService = indexFieldDataService;
|
||||
this.shardBitsetFilterCache = new ShardBitsetFilterCache(shardId, indexSettings);
|
||||
state = IndexShardState.CREATED;
|
||||
this.refreshInterval = settings.getAsTime(INDEX_REFRESH_INTERVAL, EngineConfig.DEFAULT_REFRESH_INTERVAL);
|
||||
this.flushOnClose = settings.getAsBoolean(INDEX_FLUSH_ON_CLOSE, true);
|
||||
this.path = path;
|
||||
this.mergePolicyConfig = new MergePolicyConfig(logger, settings);
|
||||
/* create engine config */
|
||||
logger.debug("state: [CREATED]");
|
||||
|
||||
|
@ -269,7 +250,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
}
|
||||
|
||||
this.engineConfig = newEngineConfig(translogConfig, cachingPolicy);
|
||||
this.flushThresholdSize = settings.getAsBytesSize(INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE, new ByteSizeValue(512, ByteSizeUnit.MB));
|
||||
this.indexShardOperationCounter = new IndexShardOperationCounter(logger, shardId);
|
||||
this.provider = provider;
|
||||
this.searcherWrapper = indexSearcherWrapper;
|
||||
|
@ -561,23 +541,25 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
/** Writes all indexing changes to disk and opens a new searcher reflecting all changes. This can throw {@link EngineClosedException}. */
|
||||
public void refresh(String source) {
|
||||
verifyNotClosed();
|
||||
if (canIndex()) {
|
||||
long bytes = getEngine().getIndexBufferRAMBytesUsed();
|
||||
writingBytes.addAndGet(bytes);
|
||||
try {
|
||||
logger.debug("refresh with source [{}] indexBufferRAMBytesUsed [{}]", source, new ByteSizeValue(bytes));
|
||||
if (getEngine().refreshNeeded()) {
|
||||
if (canIndex()) {
|
||||
long bytes = getEngine().getIndexBufferRAMBytesUsed();
|
||||
writingBytes.addAndGet(bytes);
|
||||
try {
|
||||
logger.debug("refresh with source [{}] indexBufferRAMBytesUsed [{}]", source, new ByteSizeValue(bytes));
|
||||
long time = System.nanoTime();
|
||||
getEngine().refresh(source);
|
||||
refreshMetric.inc(System.nanoTime() - time);
|
||||
} finally {
|
||||
logger.debug("remove [{}] writing bytes for shard [{}]", new ByteSizeValue(bytes), shardId());
|
||||
writingBytes.addAndGet(-bytes);
|
||||
}
|
||||
} else {
|
||||
logger.debug("refresh with source [{}]", source);
|
||||
long time = System.nanoTime();
|
||||
getEngine().refresh(source);
|
||||
refreshMetric.inc(System.nanoTime() - time);
|
||||
} finally {
|
||||
logger.debug("remove [{}] writing bytes for shard [{}]", new ByteSizeValue(bytes), shardId());
|
||||
writingBytes.addAndGet(-bytes);
|
||||
}
|
||||
} else {
|
||||
logger.debug("refresh with source [{}]", source);
|
||||
long time = System.nanoTime();
|
||||
getEngine().refresh(source);
|
||||
refreshMetric.inc(System.nanoTime() - time);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -820,7 +802,7 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
} finally {
|
||||
final Engine engine = this.currentEngineReference.getAndSet(null);
|
||||
try {
|
||||
if (engine != null && flushEngine && this.flushOnClose) {
|
||||
if (engine != null && flushEngine) {
|
||||
engine.flushAndClose();
|
||||
}
|
||||
} finally { // playing safe here and close the engine even if the above succeeds - close can be called multiple times
|
||||
|
@ -954,7 +936,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
public void finalizeRecovery() {
|
||||
recoveryState().setStage(RecoveryState.Stage.FINALIZE);
|
||||
getEngine().refresh("recovery_finalization");
|
||||
startScheduledTasksIfNeeded();
|
||||
engineConfig.setEnableGcDeletes(true);
|
||||
}
|
||||
|
||||
|
@ -1022,15 +1003,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
}
|
||||
}
|
||||
|
||||
private void startScheduledTasksIfNeeded() {
|
||||
if (refreshInterval.millis() > 0) {
|
||||
refreshScheduledFuture = threadPool.schedule(refreshInterval, ThreadPool.Names.SAME, new EngineRefresher());
|
||||
logger.debug("scheduling refresher every {}", refreshInterval);
|
||||
} else {
|
||||
logger.debug("scheduled refresher disabled");
|
||||
}
|
||||
}
|
||||
|
||||
/** Returns number of heap bytes used by the indexing buffer for this shard, or 0 if the shard is closed */
|
||||
public long getIndexBufferRAMBytesUsed() {
|
||||
Engine engine = getEngineOrNull();
|
||||
|
@ -1061,10 +1033,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
}
|
||||
}
|
||||
|
||||
public final boolean isFlushOnClose() {
|
||||
return flushOnClose;
|
||||
}
|
||||
|
||||
/**
|
||||
* Deletes the shards metadata state. This method can only be executed if the shard is not active.
|
||||
*
|
||||
|
@ -1106,7 +1074,7 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
if (engine != null) {
|
||||
try {
|
||||
Translog translog = engine.getTranslog();
|
||||
return translog.sizeInBytes() > flushThresholdSize.bytes();
|
||||
return translog.sizeInBytes() > indexSettings.getFlushThresholdSize().bytes();
|
||||
} catch (AlreadyClosedException | EngineClosedException ex) {
|
||||
// that's fine we are already close - no need to flush
|
||||
}
|
||||
|
@ -1114,73 +1082,10 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
return false;
|
||||
}
|
||||
|
||||
public void onRefreshSettings(Settings settings) {
|
||||
boolean change = false;
|
||||
synchronized (mutex) {
|
||||
if (state() == IndexShardState.CLOSED) { // no need to update anything if we are closed
|
||||
return;
|
||||
}
|
||||
ByteSizeValue flushThresholdSize = settings.getAsBytesSize(INDEX_TRANSLOG_FLUSH_THRESHOLD_SIZE, this.flushThresholdSize);
|
||||
if (!flushThresholdSize.equals(this.flushThresholdSize)) {
|
||||
logger.info("updating flush_threshold_size from [{}] to [{}]", this.flushThresholdSize, flushThresholdSize);
|
||||
this.flushThresholdSize = flushThresholdSize;
|
||||
}
|
||||
|
||||
final EngineConfig config = engineConfig;
|
||||
final boolean flushOnClose = settings.getAsBoolean(INDEX_FLUSH_ON_CLOSE, this.flushOnClose);
|
||||
if (flushOnClose != this.flushOnClose) {
|
||||
logger.info("updating {} from [{}] to [{}]", INDEX_FLUSH_ON_CLOSE, this.flushOnClose, flushOnClose);
|
||||
this.flushOnClose = flushOnClose;
|
||||
}
|
||||
|
||||
TimeValue refreshInterval = settings.getAsTime(INDEX_REFRESH_INTERVAL, this.refreshInterval);
|
||||
if (!refreshInterval.equals(this.refreshInterval)) {
|
||||
logger.info("updating refresh_interval from [{}] to [{}]", this.refreshInterval, refreshInterval);
|
||||
if (refreshScheduledFuture != null) {
|
||||
// NOTE: we pass false here so we do NOT attempt Thread.interrupt if EngineRefresher.run is currently running. This is
|
||||
// very important, because doing so can cause files to suddenly be closed if they were doing IO when the interrupt
|
||||
// hit. See https://issues.apache.org/jira/browse/LUCENE-2239
|
||||
FutureUtils.cancel(refreshScheduledFuture);
|
||||
refreshScheduledFuture = null;
|
||||
}
|
||||
this.refreshInterval = refreshInterval;
|
||||
if (refreshInterval.millis() > 0) {
|
||||
refreshScheduledFuture = threadPool.schedule(refreshInterval, ThreadPool.Names.SAME, new EngineRefresher());
|
||||
}
|
||||
}
|
||||
|
||||
long gcDeletesInMillis = settings.getAsTime(EngineConfig.INDEX_GC_DELETES_SETTING, TimeValue.timeValueMillis(config.getGcDeletesInMillis())).millis();
|
||||
if (gcDeletesInMillis != config.getGcDeletesInMillis()) {
|
||||
logger.info("updating {} from [{}] to [{}]", EngineConfig.INDEX_GC_DELETES_SETTING, TimeValue.timeValueMillis(config.getGcDeletesInMillis()), TimeValue.timeValueMillis(gcDeletesInMillis));
|
||||
config.setGcDeletesInMillis(gcDeletesInMillis);
|
||||
change = true;
|
||||
}
|
||||
|
||||
final int maxThreadCount = settings.getAsInt(MergeSchedulerConfig.MAX_THREAD_COUNT, mergeSchedulerConfig.getMaxThreadCount());
|
||||
if (maxThreadCount != mergeSchedulerConfig.getMaxThreadCount()) {
|
||||
logger.info("updating [{}] from [{}] to [{}]", MergeSchedulerConfig.MAX_THREAD_COUNT, mergeSchedulerConfig.getMaxMergeCount(), maxThreadCount);
|
||||
mergeSchedulerConfig.setMaxThreadCount(maxThreadCount);
|
||||
change = true;
|
||||
}
|
||||
|
||||
final int maxMergeCount = settings.getAsInt(MergeSchedulerConfig.MAX_MERGE_COUNT, mergeSchedulerConfig.getMaxMergeCount());
|
||||
if (maxMergeCount != mergeSchedulerConfig.getMaxMergeCount()) {
|
||||
logger.info("updating [{}] from [{}] to [{}]", MergeSchedulerConfig.MAX_MERGE_COUNT, mergeSchedulerConfig.getMaxMergeCount(), maxMergeCount);
|
||||
mergeSchedulerConfig.setMaxMergeCount(maxMergeCount);
|
||||
change = true;
|
||||
}
|
||||
|
||||
final boolean autoThrottle = settings.getAsBoolean(MergeSchedulerConfig.AUTO_THROTTLE, mergeSchedulerConfig.isAutoThrottle());
|
||||
if (autoThrottle != mergeSchedulerConfig.isAutoThrottle()) {
|
||||
logger.info("updating [{}] from [{}] to [{}]", MergeSchedulerConfig.AUTO_THROTTLE, mergeSchedulerConfig.isAutoThrottle(), autoThrottle);
|
||||
mergeSchedulerConfig.setAutoThrottle(autoThrottle);
|
||||
change = true;
|
||||
}
|
||||
}
|
||||
mergePolicyConfig.onRefreshSettings(settings);
|
||||
searchService.onRefreshSettings(settings);
|
||||
if (change) {
|
||||
getEngine().onSettingsChanged();
|
||||
public void onSettingsChanged() {
|
||||
Engine engineOrNull = getEngineOrNull();
|
||||
if (engineOrNull != null) {
|
||||
engineOrNull.onSettingsChanged();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1284,43 +1189,6 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
internalIndexingStats.noopUpdate(type);
|
||||
}
|
||||
|
||||
final class EngineRefresher implements Runnable {
|
||||
@Override
|
||||
public void run() {
|
||||
// we check before if a refresh is needed, if not, we reschedule, otherwise, we fork, refresh, and then reschedule
|
||||
if (!getEngine().refreshNeeded()) {
|
||||
reschedule();
|
||||
return;
|
||||
}
|
||||
threadPool.executor(ThreadPool.Names.REFRESH).execute(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
try {
|
||||
// TODO: now that we use refresh to clear the indexing buffer, we should check here if we did that "recently" and
|
||||
// reschedule if so...
|
||||
if (getEngine().refreshNeeded()) {
|
||||
refresh("schedule");
|
||||
}
|
||||
} catch (Exception e) {
|
||||
handleRefreshException(e);
|
||||
}
|
||||
|
||||
reschedule();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Schedules another (future) refresh, if refresh_interval is still enabled.
|
||||
*/
|
||||
private void reschedule() {
|
||||
synchronized (mutex) {
|
||||
if (state != IndexShardState.CLOSED && refreshInterval.millis() > 0) {
|
||||
refreshScheduledFuture = threadPool.schedule(refreshInterval, ThreadPool.Names.SAME, this);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void checkIndex() throws IOException {
|
||||
if (store.tryIncRef()) {
|
||||
|
@ -1497,7 +1365,7 @@ public class IndexShard extends AbstractIndexShardComponent {
|
|||
};
|
||||
final Engine.Warmer engineWarmer = (searcher, toLevel) -> warmer.warm(searcher, this, idxSettings, toLevel);
|
||||
return new EngineConfig(shardId,
|
||||
threadPool, indexSettings, engineWarmer, store, deletionPolicy, mergePolicyConfig.getMergePolicy(), mergeSchedulerConfig,
|
||||
threadPool, indexSettings, engineWarmer, store, deletionPolicy, indexSettings.getMergePolicy(),
|
||||
mapperService.indexAnalyzer(), similarityService.similarity(mapperService), codecService, shardEventListener, translogRecoveryPerformer, indexCache.query(), cachingPolicy, translogConfig,
|
||||
idxSettings.getSettings().getAsTime(IndexingMemoryController.SHARD_INACTIVE_TIME_SETTING, IndexingMemoryController.SHARD_DEFAULT_INACTIVE_TIME));
|
||||
}
|
||||
|
|
|
@ -29,6 +29,7 @@ import org.elasticsearch.index.engine.EngineFactory;
|
|||
import org.elasticsearch.index.fielddata.IndexFieldDataService;
|
||||
import org.elasticsearch.index.mapper.MapperService;
|
||||
import org.elasticsearch.index.merge.MergeStats;
|
||||
import org.elasticsearch.index.search.stats.SearchSlowLog;
|
||||
import org.elasticsearch.index.similarity.SimilarityService;
|
||||
import org.elasticsearch.index.store.Store;
|
||||
import org.elasticsearch.index.translog.TranslogStats;
|
||||
|
@ -44,8 +45,8 @@ import java.io.IOException;
|
|||
public final class ShadowIndexShard extends IndexShard {
|
||||
|
||||
public ShadowIndexShard(ShardId shardId, IndexSettings indexSettings, ShardPath path, Store store, IndexCache indexCache, MapperService mapperService, SimilarityService similarityService, IndexFieldDataService indexFieldDataService, @Nullable EngineFactory engineFactory,
|
||||
IndexEventListener indexEventListener, IndexSearcherWrapper wrapper, NodeServicesProvider provider) throws IOException {
|
||||
super(shardId, indexSettings, path, store, indexCache, mapperService, similarityService, indexFieldDataService, engineFactory, indexEventListener, wrapper, provider);
|
||||
IndexEventListener indexEventListener, IndexSearcherWrapper wrapper, NodeServicesProvider provider, SearchSlowLog searchSlowLog) throws IOException {
|
||||
super(shardId, indexSettings, path, store, indexCache, mapperService, similarityService, indexFieldDataService, engineFactory, indexEventListener, wrapper, provider, searchSlowLog);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -576,7 +576,11 @@ public class Translog extends AbstractIndexShardComponent implements IndexShardC
|
|||
if (current.getTragicException() != null) {
|
||||
try {
|
||||
close();
|
||||
} catch (AlreadyClosedException inner) {
|
||||
// don't do anything in this case. The AlreadyClosedException comes from TranslogWriter and we should not add it as suppressed because
|
||||
// will contain the Exception ex as cause. See also https://github.com/elastic/elasticsearch/issues/15941
|
||||
} catch (Exception inner) {
|
||||
assert (ex != inner.getCause());
|
||||
ex.addSuppressed(inner);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -256,6 +256,8 @@ public class IndexingMemoryController extends AbstractComponent implements Index
|
|||
} finally {
|
||||
runLock.unlock();
|
||||
}
|
||||
// Could be while we were checking, more bytes arrived:
|
||||
totalBytes = bytesWrittenSinceCheck.addAndGet(bytes);
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
|
|
|
@ -111,8 +111,9 @@ public class OsProbe {
|
|||
* Returns the system load averages
|
||||
*/
|
||||
public double[] getSystemLoadAverage() {
|
||||
if (Constants.LINUX) {
|
||||
double[] loadAverage = readProcLoadavg("/proc/loadavg");
|
||||
if (Constants.LINUX || Constants.FREE_BSD) {
|
||||
final String procLoadAvg = Constants.LINUX ? "/proc/loadavg" : "/compat/linux/proc/loadavg";
|
||||
double[] loadAverage = readProcLoadavg(procLoadAvg);
|
||||
if (loadAverage != null) {
|
||||
return loadAverage;
|
||||
}
|
||||
|
|
|
@ -168,11 +168,6 @@ public class InternalSettingsPreparer {
|
|||
output.put(ClusterName.SETTING, ClusterName.DEFAULT.value());
|
||||
}
|
||||
|
||||
String v = output.get(Settings.SETTINGS_REQUIRE_UNITS);
|
||||
if (v != null) {
|
||||
Settings.setSettingsRequireUnits(Booleans.parseBoolean(v, true));
|
||||
}
|
||||
|
||||
replacePromptPlaceholders(output, terminal);
|
||||
// all settings placeholders have been resolved. resolve the value for the name setting by checking for name,
|
||||
// then looking for node.name, and finally generate one if needed
|
||||
|
|
|
@ -72,8 +72,6 @@ import java.util.Set;
|
|||
* </ul>
|
||||
*/
|
||||
public final class ClassPermission extends BasicPermission {
|
||||
private static final long serialVersionUID = 3530711429252193884L;
|
||||
|
||||
public static final String STANDARD = "<<STANDARD>>";
|
||||
/** Typical set of classes for scripting: basic data types, math, dates, and simple collections */
|
||||
// this is the list from the old grovy sandbox impl (+ some things like String, Iterator, etc that were missing)
|
||||
|
@ -109,17 +107,17 @@ public final class ClassPermission extends BasicPermission {
|
|||
|
||||
/**
|
||||
* Creates a new ClassPermission object.
|
||||
*
|
||||
*
|
||||
* @param name class to grant permission to
|
||||
*/
|
||||
public ClassPermission(String name) {
|
||||
super(name);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Creates a new ClassPermission object.
|
||||
* This constructor exists for use by the {@code Policy} object to instantiate new Permission objects.
|
||||
*
|
||||
*
|
||||
* @param name class to grant permission to
|
||||
* @param actions ignored
|
||||
*/
|
||||
|
@ -144,8 +142,6 @@ public final class ClassPermission extends BasicPermission {
|
|||
// BasicPermissionCollection only handles wildcards, we expand <<STANDARD>> here
|
||||
PermissionCollection impl = super.newPermissionCollection();
|
||||
return new PermissionCollection() {
|
||||
private static final long serialVersionUID = 6792220143549780002L;
|
||||
|
||||
@Override
|
||||
public void add(Permission permission) {
|
||||
if (permission instanceof ClassPermission && STANDARD.equals(permission.getName())) {
|
||||
|
@ -156,12 +152,12 @@ public final class ClassPermission extends BasicPermission {
|
|||
impl.add(permission);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean implies(Permission permission) {
|
||||
return impl.implies(permission);
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public Enumeration<Permission> elements() {
|
||||
return impl.elements();
|
||||
|
|
|
@ -126,7 +126,20 @@ public class DefaultSearchContext extends SearchContext {
|
|||
private Sort sort;
|
||||
private Float minimumScore;
|
||||
private boolean trackScores = false; // when sorting, track scores as well...
|
||||
/**
|
||||
* The original query as sent by the user without the types and aliases
|
||||
* applied. Putting things in here leaks them into highlighting so don't add
|
||||
* things like the type filter or alias filters.
|
||||
*/
|
||||
private ParsedQuery originalQuery;
|
||||
/**
|
||||
* Just like originalQuery but with the filters from types and aliases
|
||||
* applied.
|
||||
*/
|
||||
private ParsedQuery filteredQuery;
|
||||
/**
|
||||
* The query to actually execute.
|
||||
*/
|
||||
private Query query;
|
||||
private ParsedQuery postFilter;
|
||||
private Query aliasFilter;
|
||||
|
@ -210,22 +223,7 @@ public class DefaultSearchContext extends SearchContext {
|
|||
if (queryBoost() != AbstractQueryBuilder.DEFAULT_BOOST) {
|
||||
parsedQuery(new ParsedQuery(new FunctionScoreQuery(query(), new WeightFactorFunction(queryBoost)), parsedQuery()));
|
||||
}
|
||||
Query searchFilter = searchFilter(types());
|
||||
if (searchFilter != null) {
|
||||
if (Queries.isConstantMatchAllQuery(query())) {
|
||||
Query q = new ConstantScoreQuery(searchFilter);
|
||||
if (query().getBoost() != AbstractQueryBuilder.DEFAULT_BOOST) {
|
||||
q = new BoostQuery(q, query().getBoost());
|
||||
}
|
||||
parsedQuery(new ParsedQuery(q, parsedQuery()));
|
||||
} else {
|
||||
BooleanQuery filtered = new BooleanQuery.Builder()
|
||||
.add(query(), Occur.MUST)
|
||||
.add(searchFilter, Occur.FILTER)
|
||||
.build();
|
||||
parsedQuery(new ParsedQuery(filtered, parsedQuery()));
|
||||
}
|
||||
}
|
||||
filteredQuery(buildFilteredQuery());
|
||||
try {
|
||||
this.query = searcher().rewrite(this.query);
|
||||
} catch (IOException e) {
|
||||
|
@ -233,6 +231,26 @@ public class DefaultSearchContext extends SearchContext {
|
|||
}
|
||||
}
|
||||
|
||||
private ParsedQuery buildFilteredQuery() {
|
||||
Query searchFilter = searchFilter(types());
|
||||
if (searchFilter == null) {
|
||||
return originalQuery;
|
||||
}
|
||||
Query result;
|
||||
if (Queries.isConstantMatchAllQuery(query())) {
|
||||
result = new ConstantScoreQuery(searchFilter);
|
||||
if (query().getBoost() != AbstractQueryBuilder.DEFAULT_BOOST) {
|
||||
result = new BoostQuery(result, query().getBoost());
|
||||
}
|
||||
} else {
|
||||
result = new BooleanQuery.Builder()
|
||||
.add(query, Occur.MUST)
|
||||
.add(searchFilter, Occur.FILTER)
|
||||
.build();
|
||||
}
|
||||
return new ParsedQuery(result, originalQuery);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query searchFilter(String[] types) {
|
||||
Query filter = mapperService().searchFilter(types);
|
||||
|
@ -547,6 +565,15 @@ public class DefaultSearchContext extends SearchContext {
|
|||
return this;
|
||||
}
|
||||
|
||||
public ParsedQuery filteredQuery() {
|
||||
return filteredQuery;
|
||||
}
|
||||
|
||||
private void filteredQuery(ParsedQuery filteredQuery) {
|
||||
this.filteredQuery = filteredQuery;
|
||||
this.query = filteredQuery.query();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ParsedQuery parsedQuery() {
|
||||
return this.originalQuery;
|
||||
|
|
|
@ -0,0 +1,117 @@
|
|||
/*
|
||||
* 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.rescore;
|
||||
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
import org.elasticsearch.common.io.stream.Writeable;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.Locale;
|
||||
|
||||
public enum QueryRescoreMode implements Writeable<QueryRescoreMode> {
|
||||
Avg {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return (primary + secondary) / 2;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "avg";
|
||||
}
|
||||
},
|
||||
Max {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return Math.max(primary, secondary);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "max";
|
||||
}
|
||||
},
|
||||
Min {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return Math.min(primary, secondary);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "min";
|
||||
}
|
||||
},
|
||||
Total {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return primary + secondary;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "sum";
|
||||
}
|
||||
},
|
||||
Multiply {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return primary * secondary;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "product";
|
||||
}
|
||||
};
|
||||
|
||||
public abstract float combine(float primary, float secondary);
|
||||
|
||||
static QueryRescoreMode PROTOTYPE = Total;
|
||||
|
||||
@Override
|
||||
public QueryRescoreMode readFrom(StreamInput in) throws IOException {
|
||||
int ordinal = in.readVInt();
|
||||
if (ordinal < 0 || ordinal >= values().length) {
|
||||
throw new IOException("Unknown ScoreMode ordinal [" + ordinal + "]");
|
||||
}
|
||||
return values()[ordinal];
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(StreamOutput out) throws IOException {
|
||||
out.writeVInt(this.ordinal());
|
||||
}
|
||||
|
||||
public static QueryRescoreMode fromString(String scoreMode) {
|
||||
for (QueryRescoreMode mode : values()) {
|
||||
if (scoreMode.toLowerCase(Locale.ROOT).equals(mode.name().toLowerCase(Locale.ROOT))) {
|
||||
return mode;
|
||||
}
|
||||
}
|
||||
throw new IllegalArgumentException("illegal score_mode [" + scoreMode + "]");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return name().toLowerCase(Locale.ROOT);
|
||||
}
|
||||
}
|
|
@ -38,66 +38,6 @@ import java.util.Set;
|
|||
|
||||
public final class QueryRescorer implements Rescorer {
|
||||
|
||||
private static enum ScoreMode {
|
||||
Avg {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return (primary + secondary) / 2;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "avg";
|
||||
}
|
||||
},
|
||||
Max {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return Math.max(primary, secondary);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "max";
|
||||
}
|
||||
},
|
||||
Min {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return Math.min(primary, secondary);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "min";
|
||||
}
|
||||
},
|
||||
Total {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return primary + secondary;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "sum";
|
||||
}
|
||||
},
|
||||
Multiply {
|
||||
@Override
|
||||
public float combine(float primary, float secondary) {
|
||||
return primary * secondary;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "product";
|
||||
}
|
||||
};
|
||||
|
||||
public abstract float combine(float primary, float secondary);
|
||||
}
|
||||
|
||||
public static final Rescorer INSTANCE = new QueryRescorer();
|
||||
public static final String NAME = "query";
|
||||
|
||||
|
@ -170,7 +110,7 @@ public final class QueryRescorer implements Rescorer {
|
|||
rescoreExplain.getValue() * secondaryWeight,
|
||||
"product of:",
|
||||
rescoreExplain, Explanation.match(secondaryWeight, "secondaryWeight"));
|
||||
ScoreMode scoreMode = rescore.scoreMode();
|
||||
QueryRescoreMode scoreMode = rescore.scoreMode();
|
||||
return Explanation.match(
|
||||
scoreMode.combine(prim.getValue(), sec.getValue()),
|
||||
scoreMode + " of:",
|
||||
|
@ -228,7 +168,7 @@ public final class QueryRescorer implements Rescorer {
|
|||
// secondary score?
|
||||
in.scoreDocs[i].score *= ctx.queryWeight();
|
||||
}
|
||||
|
||||
|
||||
// TODO: this is wrong, i.e. we are comparing apples and oranges at this point. It would be better if we always rescored all
|
||||
// incoming first pass hits, instead of allowing recoring of just the top subset:
|
||||
Arrays.sort(in.scoreDocs, SCORE_DOC_COMPARATOR);
|
||||
|
@ -240,13 +180,13 @@ public final class QueryRescorer implements Rescorer {
|
|||
|
||||
public QueryRescoreContext(QueryRescorer rescorer) {
|
||||
super(NAME, 10, rescorer);
|
||||
this.scoreMode = ScoreMode.Total;
|
||||
this.scoreMode = QueryRescoreMode.Total;
|
||||
}
|
||||
|
||||
private ParsedQuery parsedQuery;
|
||||
private float queryWeight = 1.0f;
|
||||
private float rescoreQueryWeight = 1.0f;
|
||||
private ScoreMode scoreMode;
|
||||
private QueryRescoreMode scoreMode;
|
||||
|
||||
public void setParsedQuery(ParsedQuery parsedQuery) {
|
||||
this.parsedQuery = parsedQuery;
|
||||
|
@ -264,7 +204,7 @@ public final class QueryRescorer implements Rescorer {
|
|||
return rescoreQueryWeight;
|
||||
}
|
||||
|
||||
public ScoreMode scoreMode() {
|
||||
public QueryRescoreMode scoreMode() {
|
||||
return scoreMode;
|
||||
}
|
||||
|
||||
|
@ -276,26 +216,13 @@ public final class QueryRescorer implements Rescorer {
|
|||
this.queryWeight = queryWeight;
|
||||
}
|
||||
|
||||
public void setScoreMode(ScoreMode scoreMode) {
|
||||
public void setScoreMode(QueryRescoreMode scoreMode) {
|
||||
this.scoreMode = scoreMode;
|
||||
}
|
||||
|
||||
public void setScoreMode(String scoreMode) {
|
||||
if ("avg".equals(scoreMode)) {
|
||||
setScoreMode(ScoreMode.Avg);
|
||||
} else if ("max".equals(scoreMode)) {
|
||||
setScoreMode(ScoreMode.Max);
|
||||
} else if ("min".equals(scoreMode)) {
|
||||
setScoreMode(ScoreMode.Min);
|
||||
} else if ("total".equals(scoreMode)) {
|
||||
setScoreMode(ScoreMode.Total);
|
||||
} else if ("multiply".equals(scoreMode)) {
|
||||
setScoreMode(ScoreMode.Multiply);
|
||||
} else {
|
||||
throw new IllegalArgumentException("illegal score_mode [" + scoreMode + "]");
|
||||
}
|
||||
setScoreMode(QueryRescoreMode.fromString(scoreMode));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -19,24 +19,36 @@
|
|||
|
||||
package org.elasticsearch.search.rescore;
|
||||
|
||||
import org.elasticsearch.ExceptionsHelper;
|
||||
import org.elasticsearch.common.io.stream.NamedWriteable;
|
||||
import org.elasticsearch.common.io.stream.StreamInput;
|
||||
import org.elasticsearch.common.io.stream.StreamOutput;
|
||||
import org.elasticsearch.common.io.stream.Writeable;
|
||||
import org.elasticsearch.common.xcontent.ToXContent;
|
||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||
import org.elasticsearch.common.xcontent.XContentFactory;
|
||||
import org.elasticsearch.index.query.MatchAllQueryBuilder;
|
||||
import org.elasticsearch.index.query.QueryBuilder;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.Locale;
|
||||
import java.util.Objects;
|
||||
|
||||
public class RescoreBuilder implements ToXContent {
|
||||
public class RescoreBuilder implements ToXContent, Writeable<RescoreBuilder> {
|
||||
|
||||
private Rescorer rescorer;
|
||||
private Integer windowSize;
|
||||
public static final RescoreBuilder PROTOYPE = new RescoreBuilder(new QueryRescorer(new MatchAllQueryBuilder()));
|
||||
|
||||
public static QueryRescorer queryRescorer(QueryBuilder queryBuilder) {
|
||||
return new QueryRescorer(queryBuilder);
|
||||
public RescoreBuilder(Rescorer rescorer) {
|
||||
if (rescorer == null) {
|
||||
throw new IllegalArgumentException("rescorer cannot be null");
|
||||
}
|
||||
this.rescorer = rescorer;
|
||||
}
|
||||
|
||||
public RescoreBuilder rescorer(Rescorer rescorer) {
|
||||
this.rescorer = rescorer;
|
||||
return this;
|
||||
public Rescorer rescorer() {
|
||||
return this.rescorer;
|
||||
}
|
||||
|
||||
public RescoreBuilder windowSize(int windowSize) {
|
||||
|
@ -48,10 +60,6 @@ public class RescoreBuilder implements ToXContent {
|
|||
return windowSize;
|
||||
}
|
||||
|
||||
public boolean isEmpty() {
|
||||
return rescorer == null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
if (windowSize != null) {
|
||||
|
@ -61,13 +69,66 @@ public class RescoreBuilder implements ToXContent {
|
|||
return builder;
|
||||
}
|
||||
|
||||
public static abstract class Rescorer implements ToXContent {
|
||||
public static QueryRescorer queryRescorer(QueryBuilder<?> queryBuilder) {
|
||||
return new QueryRescorer(queryBuilder);
|
||||
}
|
||||
|
||||
@Override
|
||||
public final int hashCode() {
|
||||
return Objects.hash(windowSize, rescorer);
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean equals(Object obj) {
|
||||
if (this == obj) {
|
||||
return true;
|
||||
}
|
||||
if (obj == null || getClass() != obj.getClass()) {
|
||||
return false;
|
||||
}
|
||||
RescoreBuilder other = (RescoreBuilder) obj;
|
||||
return Objects.equals(windowSize, other.windowSize) &&
|
||||
Objects.equals(rescorer, other.rescorer);
|
||||
}
|
||||
|
||||
@Override
|
||||
public RescoreBuilder readFrom(StreamInput in) throws IOException {
|
||||
RescoreBuilder builder = new RescoreBuilder(in.readRescorer());
|
||||
Integer windowSize = in.readOptionalVInt();
|
||||
if (windowSize != null) {
|
||||
builder.windowSize(windowSize);
|
||||
}
|
||||
return builder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(StreamOutput out) throws IOException {
|
||||
out.writeRescorer(rescorer);
|
||||
out.writeOptionalVInt(this.windowSize);
|
||||
}
|
||||
|
||||
@Override
|
||||
public final String toString() {
|
||||
try {
|
||||
XContentBuilder builder = XContentFactory.jsonBuilder();
|
||||
builder.prettyPrint();
|
||||
builder.startObject();
|
||||
toXContent(builder, EMPTY_PARAMS);
|
||||
builder.endObject();
|
||||
return builder.string();
|
||||
} catch (Exception e) {
|
||||
return "{ \"error\" : \"" + ExceptionsHelper.detailedMessage(e) + "\"}";
|
||||
}
|
||||
}
|
||||
|
||||
public static abstract class Rescorer implements ToXContent, NamedWriteable<Rescorer> {
|
||||
|
||||
private String name;
|
||||
|
||||
public Rescorer(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
builder.startObject(name);
|
||||
|
@ -78,23 +139,41 @@ public class RescoreBuilder implements ToXContent {
|
|||
|
||||
protected abstract XContentBuilder innerToXContent(XContentBuilder builder, Params params) throws IOException;
|
||||
|
||||
@Override
|
||||
public abstract int hashCode();
|
||||
|
||||
@Override
|
||||
public abstract boolean equals(Object obj);
|
||||
}
|
||||
|
||||
public static class QueryRescorer extends Rescorer {
|
||||
|
||||
private static final String NAME = "query";
|
||||
private QueryBuilder queryBuilder;
|
||||
private Float rescoreQueryWeight;
|
||||
private Float queryWeight;
|
||||
private String scoreMode;
|
||||
public static final QueryRescorer PROTOTYPE = new QueryRescorer(new MatchAllQueryBuilder());
|
||||
public static final float DEFAULT_RESCORE_QUERYWEIGHT = 1.0f;
|
||||
public static final float DEFAULT_QUERYWEIGHT = 1.0f;
|
||||
public static final QueryRescoreMode DEFAULT_SCORE_MODE = QueryRescoreMode.Total;
|
||||
private final QueryBuilder<?> queryBuilder;
|
||||
private float rescoreQueryWeight = DEFAULT_RESCORE_QUERYWEIGHT;
|
||||
private float queryWeight = DEFAULT_QUERYWEIGHT;
|
||||
private QueryRescoreMode scoreMode = DEFAULT_SCORE_MODE;
|
||||
|
||||
/**
|
||||
* Creates a new {@link QueryRescorer} instance
|
||||
* @param builder the query builder to build the rescore query from
|
||||
*/
|
||||
public QueryRescorer(QueryBuilder builder) {
|
||||
public QueryRescorer(QueryBuilder<?> builder) {
|
||||
super(NAME);
|
||||
this.queryBuilder = builder;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the query used for this rescore query
|
||||
*/
|
||||
public QueryBuilder<?> getRescoreQuery() {
|
||||
return this.queryBuilder;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the original query weight for rescoring. The default is <tt>1.0</tt>
|
||||
*/
|
||||
|
@ -103,6 +182,14 @@ public class RescoreBuilder implements ToXContent {
|
|||
return this;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Gets the original query weight for rescoring. The default is <tt>1.0</tt>
|
||||
*/
|
||||
public float getQueryWeight() {
|
||||
return this.queryWeight;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the original query weight for rescoring. The default is <tt>1.0</tt>
|
||||
*/
|
||||
|
@ -112,27 +199,76 @@ public class RescoreBuilder implements ToXContent {
|
|||
}
|
||||
|
||||
/**
|
||||
* Sets the original query score mode. The default is <tt>total</tt>
|
||||
* Gets the original query weight for rescoring. The default is <tt>1.0</tt>
|
||||
*/
|
||||
public QueryRescorer setScoreMode(String scoreMode) {
|
||||
public float getRescoreQueryWeight() {
|
||||
return this.rescoreQueryWeight;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the original query score mode. The default is {@link QueryRescoreMode#Total}.
|
||||
*/
|
||||
public QueryRescorer setScoreMode(QueryRescoreMode scoreMode) {
|
||||
this.scoreMode = scoreMode;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the original query score mode. The default is <tt>total</tt>
|
||||
*/
|
||||
public QueryRescoreMode getScoreMode() {
|
||||
return this.scoreMode;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected XContentBuilder innerToXContent(XContentBuilder builder, Params params) throws IOException {
|
||||
builder.field("rescore_query", queryBuilder);
|
||||
if (queryWeight != null) {
|
||||
builder.field("query_weight", queryWeight);
|
||||
}
|
||||
if (rescoreQueryWeight != null) {
|
||||
builder.field("rescore_query_weight", rescoreQueryWeight);
|
||||
}
|
||||
if (scoreMode != null) {
|
||||
builder.field("score_mode", scoreMode);
|
||||
}
|
||||
builder.field("query_weight", queryWeight);
|
||||
builder.field("rescore_query_weight", rescoreQueryWeight);
|
||||
builder.field("score_mode", scoreMode.name().toLowerCase(Locale.ROOT));
|
||||
return builder;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public final int hashCode() {
|
||||
return Objects.hash(getClass(), scoreMode, queryWeight, rescoreQueryWeight, queryBuilder);
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean equals(Object obj) {
|
||||
if (this == obj) {
|
||||
return true;
|
||||
}
|
||||
if (obj == null || getClass() != obj.getClass()) {
|
||||
return false;
|
||||
}
|
||||
QueryRescorer other = (QueryRescorer) obj;
|
||||
return Objects.equals(scoreMode, other.scoreMode) &&
|
||||
Objects.equals(queryWeight, other.queryWeight) &&
|
||||
Objects.equals(rescoreQueryWeight, other.rescoreQueryWeight) &&
|
||||
Objects.equals(queryBuilder, other.queryBuilder);
|
||||
}
|
||||
|
||||
@Override
|
||||
public QueryRescorer readFrom(StreamInput in) throws IOException {
|
||||
QueryRescorer rescorer = new QueryRescorer(in.readQuery());
|
||||
rescorer.setScoreMode(QueryRescoreMode.PROTOTYPE.readFrom(in));
|
||||
rescorer.setRescoreQueryWeight(in.readFloat());
|
||||
rescorer.setQueryWeight(in.readFloat());
|
||||
return rescorer;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(StreamOutput out) throws IOException {
|
||||
out.writeQuery(queryBuilder);
|
||||
scoreMode.writeTo(out);
|
||||
out.writeFloat(rescoreQueryWeight);
|
||||
out.writeFloat(queryWeight);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getWriteableName() {
|
||||
return NAME;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -24,8 +24,6 @@ import org.joda.time.chrono.ISOChronology;
|
|||
import org.joda.time.convert.ConverterManager;
|
||||
import org.joda.time.convert.InstantConverter;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* BaseDateTime is an abstract implementation of ReadableDateTime that stores
|
||||
* data in <code>long</code> and <code>Chronology</code> fields.
|
||||
|
@ -43,13 +41,7 @@ import java.io.Serializable;
|
|||
*/
|
||||
public abstract class BaseDateTime
|
||||
extends AbstractDateTime
|
||||
implements ReadableDateTime, Serializable {
|
||||
|
||||
/**
|
||||
* Serialization lock
|
||||
*/
|
||||
private static final long serialVersionUID = -6728882245981L;
|
||||
|
||||
implements ReadableDateTime {
|
||||
/**
|
||||
* The millis from 1970-01-01T00:00:00Z
|
||||
*/
|
||||
|
|
|
@ -118,4 +118,7 @@ grant {
|
|||
|
||||
// load averages on Linux
|
||||
permission java.io.FilePermission "/proc/loadavg", "read";
|
||||
|
||||
// load averages on FreeBSD
|
||||
permission java.io.FilePermission "/compat/linux/proc/loadavg", "read";
|
||||
};
|
||||
|
|
|
@ -159,16 +159,13 @@ public class BlendedTermQueryTests extends ESTestCase {
|
|||
{
|
||||
BooleanQuery.Builder query = new BooleanQuery.Builder();
|
||||
query.setDisableCoord(true);
|
||||
DisjunctionMaxQuery uname = new DisjunctionMaxQuery(0.0f);
|
||||
uname.add(new TermQuery(new Term("username", "foo")));
|
||||
uname.add(new TermQuery(new Term("song", "foo")));
|
||||
DisjunctionMaxQuery uname = new DisjunctionMaxQuery(
|
||||
Arrays.asList(new TermQuery(new Term("username", "foo")), new TermQuery(new Term("song", "foo"))), 0.0f);
|
||||
|
||||
DisjunctionMaxQuery s = new DisjunctionMaxQuery(0.0f);
|
||||
s.add(new TermQuery(new Term("username", "fighers")));
|
||||
s.add(new TermQuery(new Term("song", "fighers")));
|
||||
DisjunctionMaxQuery gen = new DisjunctionMaxQuery(0f);
|
||||
gen.add(new TermQuery(new Term("username", "generator")));
|
||||
gen.add(new TermQuery(new Term("song", "generator")));
|
||||
DisjunctionMaxQuery s = new DisjunctionMaxQuery(
|
||||
Arrays.asList(new TermQuery(new Term("username", "fighers")), new TermQuery(new Term("song", "fighers"))), 0.0f);
|
||||
DisjunctionMaxQuery gen = new DisjunctionMaxQuery(
|
||||
Arrays.asList(new TermQuery(new Term("username", "generator")), new TermQuery(new Term("song", "generator"))), 0f);
|
||||
query.add(uname, BooleanClause.Occur.SHOULD);
|
||||
query.add(s, BooleanClause.Occur.SHOULD);
|
||||
query.add(gen, BooleanClause.Occur.SHOULD);
|
||||
|
|
|
@ -200,6 +200,7 @@ public class CreateIndexIT extends ESIntegTestCase {
|
|||
}
|
||||
}
|
||||
|
||||
@AwaitsFix(bugUrl = "https://github.com/elastic/elasticsearch/issues/14932,https://github.com/elastic/elasticsearch/pull/15853" )
|
||||
public void testCreateAndDeleteIndexConcurrently() throws InterruptedException {
|
||||
createIndex("test");
|
||||
final AtomicInteger indexVersion = new AtomicInteger(0);
|
||||
|
|
|
@ -22,7 +22,7 @@ package org.elasticsearch.action.admin.indices.segments;
|
|||
import org.elasticsearch.action.support.IndicesOptions;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.index.engine.Segment;
|
||||
import org.elasticsearch.index.shard.MergePolicyConfig;
|
||||
import org.elasticsearch.index.MergePolicyConfig;
|
||||
import org.elasticsearch.indices.IndexClosedException;
|
||||
import org.elasticsearch.test.ESSingleNodeTestCase;
|
||||
import org.junit.Before;
|
||||
|
|
|
@ -268,7 +268,7 @@ public class TransportBroadcastByNodeActionTests extends ESTestCase {
|
|||
PlainActionFuture<Response> listener = new PlainActionFuture<>();
|
||||
|
||||
action.new AsyncAction(request, listener).start();
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequests = transport.capturedRequestsByTargetNode();
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequests = transport.getCapturedRequestsByTargetNodeAndClear();
|
||||
|
||||
ShardsIterator shardIt = clusterService.state().routingTable().allShards(new String[]{TEST_INDEX});
|
||||
Set<String> set = new HashSet<>();
|
||||
|
@ -303,7 +303,7 @@ public class TransportBroadcastByNodeActionTests extends ESTestCase {
|
|||
|
||||
action.new AsyncAction(request, listener).start();
|
||||
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequests = transport.capturedRequestsByTargetNode();
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequests = transport.getCapturedRequestsByTargetNodeAndClear();
|
||||
|
||||
// the master should not be in the list of nodes that requests were sent to
|
||||
ShardsIterator shardIt = clusterService.state().routingTable().allShards(new String[]{TEST_INDEX});
|
||||
|
@ -389,8 +389,7 @@ public class TransportBroadcastByNodeActionTests extends ESTestCase {
|
|||
}
|
||||
|
||||
action.new AsyncAction(request, listener).start();
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequests = transport.capturedRequestsByTargetNode();
|
||||
transport.clear();
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequests = transport.getCapturedRequestsByTargetNodeAndClear();
|
||||
|
||||
ShardsIterator shardIt = clusterService.state().getRoutingTable().allShards(new String[]{TEST_INDEX});
|
||||
Map<String, List<ShardRouting>> map = new HashMap<>();
|
||||
|
|
|
@ -68,6 +68,7 @@ import java.util.ArrayList;
|
|||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.CountDownLatch;
|
||||
import java.util.concurrent.ExecutionException;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
@ -193,7 +194,8 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
|
||||
final IndexShardRoutingTable shardRoutingTable = clusterService.state().routingTable().index(index).shard(shardId.id());
|
||||
final String primaryNodeId = shardRoutingTable.primaryShard().currentNodeId();
|
||||
final List<CapturingTransport.CapturedRequest> capturedRequests = transport.capturedRequestsByTargetNode().get(primaryNodeId);
|
||||
final List<CapturingTransport.CapturedRequest> capturedRequests =
|
||||
transport.getCapturedRequestsByTargetNodeAndClear().get(primaryNodeId);
|
||||
assertThat(capturedRequests, notNullValue());
|
||||
assertThat(capturedRequests.size(), equalTo(1));
|
||||
assertThat(capturedRequests.get(0).action, equalTo("testAction[p]"));
|
||||
|
@ -235,7 +237,7 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
reroutePhase.run();
|
||||
assertThat(request.shardId(), equalTo(shardId));
|
||||
logger.info("--> primary is assigned to [{}], checking request forwarded", primaryNodeId);
|
||||
final List<CapturingTransport.CapturedRequest> capturedRequests = transport.capturedRequestsByTargetNode().get(primaryNodeId);
|
||||
final List<CapturingTransport.CapturedRequest> capturedRequests = transport.getCapturedRequestsByTargetNodeAndClear().get(primaryNodeId);
|
||||
assertThat(capturedRequests, notNullValue());
|
||||
assertThat(capturedRequests.size(), equalTo(1));
|
||||
if (clusterService.state().nodes().localNodeId().equals(primaryNodeId)) {
|
||||
|
@ -256,7 +258,7 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
primaryPhase.run();
|
||||
assertThat("request was not processed on primary", request.processedOnPrimary.get(), equalTo(true));
|
||||
final String replicaNodeId = clusterService.state().getRoutingTable().shardRoutingTable(index, shardId.id()).replicaShards().get(0).currentNodeId();
|
||||
final List<CapturingTransport.CapturedRequest> requests = transport.capturedRequestsByTargetNode().get(replicaNodeId);
|
||||
final List<CapturingTransport.CapturedRequest> requests = transport.getCapturedRequestsByTargetNodeAndClear().get(replicaNodeId);
|
||||
assertThat(requests, notNullValue());
|
||||
assertThat(requests.size(), equalTo(1));
|
||||
assertThat("replica request was not sent", requests.get(0).action, equalTo("testAction[r]"));
|
||||
|
@ -286,8 +288,9 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
TransportReplicationAction<Request, Request, Response>.PrimaryPhase primaryPhase = actionWithAddedReplicaAfterPrimaryOp.new PrimaryPhase(request, createTransportChannel(listener));
|
||||
primaryPhase.run();
|
||||
assertThat("request was not processed on primary", request.processedOnPrimary.get(), equalTo(true));
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequestsByTargetNode = transport.getCapturedRequestsByTargetNodeAndClear();
|
||||
for (ShardRouting replica : stateWithAddedReplicas.getRoutingTable().shardRoutingTable(index, shardId.id()).replicaShards()) {
|
||||
List<CapturingTransport.CapturedRequest> requests = transport.capturedRequestsByTargetNode().get(replica.currentNodeId());
|
||||
List<CapturingTransport.CapturedRequest> requests = capturedRequestsByTargetNode.get(replica.currentNodeId());
|
||||
assertThat(requests, notNullValue());
|
||||
assertThat(requests.size(), equalTo(1));
|
||||
assertThat("replica request was not sent", requests.get(0).action, equalTo("testAction[r]"));
|
||||
|
@ -319,8 +322,9 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
primaryPhase.run();
|
||||
assertThat("request was not processed on primary", request.processedOnPrimary.get(), equalTo(true));
|
||||
ShardRouting relocatingReplicaShard = stateWithRelocatingReplica.getRoutingTable().shardRoutingTable(index, shardId.id()).replicaShards().get(0);
|
||||
Map<String, List<CapturingTransport.CapturedRequest>> capturedRequestsByTargetNode = transport.getCapturedRequestsByTargetNodeAndClear();
|
||||
for (String node : new String[] {relocatingReplicaShard.currentNodeId(), relocatingReplicaShard.relocatingNodeId()}) {
|
||||
List<CapturingTransport.CapturedRequest> requests = transport.capturedRequestsByTargetNode().get(node);
|
||||
List<CapturingTransport.CapturedRequest> requests = capturedRequestsByTargetNode.get(node);
|
||||
assertThat(requests, notNullValue());
|
||||
assertThat(requests.size(), equalTo(1));
|
||||
assertThat("replica request was not sent to replica", requests.get(0).action, equalTo("testAction[r]"));
|
||||
|
@ -489,8 +493,7 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
assertThat(replicationPhase.totalShards(), equalTo(totalShards));
|
||||
assertThat(replicationPhase.pending(), equalTo(assignedReplicas));
|
||||
replicationPhase.run();
|
||||
final CapturingTransport.CapturedRequest[] capturedRequests = transport.capturedRequests();
|
||||
transport.clear();
|
||||
final CapturingTransport.CapturedRequest[] capturedRequests = transport.getCapturedRequestsAndClear();
|
||||
|
||||
HashMap<String, Request> nodesSentTo = new HashMap<>();
|
||||
boolean executeOnReplica =
|
||||
|
@ -544,8 +547,7 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
logger.debug("--> simulating failure on {} with [{}]", capturedRequest.node, t.getClass().getSimpleName());
|
||||
transport.handleResponse(capturedRequest.requestId, t);
|
||||
if (criticalFailure) {
|
||||
CapturingTransport.CapturedRequest[] shardFailedRequests = transport.capturedRequests();
|
||||
transport.clear();
|
||||
CapturingTransport.CapturedRequest[] shardFailedRequests = transport.getCapturedRequestsAndClear();
|
||||
assertEquals(1, shardFailedRequests.length);
|
||||
CapturingTransport.CapturedRequest shardFailedRequest = shardFailedRequests[0];
|
||||
// get the shard the request was sent to
|
||||
|
@ -636,19 +638,17 @@ public class TransportReplicationActionTests extends ESTestCase {
|
|||
assertThat(transport.capturedRequests().length, equalTo(1));
|
||||
// try once with successful response
|
||||
transport.handleResponse(transport.capturedRequests()[0].requestId, TransportResponse.Empty.INSTANCE);
|
||||
assertIndexShardCounter(1);
|
||||
transport.clear();
|
||||
assertIndexShardCounter(1);
|
||||
request = new Request(shardId).timeout("100ms");
|
||||
primaryPhase = action.new PrimaryPhase(request, createTransportChannel(listener));
|
||||
primaryPhase.run();
|
||||
assertIndexShardCounter(2);
|
||||
CapturingTransport.CapturedRequest[] replicationRequests = transport.capturedRequests();
|
||||
transport.clear();
|
||||
CapturingTransport.CapturedRequest[] replicationRequests = transport.getCapturedRequestsAndClear();
|
||||
assertThat(replicationRequests.length, equalTo(1));
|
||||
// try with failure response
|
||||
transport.handleResponse(replicationRequests[0].requestId, new CorruptIndexException("simulated", (String) null));
|
||||
CapturingTransport.CapturedRequest[] shardFailedRequests = transport.capturedRequests();
|
||||
transport.clear();
|
||||
CapturingTransport.CapturedRequest[] shardFailedRequests = transport.getCapturedRequestsAndClear();
|
||||
assertEquals(1, shardFailedRequests.length);
|
||||
transport.handleResponse(shardFailedRequests[0].requestId, TransportResponse.Empty.INSTANCE);
|
||||
assertIndexShardCounter(1);
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
|
||||
package org.elasticsearch.action.update;
|
||||
|
||||
import org.elasticsearch.ElasticsearchParseException;
|
||||
import org.elasticsearch.Version;
|
||||
import org.elasticsearch.action.index.IndexRequest;
|
||||
import org.elasticsearch.common.io.stream.Streamable;
|
||||
|
@ -166,4 +167,15 @@ public class UpdateRequestTests extends ESTestCase {
|
|||
indexAction = (IndexRequest) action;
|
||||
assertThat(indexAction.ttl(), is(providedTTLValue));
|
||||
}
|
||||
|
||||
// Related to issue #15822
|
||||
public void testInvalidBodyThrowsParseException() throws Exception {
|
||||
UpdateRequest request = new UpdateRequest("test", "type", "1");
|
||||
try {
|
||||
request.source(new byte[] { (byte) '"' });
|
||||
fail("Should have thrown a ElasticsearchParseException");
|
||||
} catch (ElasticsearchParseException e) {
|
||||
assertThat(e.getMessage(), equalTo("Failed to derive xcontent"));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -46,11 +46,11 @@ import org.elasticsearch.common.xcontent.XContentParser;
|
|||
import org.elasticsearch.common.xcontent.XContentType;
|
||||
import org.elasticsearch.env.NodeEnvironment;
|
||||
import org.elasticsearch.gateway.MetaDataStateFormat;
|
||||
import org.elasticsearch.index.engine.EngineConfig;
|
||||
import org.elasticsearch.index.IndexSettings;
|
||||
import org.elasticsearch.index.engine.Segment;
|
||||
import org.elasticsearch.index.mapper.string.StringFieldMapperPositionIncrementGapTests;
|
||||
import org.elasticsearch.index.query.QueryBuilders;
|
||||
import org.elasticsearch.index.shard.MergePolicyConfig;
|
||||
import org.elasticsearch.index.MergePolicyConfig;
|
||||
import org.elasticsearch.search.SearchHit;
|
||||
import org.elasticsearch.search.aggregations.AggregationBuilders;
|
||||
import org.elasticsearch.search.aggregations.bucket.histogram.Histogram;
|
||||
|
@ -383,7 +383,7 @@ public class OldIndexBackwardsCompatibilityIT extends ESIntegTestCase {
|
|||
assertThat(source, Matchers.hasKey("foo"));
|
||||
|
||||
assertAcked(client().admin().indices().prepareUpdateSettings(indexName).setSettings(Settings.builder()
|
||||
.put("refresh_interval", EngineConfig.DEFAULT_REFRESH_INTERVAL)
|
||||
.put("refresh_interval", IndexSettings.DEFAULT_REFRESH_INTERVAL)
|
||||
.build()));
|
||||
}
|
||||
|
||||
|
|
|
@ -135,8 +135,7 @@ public class ShardStateActionTests extends ESTestCase {
|
|||
}
|
||||
});
|
||||
|
||||
final CapturingTransport.CapturedRequest[] capturedRequests = transport.capturedRequests();
|
||||
transport.clear();
|
||||
final CapturingTransport.CapturedRequest[] capturedRequests = transport.getCapturedRequestsAndClear();
|
||||
assertThat(capturedRequests.length, equalTo(1));
|
||||
assert !failure.get();
|
||||
transport.handleResponse(capturedRequests[0].requestId, new TransportException("simulated"));
|
||||
|
@ -171,8 +170,7 @@ public class ShardStateActionTests extends ESTestCase {
|
|||
progress.set(true);
|
||||
assertTrue(timedOut.get());
|
||||
|
||||
final CapturingTransport.CapturedRequest[] capturedRequests = transport.capturedRequests();
|
||||
transport.clear();
|
||||
final CapturingTransport.CapturedRequest[] capturedRequests = transport.getCapturedRequestsAndClear();
|
||||
assertThat(capturedRequests.length, equalTo(1));
|
||||
}
|
||||
|
||||
|
|
|
@ -22,11 +22,14 @@ package org.elasticsearch.cluster.routing;
|
|||
import org.elasticsearch.cluster.ClusterState;
|
||||
import org.elasticsearch.common.settings.Settings;
|
||||
import org.elasticsearch.gateway.GatewayAllocator;
|
||||
import org.elasticsearch.plugins.Plugin;
|
||||
import org.elasticsearch.test.ESIntegTestCase;
|
||||
import org.elasticsearch.test.InternalTestCluster;
|
||||
import org.elasticsearch.test.disruption.NetworkDisconnectPartition;
|
||||
import org.elasticsearch.test.transport.MockTransportService;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
|
@ -41,6 +44,12 @@ import static org.hamcrest.Matchers.equalTo;
|
|||
@ESIntegTestCase.SuppressLocalMode
|
||||
public class PrimaryAllocationIT extends ESIntegTestCase {
|
||||
|
||||
@Override
|
||||
protected Collection<Class<? extends Plugin>> nodePlugins() {
|
||||
// disruption tests need MockTransportService
|
||||
return pluginList(MockTransportService.TestPlugin.class);
|
||||
}
|
||||
|
||||
public void testDoNotAllowStaleReplicasToBePromotedToPrimary() throws Exception {
|
||||
logger.info("--> starting 3 nodes, 1 master, 2 data");
|
||||
String master = internalCluster().startMasterOnlyNode(Settings.EMPTY);
|
||||
|
|
|
@ -329,19 +329,6 @@ public class ClusterSettingsIT extends ESIntegTestCase {
|
|||
}
|
||||
}
|
||||
|
||||
public void testMissingUnitsLenient() {
|
||||
try {
|
||||
createNode(Settings.builder().put(Settings.SETTINGS_REQUIRE_UNITS, "false").build());
|
||||
assertAcked(prepareCreate("test"));
|
||||
ensureGreen();
|
||||
client().admin().indices().prepareUpdateSettings("test").setSettings(Settings.builder().put("index.refresh_interval", "10")).execute().actionGet();
|
||||
} finally {
|
||||
// Restore the default so subsequent tests require units:
|
||||
assertFalse(Settings.getSettingsRequireUnits());
|
||||
Settings.setSettingsRequireUnits(true);
|
||||
}
|
||||
}
|
||||
|
||||
private void createNode(Settings settings) {
|
||||
internalCluster().startNode(Settings.builder()
|
||||
.put(ClusterName.SETTING, "ClusterSettingsIT")
|
||||
|
|
|
@ -34,6 +34,7 @@ import com.vividsolutions.jts.geom.LinearRing;
|
|||
import com.vividsolutions.jts.geom.MultiLineString;
|
||||
import com.vividsolutions.jts.geom.Point;
|
||||
import com.vividsolutions.jts.geom.Polygon;
|
||||
|
||||
import org.elasticsearch.ElasticsearchParseException;
|
||||
import org.elasticsearch.common.geo.builders.ShapeBuilder;
|
||||
import org.elasticsearch.common.xcontent.XContentFactory;
|
||||
|
|
|
@ -28,6 +28,8 @@ import com.spatial4j.core.shape.impl.PointImpl;
|
|||
import com.vividsolutions.jts.geom.Coordinate;
|
||||
import com.vividsolutions.jts.geom.LineString;
|
||||
import com.vividsolutions.jts.geom.Polygon;
|
||||
|
||||
import org.elasticsearch.common.geo.builders.CoordinatesBuilder;
|
||||
import org.elasticsearch.common.geo.builders.LineStringBuilder;
|
||||
import org.elasticsearch.common.geo.builders.PolygonBuilder;
|
||||
import org.elasticsearch.common.geo.builders.ShapeBuilder;
|
||||
|
@ -50,7 +52,7 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
}
|
||||
|
||||
public void testNewRectangle() {
|
||||
Rectangle rectangle = ShapeBuilders.newEnvelope().topLeft(-45, 30).bottomRight(45, -30).build();
|
||||
Rectangle rectangle = ShapeBuilders.newEnvelope(new Coordinate(-45, 30), new Coordinate(45, -30)).build();
|
||||
assertEquals(-45D, rectangle.getMinX(), 0.0d);
|
||||
assertEquals(-30D, rectangle.getMinY(), 0.0d);
|
||||
assertEquals(45D, rectangle.getMaxX(), 0.0d);
|
||||
|
@ -58,12 +60,12 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
}
|
||||
|
||||
public void testNewPolygon() {
|
||||
Polygon polygon = ShapeBuilders.newPolygon()
|
||||
.point(-45, 30)
|
||||
.point(45, 30)
|
||||
.point(45, -30)
|
||||
.point(-45, -30)
|
||||
.point(-45, 30).toPolygon();
|
||||
Polygon polygon = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-45, 30)
|
||||
.coordinate(45, 30)
|
||||
.coordinate(45, -30)
|
||||
.coordinate(-45, -30)
|
||||
.coordinate(-45, 30)).toPolygon();
|
||||
|
||||
LineString exterior = polygon.getExteriorRing();
|
||||
assertEquals(exterior.getCoordinateN(0), new Coordinate(-45, 30));
|
||||
|
@ -73,12 +75,12 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
}
|
||||
|
||||
public void testNewPolygon_coordinate() {
|
||||
Polygon polygon = ShapeBuilders.newPolygon()
|
||||
.point(new Coordinate(-45, 30))
|
||||
.point(new Coordinate(45, 30))
|
||||
.point(new Coordinate(45, -30))
|
||||
.point(new Coordinate(-45, -30))
|
||||
.point(new Coordinate(-45, 30)).toPolygon();
|
||||
Polygon polygon = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(new Coordinate(-45, 30))
|
||||
.coordinate(new Coordinate(45, 30))
|
||||
.coordinate(new Coordinate(45, -30))
|
||||
.coordinate(new Coordinate(-45, -30))
|
||||
.coordinate(new Coordinate(-45, 30))).toPolygon();
|
||||
|
||||
LineString exterior = polygon.getExteriorRing();
|
||||
assertEquals(exterior.getCoordinateN(0), new Coordinate(-45, 30));
|
||||
|
@ -88,8 +90,9 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
}
|
||||
|
||||
public void testNewPolygon_coordinates() {
|
||||
Polygon polygon = ShapeBuilders.newPolygon()
|
||||
.points(new Coordinate(-45, 30), new Coordinate(45, 30), new Coordinate(45, -30), new Coordinate(-45, -30), new Coordinate(-45, 30)).toPolygon();
|
||||
Polygon polygon = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinates(new Coordinate(-45, 30), new Coordinate(45, 30), new Coordinate(45, -30), new Coordinate(-45, -30), new Coordinate(-45, 30))
|
||||
).toPolygon();
|
||||
|
||||
LineString exterior = polygon.getExteriorRing();
|
||||
assertEquals(exterior.getCoordinateN(0), new Coordinate(-45, 30));
|
||||
|
@ -100,86 +103,93 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
|
||||
public void testLineStringBuilder() {
|
||||
// Building a simple LineString
|
||||
ShapeBuilders.newLineString()
|
||||
.point(-130.0, 55.0)
|
||||
.point(-130.0, -40.0)
|
||||
.point(-15.0, -40.0)
|
||||
.point(-20.0, 50.0)
|
||||
.point(-45.0, 50.0)
|
||||
.point(-45.0, -15.0)
|
||||
.point(-110.0, -15.0)
|
||||
.point(-110.0, 55.0).build();
|
||||
ShapeBuilders.newLineString(new CoordinatesBuilder()
|
||||
.coordinate(-130.0, 55.0)
|
||||
.coordinate(-130.0, -40.0)
|
||||
.coordinate(-15.0, -40.0)
|
||||
.coordinate(-20.0, 50.0)
|
||||
.coordinate(-45.0, 50.0)
|
||||
.coordinate(-45.0, -15.0)
|
||||
.coordinate(-110.0, -15.0)
|
||||
.coordinate(-110.0, 55.0)).build();
|
||||
|
||||
// Building a linestring that needs to be wrapped
|
||||
ShapeBuilders.newLineString()
|
||||
.point(100.0, 50.0)
|
||||
.point(110.0, -40.0)
|
||||
.point(240.0, -40.0)
|
||||
.point(230.0, 60.0)
|
||||
.point(200.0, 60.0)
|
||||
.point(200.0, -30.0)
|
||||
.point(130.0, -30.0)
|
||||
.point(130.0, 60.0)
|
||||
ShapeBuilders.newLineString(new CoordinatesBuilder()
|
||||
.coordinate(100.0, 50.0)
|
||||
.coordinate(110.0, -40.0)
|
||||
.coordinate(240.0, -40.0)
|
||||
.coordinate(230.0, 60.0)
|
||||
.coordinate(200.0, 60.0)
|
||||
.coordinate(200.0, -30.0)
|
||||
.coordinate(130.0, -30.0)
|
||||
.coordinate(130.0, 60.0)
|
||||
)
|
||||
.build();
|
||||
|
||||
// Building a lineString on the dateline
|
||||
ShapeBuilders.newLineString()
|
||||
.point(-180.0, 80.0)
|
||||
.point(-180.0, 40.0)
|
||||
.point(-180.0, -40.0)
|
||||
.point(-180.0, -80.0)
|
||||
ShapeBuilders.newLineString(new CoordinatesBuilder()
|
||||
.coordinate(-180.0, 80.0)
|
||||
.coordinate(-180.0, 40.0)
|
||||
.coordinate(-180.0, -40.0)
|
||||
.coordinate(-180.0, -80.0)
|
||||
)
|
||||
.build();
|
||||
|
||||
// Building a lineString on the dateline
|
||||
ShapeBuilders.newLineString()
|
||||
.point(180.0, 80.0)
|
||||
.point(180.0, 40.0)
|
||||
.point(180.0, -40.0)
|
||||
.point(180.0, -80.0)
|
||||
ShapeBuilders.newLineString(new CoordinatesBuilder()
|
||||
.coordinate(180.0, 80.0)
|
||||
.coordinate(180.0, 40.0)
|
||||
.coordinate(180.0, -40.0)
|
||||
.coordinate(180.0, -80.0)
|
||||
)
|
||||
.build();
|
||||
}
|
||||
|
||||
public void testMultiLineString() {
|
||||
ShapeBuilders.newMultiLinestring()
|
||||
.linestring(new LineStringBuilder()
|
||||
.point(-100.0, 50.0)
|
||||
.point(50.0, 50.0)
|
||||
.point(50.0, 20.0)
|
||||
.point(-100.0, 20.0)
|
||||
.linestring(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-100.0, 50.0)
|
||||
.coordinate(50.0, 50.0)
|
||||
.coordinate(50.0, 20.0)
|
||||
.coordinate(-100.0, 20.0)
|
||||
)
|
||||
)
|
||||
.linestring(new LineStringBuilder()
|
||||
.point(-100.0, 20.0)
|
||||
.point(50.0, 20.0)
|
||||
.point(50.0, 0.0)
|
||||
.point(-100.0, 0.0)
|
||||
.linestring(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-100.0, 20.0)
|
||||
.coordinate(50.0, 20.0)
|
||||
.coordinate(50.0, 0.0)
|
||||
.coordinate(-100.0, 0.0)
|
||||
)
|
||||
)
|
||||
.build();
|
||||
|
||||
// LineString that needs to be wrappped
|
||||
ShapeBuilders.newMultiLinestring()
|
||||
.linestring(new LineStringBuilder()
|
||||
.point(150.0, 60.0)
|
||||
.point(200.0, 60.0)
|
||||
.point(200.0, 40.0)
|
||||
.point(150.0, 40.0)
|
||||
.linestring(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(150.0, 60.0)
|
||||
.coordinate(200.0, 60.0)
|
||||
.coordinate(200.0, 40.0)
|
||||
.coordinate(150.0, 40.0)
|
||||
)
|
||||
)
|
||||
.linestring(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(150.0, 20.0)
|
||||
.coordinate(200.0, 20.0)
|
||||
.coordinate(200.0, 0.0)
|
||||
.coordinate(150.0, 0.0)
|
||||
)
|
||||
.linestring(new LineStringBuilder()
|
||||
.point(150.0, 20.0)
|
||||
.point(200.0, 20.0)
|
||||
.point(200.0, 0.0)
|
||||
.point(150.0, 0.0)
|
||||
)
|
||||
.build();
|
||||
}
|
||||
|
||||
public void testPolygonSelfIntersection() {
|
||||
try {
|
||||
ShapeBuilders.newPolygon()
|
||||
.point(-40.0, 50.0)
|
||||
.point(40.0, 50.0)
|
||||
.point(-40.0, -50.0)
|
||||
.point(40.0, -50.0)
|
||||
.close().build();
|
||||
ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-40.0, 50.0)
|
||||
.coordinate(40.0, 50.0)
|
||||
.coordinate(-40.0, -50.0)
|
||||
.coordinate(40.0, -50.0).close())
|
||||
.build();
|
||||
fail("Expected InvalidShapeException");
|
||||
} catch (InvalidShapeException e) {
|
||||
assertThat(e.getMessage(), containsString("Self-intersection at or near point (0.0"));
|
||||
|
@ -212,22 +222,26 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
}
|
||||
|
||||
public void testPolygonWrapping() {
|
||||
Shape shape = ShapeBuilders.newPolygon()
|
||||
.point(-150.0, 65.0)
|
||||
.point(-250.0, 65.0)
|
||||
.point(-250.0, -65.0)
|
||||
.point(-150.0, -65.0)
|
||||
.close().build();
|
||||
Shape shape = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-150.0, 65.0)
|
||||
.coordinate(-250.0, 65.0)
|
||||
.coordinate(-250.0, -65.0)
|
||||
.coordinate(-150.0, -65.0)
|
||||
.close()
|
||||
)
|
||||
.build();
|
||||
|
||||
assertMultiPolygon(shape);
|
||||
}
|
||||
|
||||
public void testLineStringWrapping() {
|
||||
Shape shape = ShapeBuilders.newLineString()
|
||||
.point(-150.0, 65.0)
|
||||
.point(-250.0, 65.0)
|
||||
.point(-250.0, -65.0)
|
||||
.point(-150.0, -65.0)
|
||||
Shape shape = ShapeBuilders.newLineString(new CoordinatesBuilder()
|
||||
.coordinate(-150.0, 65.0)
|
||||
.coordinate(-250.0, 65.0)
|
||||
.coordinate(-250.0, -65.0)
|
||||
.coordinate(-150.0, -65.0)
|
||||
.close()
|
||||
)
|
||||
.build();
|
||||
assertMultiLineString(shape);
|
||||
}
|
||||
|
@ -238,36 +252,39 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
// expected results: 3 polygons, 1 with a hole
|
||||
|
||||
// a giant c shape
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(174,0)
|
||||
.point(-176,0)
|
||||
.point(-176,3)
|
||||
.point(177,3)
|
||||
.point(177,5)
|
||||
.point(-176,5)
|
||||
.point(-176,8)
|
||||
.point(174,8)
|
||||
.point(174,0);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(174,0)
|
||||
.coordinate(-176,0)
|
||||
.coordinate(-176,3)
|
||||
.coordinate(177,3)
|
||||
.coordinate(177,5)
|
||||
.coordinate(-176,5)
|
||||
.coordinate(-176,8)
|
||||
.coordinate(174,8)
|
||||
.coordinate(174,0)
|
||||
);
|
||||
|
||||
// 3/4 of an embedded 'c', crossing dateline once
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(175, 1)
|
||||
.point(175, 7)
|
||||
.point(-178, 7)
|
||||
.point(-178, 6)
|
||||
.point(176, 6)
|
||||
.point(176, 2)
|
||||
.point(179, 2)
|
||||
.point(179,1)
|
||||
.point(175, 1));
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(175, 1)
|
||||
.coordinate(175, 7)
|
||||
.coordinate(-178, 7)
|
||||
.coordinate(-178, 6)
|
||||
.coordinate(176, 6)
|
||||
.coordinate(176, 2)
|
||||
.coordinate(179, 2)
|
||||
.coordinate(179,1)
|
||||
.coordinate(175, 1)
|
||||
));
|
||||
|
||||
// embedded hole right of the dateline
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-179, 1)
|
||||
.point(-179, 2)
|
||||
.point(-177, 2)
|
||||
.point(-177,1)
|
||||
.point(-179,1));
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-179, 1)
|
||||
.coordinate(-179, 2)
|
||||
.coordinate(-177, 2)
|
||||
.coordinate(-177,1)
|
||||
.coordinate(-179,1)
|
||||
));
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
assertMultiPolygon(shape);
|
||||
|
@ -279,141 +296,150 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
// expected results: 3 polygons, 1 with a hole
|
||||
|
||||
// a giant c shape
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(-186,0)
|
||||
.point(-176,0)
|
||||
.point(-176,3)
|
||||
.point(-183,3)
|
||||
.point(-183,5)
|
||||
.point(-176,5)
|
||||
.point(-176,8)
|
||||
.point(-186,8)
|
||||
.point(-186,0);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-186,0)
|
||||
.coordinate(-176,0)
|
||||
.coordinate(-176,3)
|
||||
.coordinate(-183,3)
|
||||
.coordinate(-183,5)
|
||||
.coordinate(-176,5)
|
||||
.coordinate(-176,8)
|
||||
.coordinate(-186,8)
|
||||
.coordinate(-186,0)
|
||||
);
|
||||
|
||||
// 3/4 of an embedded 'c', crossing dateline once
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-185,1)
|
||||
.point(-181,1)
|
||||
.point(-181,2)
|
||||
.point(-184,2)
|
||||
.point(-184,6)
|
||||
.point(-178,6)
|
||||
.point(-178,7)
|
||||
.point(-185,7)
|
||||
.point(-185,1));
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-185,1)
|
||||
.coordinate(-181,1)
|
||||
.coordinate(-181,2)
|
||||
.coordinate(-184,2)
|
||||
.coordinate(-184,6)
|
||||
.coordinate(-178,6)
|
||||
.coordinate(-178,7)
|
||||
.coordinate(-185,7)
|
||||
.coordinate(-185,1)
|
||||
));
|
||||
|
||||
// embedded hole right of the dateline
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-179,1)
|
||||
.point(-177,1)
|
||||
.point(-177,2)
|
||||
.point(-179,2)
|
||||
.point(-179,1));
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-179,1)
|
||||
.coordinate(-177,1)
|
||||
.coordinate(-177,2)
|
||||
.coordinate(-179,2)
|
||||
.coordinate(-179,1)
|
||||
));
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
assertMultiPolygon(shape);
|
||||
}
|
||||
|
||||
public void testComplexShapeWithHole() {
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(-85.0018514,37.1311314)
|
||||
.point(-85.0016645,37.1315293)
|
||||
.point(-85.0016246,37.1317069)
|
||||
.point(-85.0016526,37.1318183)
|
||||
.point(-85.0017119,37.1319196)
|
||||
.point(-85.0019371,37.1321182)
|
||||
.point(-85.0019972,37.1322115)
|
||||
.point(-85.0019942,37.1323234)
|
||||
.point(-85.0019543,37.1324336)
|
||||
.point(-85.001906,37.1324985)
|
||||
.point(-85.001834,37.1325497)
|
||||
.point(-85.0016965,37.1325907)
|
||||
.point(-85.0016011,37.1325873)
|
||||
.point(-85.0014816,37.1325353)
|
||||
.point(-85.0011755,37.1323509)
|
||||
.point(-85.000955,37.1322802)
|
||||
.point(-85.0006241,37.1322529)
|
||||
.point(-85.0000002,37.1322307)
|
||||
.point(-84.9994,37.1323001)
|
||||
.point(-84.999109,37.1322864)
|
||||
.point(-84.998934,37.1322415)
|
||||
.point(-84.9988639,37.1321888)
|
||||
.point(-84.9987841,37.1320944)
|
||||
.point(-84.9987208,37.131954)
|
||||
.point(-84.998736,37.1316611)
|
||||
.point(-84.9988091,37.131334)
|
||||
.point(-84.9989283,37.1311337)
|
||||
.point(-84.9991943,37.1309198)
|
||||
.point(-84.9993573,37.1308459)
|
||||
.point(-84.9995888,37.1307924)
|
||||
.point(-84.9998746,37.130806)
|
||||
.point(-85.0000002,37.1308358)
|
||||
.point(-85.0004984,37.1310658)
|
||||
.point(-85.0008008,37.1311625)
|
||||
.point(-85.0009461,37.1311684)
|
||||
.point(-85.0011373,37.1311515)
|
||||
.point(-85.0016455,37.1310491)
|
||||
.point(-85.0018514,37.1311314);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-85.0018514,37.1311314)
|
||||
.coordinate(-85.0016645,37.1315293)
|
||||
.coordinate(-85.0016246,37.1317069)
|
||||
.coordinate(-85.0016526,37.1318183)
|
||||
.coordinate(-85.0017119,37.1319196)
|
||||
.coordinate(-85.0019371,37.1321182)
|
||||
.coordinate(-85.0019972,37.1322115)
|
||||
.coordinate(-85.0019942,37.1323234)
|
||||
.coordinate(-85.0019543,37.1324336)
|
||||
.coordinate(-85.001906,37.1324985)
|
||||
.coordinate(-85.001834,37.1325497)
|
||||
.coordinate(-85.0016965,37.1325907)
|
||||
.coordinate(-85.0016011,37.1325873)
|
||||
.coordinate(-85.0014816,37.1325353)
|
||||
.coordinate(-85.0011755,37.1323509)
|
||||
.coordinate(-85.000955,37.1322802)
|
||||
.coordinate(-85.0006241,37.1322529)
|
||||
.coordinate(-85.0000002,37.1322307)
|
||||
.coordinate(-84.9994,37.1323001)
|
||||
.coordinate(-84.999109,37.1322864)
|
||||
.coordinate(-84.998934,37.1322415)
|
||||
.coordinate(-84.9988639,37.1321888)
|
||||
.coordinate(-84.9987841,37.1320944)
|
||||
.coordinate(-84.9987208,37.131954)
|
||||
.coordinate(-84.998736,37.1316611)
|
||||
.coordinate(-84.9988091,37.131334)
|
||||
.coordinate(-84.9989283,37.1311337)
|
||||
.coordinate(-84.9991943,37.1309198)
|
||||
.coordinate(-84.9993573,37.1308459)
|
||||
.coordinate(-84.9995888,37.1307924)
|
||||
.coordinate(-84.9998746,37.130806)
|
||||
.coordinate(-85.0000002,37.1308358)
|
||||
.coordinate(-85.0004984,37.1310658)
|
||||
.coordinate(-85.0008008,37.1311625)
|
||||
.coordinate(-85.0009461,37.1311684)
|
||||
.coordinate(-85.0011373,37.1311515)
|
||||
.coordinate(-85.0016455,37.1310491)
|
||||
.coordinate(-85.0018514,37.1311314)
|
||||
);
|
||||
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-85.0000002,37.1317672)
|
||||
.point(-85.0001983,37.1317538)
|
||||
.point(-85.0003378,37.1317582)
|
||||
.point(-85.0004697,37.131792)
|
||||
.point(-85.0008048,37.1319439)
|
||||
.point(-85.0009342,37.1319838)
|
||||
.point(-85.0010184,37.1319463)
|
||||
.point(-85.0010618,37.13184)
|
||||
.point(-85.0010057,37.1315102)
|
||||
.point(-85.000977,37.1314403)
|
||||
.point(-85.0009182,37.1313793)
|
||||
.point(-85.0005366,37.1312209)
|
||||
.point(-85.000224,37.1311466)
|
||||
.point(-85.000087,37.1311356)
|
||||
.point(-85.0000002,37.1311433)
|
||||
.point(-84.9995021,37.1312336)
|
||||
.point(-84.9993308,37.1312859)
|
||||
.point(-84.9992567,37.1313252)
|
||||
.point(-84.9991868,37.1314277)
|
||||
.point(-84.9991593,37.1315381)
|
||||
.point(-84.9991841,37.1316527)
|
||||
.point(-84.9992329,37.1317117)
|
||||
.point(-84.9993527,37.1317788)
|
||||
.point(-84.9994931,37.1318061)
|
||||
.point(-84.9996815,37.1317979)
|
||||
.point(-85.0000002,37.1317672));
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-85.0000002,37.1317672)
|
||||
.coordinate(-85.0001983,37.1317538)
|
||||
.coordinate(-85.0003378,37.1317582)
|
||||
.coordinate(-85.0004697,37.131792)
|
||||
.coordinate(-85.0008048,37.1319439)
|
||||
.coordinate(-85.0009342,37.1319838)
|
||||
.coordinate(-85.0010184,37.1319463)
|
||||
.coordinate(-85.0010618,37.13184)
|
||||
.coordinate(-85.0010057,37.1315102)
|
||||
.coordinate(-85.000977,37.1314403)
|
||||
.coordinate(-85.0009182,37.1313793)
|
||||
.coordinate(-85.0005366,37.1312209)
|
||||
.coordinate(-85.000224,37.1311466)
|
||||
.coordinate(-85.000087,37.1311356)
|
||||
.coordinate(-85.0000002,37.1311433)
|
||||
.coordinate(-84.9995021,37.1312336)
|
||||
.coordinate(-84.9993308,37.1312859)
|
||||
.coordinate(-84.9992567,37.1313252)
|
||||
.coordinate(-84.9991868,37.1314277)
|
||||
.coordinate(-84.9991593,37.1315381)
|
||||
.coordinate(-84.9991841,37.1316527)
|
||||
.coordinate(-84.9992329,37.1317117)
|
||||
.coordinate(-84.9993527,37.1317788)
|
||||
.coordinate(-84.9994931,37.1318061)
|
||||
.coordinate(-84.9996815,37.1317979)
|
||||
.coordinate(-85.0000002,37.1317672)
|
||||
)
|
||||
);
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
assertPolygon(shape);
|
||||
}
|
||||
|
||||
public void testShapeWithHoleAtEdgeEndPoints() {
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(-4, 2)
|
||||
.point(4, 2)
|
||||
.point(6, 0)
|
||||
.point(4, -2)
|
||||
.point(-4, -2)
|
||||
.point(-6, 0)
|
||||
.point(-4, 2);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-4, 2)
|
||||
.coordinate(4, 2)
|
||||
.coordinate(6, 0)
|
||||
.coordinate(4, -2)
|
||||
.coordinate(-4, -2)
|
||||
.coordinate(-6, 0)
|
||||
.coordinate(-4, 2)
|
||||
);
|
||||
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(4, 1)
|
||||
.point(4, -1)
|
||||
.point(-4, -1)
|
||||
.point(-4, 1)
|
||||
.point(4, 1));
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(4, 1)
|
||||
.coordinate(4, -1)
|
||||
.coordinate(-4, -1)
|
||||
.coordinate(-4, 1)
|
||||
.coordinate(4, 1)
|
||||
));
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
assertPolygon(shape);
|
||||
}
|
||||
|
||||
public void testShapeWithPointOnDateline() {
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(180, 0)
|
||||
.point(176, 4)
|
||||
.point(176, -4)
|
||||
.point(180, 0);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(180, 0)
|
||||
.coordinate(176, 4)
|
||||
.coordinate(176, -4)
|
||||
.coordinate(180, 0)
|
||||
);
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
assertPolygon(shape);
|
||||
|
@ -421,21 +447,23 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
|
||||
public void testShapeWithEdgeAlongDateline() {
|
||||
// test case 1: test the positive side of the dateline
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(180, 0)
|
||||
.point(176, 4)
|
||||
.point(180, -4)
|
||||
.point(180, 0);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(180, 0)
|
||||
.coordinate(176, 4)
|
||||
.coordinate(180, -4)
|
||||
.coordinate(180, 0)
|
||||
);
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
assertPolygon(shape);
|
||||
|
||||
// test case 2: test the negative side of the dateline
|
||||
builder = ShapeBuilders.newPolygon()
|
||||
.point(-176, 4)
|
||||
.point(-180, 0)
|
||||
.point(-180, -4)
|
||||
.point(-176, 4);
|
||||
builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-176, 4)
|
||||
.coordinate(-180, 0)
|
||||
.coordinate(-180, -4)
|
||||
.coordinate(-176, 4)
|
||||
);
|
||||
|
||||
shape = builder.close().build();
|
||||
assertPolygon(shape);
|
||||
|
@ -443,73 +471,85 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
|
||||
public void testShapeWithBoundaryHoles() {
|
||||
// test case 1: test the positive side of the dateline
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(-177, 10)
|
||||
.point(176, 15)
|
||||
.point(172, 0)
|
||||
.point(176, -15)
|
||||
.point(-177, -10)
|
||||
.point(-177, 10);
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(176, 10)
|
||||
.point(180, 5)
|
||||
.point(180, -5)
|
||||
.point(176, -10)
|
||||
.point(176, 10));
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-177, 10)
|
||||
.coordinate(176, 15)
|
||||
.coordinate(172, 0)
|
||||
.coordinate(176, -15)
|
||||
.coordinate(-177, -10)
|
||||
.coordinate(-177, 10)
|
||||
);
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(176, 10)
|
||||
.coordinate(180, 5)
|
||||
.coordinate(180, -5)
|
||||
.coordinate(176, -10)
|
||||
.coordinate(176, 10)
|
||||
));
|
||||
Shape shape = builder.close().build();
|
||||
assertMultiPolygon(shape);
|
||||
|
||||
// test case 2: test the negative side of the dateline
|
||||
builder = ShapeBuilders.newPolygon()
|
||||
.point(-176, 15)
|
||||
.point(179, 10)
|
||||
.point(179, -10)
|
||||
.point(-176, -15)
|
||||
.point(-172, 0);
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-176, 10)
|
||||
.point(-176, -10)
|
||||
.point(-180, -5)
|
||||
.point(-180, 5)
|
||||
.point(-176, 10));
|
||||
builder = ShapeBuilders.newPolygon(
|
||||
new CoordinatesBuilder()
|
||||
.coordinate(-176, 15)
|
||||
.coordinate(179, 10)
|
||||
.coordinate(179, -10)
|
||||
.coordinate(-176, -15)
|
||||
.coordinate(-172, 0)
|
||||
.close()
|
||||
);
|
||||
builder.hole(new LineStringBuilder(
|
||||
new CoordinatesBuilder()
|
||||
.coordinate(-176, 10)
|
||||
.coordinate(-176, -10)
|
||||
.coordinate(-180, -5)
|
||||
.coordinate(-180, 5)
|
||||
.coordinate(-176, 10)
|
||||
.close()
|
||||
));
|
||||
shape = builder.close().build();
|
||||
assertMultiPolygon(shape);
|
||||
}
|
||||
|
||||
public void testShapeWithTangentialHole() {
|
||||
// test a shape with one tangential (shared) vertex (should pass)
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(179, 10)
|
||||
.point(168, 15)
|
||||
.point(164, 0)
|
||||
.point(166, -15)
|
||||
.point(179, -10)
|
||||
.point(179, 10);
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-177, 10)
|
||||
.point(-178, -10)
|
||||
.point(-180, -5)
|
||||
.point(-180, 5)
|
||||
.point(-177, 10));
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(179, 10)
|
||||
.coordinate(168, 15)
|
||||
.coordinate(164, 0)
|
||||
.coordinate(166, -15)
|
||||
.coordinate(179, -10)
|
||||
.coordinate(179, 10)
|
||||
);
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-177, 10)
|
||||
.coordinate(-178, -10)
|
||||
.coordinate(-180, -5)
|
||||
.coordinate(-180, 5)
|
||||
.coordinate(-177, 10)
|
||||
));
|
||||
Shape shape = builder.close().build();
|
||||
assertMultiPolygon(shape);
|
||||
}
|
||||
|
||||
public void testShapeWithInvalidTangentialHole() {
|
||||
// test a shape with one invalid tangential (shared) vertex (should throw exception)
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(179, 10)
|
||||
.point(168, 15)
|
||||
.point(164, 0)
|
||||
.point(166, -15)
|
||||
.point(179, -10)
|
||||
.point(179, 10);
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(164, 0)
|
||||
.point(175, 10)
|
||||
.point(175, 5)
|
||||
.point(179, -10)
|
||||
.point(164, 0));
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(179, 10)
|
||||
.coordinate(168, 15)
|
||||
.coordinate(164, 0)
|
||||
.coordinate(166, -15)
|
||||
.coordinate(179, -10)
|
||||
.coordinate(179, 10)
|
||||
);
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(164, 0)
|
||||
.coordinate(175, 10)
|
||||
.coordinate(175, 5)
|
||||
.coordinate(179, -10)
|
||||
.coordinate(164, 0)
|
||||
));
|
||||
try {
|
||||
builder.close().build();
|
||||
fail("Expected InvalidShapeException");
|
||||
|
@ -520,43 +560,48 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
|
||||
public void testBoundaryShapeWithTangentialHole() {
|
||||
// test a shape with one tangential (shared) vertex for each hole (should pass)
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(-177, 10)
|
||||
.point(176, 15)
|
||||
.point(172, 0)
|
||||
.point(176, -15)
|
||||
.point(-177, -10)
|
||||
.point(-177, 10);
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-177, 10)
|
||||
.point(-178, -10)
|
||||
.point(-180, -5)
|
||||
.point(-180, 5)
|
||||
.point(-177, 10));
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(172, 0)
|
||||
.point(176, 10)
|
||||
.point(176, -5)
|
||||
.point(172, 0));
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-177, 10)
|
||||
.coordinate(176, 15)
|
||||
.coordinate(172, 0)
|
||||
.coordinate(176, -15)
|
||||
.coordinate(-177, -10)
|
||||
.coordinate(-177, 10)
|
||||
);
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-177, 10)
|
||||
.coordinate(-178, -10)
|
||||
.coordinate(-180, -5)
|
||||
.coordinate(-180, 5)
|
||||
.coordinate(-177, 10)
|
||||
));
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(172, 0)
|
||||
.coordinate(176, 10)
|
||||
.coordinate(176, -5)
|
||||
.coordinate(172, 0)
|
||||
));
|
||||
Shape shape = builder.close().build();
|
||||
assertMultiPolygon(shape);
|
||||
}
|
||||
|
||||
public void testBoundaryShapeWithInvalidTangentialHole() {
|
||||
// test shape with two tangential (shared) vertices (should throw exception)
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(-177, 10)
|
||||
.point(176, 15)
|
||||
.point(172, 0)
|
||||
.point(176, -15)
|
||||
.point(-177, -10)
|
||||
.point(-177, 10);
|
||||
builder.hole(new LineStringBuilder()
|
||||
.point(-177, 10)
|
||||
.point(172, 0)
|
||||
.point(180, -5)
|
||||
.point(176, -10)
|
||||
.point(-177, 10));
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-177, 10)
|
||||
.coordinate(176, 15)
|
||||
.coordinate(172, 0)
|
||||
.coordinate(176, -15)
|
||||
.coordinate(-177, -10)
|
||||
.coordinate(-177, 10)
|
||||
);
|
||||
builder.hole(new LineStringBuilder(new CoordinatesBuilder()
|
||||
.coordinate(-177, 10)
|
||||
.coordinate(172, 0)
|
||||
.coordinate(180, -5)
|
||||
.coordinate(176, -10)
|
||||
.coordinate(-177, 10)
|
||||
));
|
||||
try {
|
||||
builder.close().build();
|
||||
fail("Expected InvalidShapeException");
|
||||
|
@ -569,11 +614,12 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
* Test an enveloping polygon around the max mercator bounds
|
||||
*/
|
||||
public void testBoundaryShape() {
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(-180, 90)
|
||||
.point(180, 90)
|
||||
.point(180, -90)
|
||||
.point(-180, -90);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(-180, 90)
|
||||
.coordinate(180, 90)
|
||||
.coordinate(180, -90)
|
||||
.coordinate(-180, 90)
|
||||
);
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
|
||||
|
@ -582,21 +628,23 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
|
||||
public void testShapeWithAlternateOrientation() {
|
||||
// cw: should produce a multi polygon spanning hemispheres
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(180, 0)
|
||||
.point(176, 4)
|
||||
.point(-176, 4)
|
||||
.point(180, 0);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(180, 0)
|
||||
.coordinate(176, 4)
|
||||
.coordinate(-176, 4)
|
||||
.coordinate(180, 0)
|
||||
);
|
||||
|
||||
Shape shape = builder.close().build();
|
||||
assertPolygon(shape);
|
||||
|
||||
// cw: geo core will convert to ccw across the dateline
|
||||
builder = ShapeBuilders.newPolygon()
|
||||
.point(180, 0)
|
||||
.point(-176, 4)
|
||||
.point(176, 4)
|
||||
.point(180, 0);
|
||||
builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(180, 0)
|
||||
.coordinate(-176, 4)
|
||||
.coordinate(176, 4)
|
||||
.coordinate(180, 0)
|
||||
);
|
||||
|
||||
shape = builder.close().build();
|
||||
|
||||
|
@ -604,12 +652,13 @@ public class ShapeBuilderTests extends ESTestCase {
|
|||
}
|
||||
|
||||
public void testInvalidShapeWithConsecutiveDuplicatePoints() {
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon()
|
||||
.point(180, 0)
|
||||
.point(176, 4)
|
||||
.point(176, 4)
|
||||
.point(-176, 4)
|
||||
.point(180, 0);
|
||||
PolygonBuilder builder = ShapeBuilders.newPolygon(new CoordinatesBuilder()
|
||||
.coordinate(180, 0)
|
||||
.coordinate(176, 4)
|
||||
.coordinate(176, 4)
|
||||
.coordinate(-176, 4)
|
||||
.coordinate(180, 0)
|
||||
);
|
||||
try {
|
||||
builder.close().build();
|
||||
fail("Expected InvalidShapeException");
|
||||
|
|
|
@ -40,7 +40,7 @@ import static org.hamcrest.Matchers.not;
|
|||
|
||||
public abstract class AbstractShapeBuilderTestCase<SB extends ShapeBuilder> extends ESTestCase {
|
||||
|
||||
private static final int NUMBER_OF_TESTBUILDERS = 20;
|
||||
private static final int NUMBER_OF_TESTBUILDERS = 100;
|
||||
private static NamedWriteableRegistry namedWriteableRegistry;
|
||||
|
||||
/**
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue