-
Notifications
You must be signed in to change notification settings - Fork 24.3k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Encapsulate source filtering (#91127)
We have two implementations of source filtering, one based on Map filtering and used by SourceLookup, and one based on jackson stream filtering used in Get and SourceFieldMapper. There are cases when stream filtering could be usefully applied to source in the fetch phase, for example if the source is not being used as a Map by any other subphase; and correspondingly if a source has already been parsed to a Map then map filtering will generally be more efficient than stream filtering that ends up re-parsing the bytes. This commit encapsulates all of this filtering logic into a single SourceFilter class, which can be passed to the filter method on Source. Different Source implementations can choose to use map or stream filtering depending on whether or not they have map or bytes representations available.
- Loading branch information
1 parent
90ad248
commit ba7a219
Showing
18 changed files
with
450 additions
and
224 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
94 changes: 94 additions & 0 deletions
94
...main/java/org/elasticsearch/benchmark/search/fetch/subphase/SourceFilteringBenchmark.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,94 @@ | ||
/* | ||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one | ||
* or more contributor license agreements. Licensed under the Elastic License | ||
* 2.0 and the Server Side Public License, v 1; you may not use this file except | ||
* in compliance with, at your election, the Elastic License 2.0 or the Server | ||
* Side Public License, v 1. | ||
*/ | ||
|
||
package org.elasticsearch.benchmark.search.fetch.subphase; | ||
|
||
import org.elasticsearch.common.Strings; | ||
import org.elasticsearch.common.bytes.BytesArray; | ||
import org.elasticsearch.common.bytes.BytesReference; | ||
import org.elasticsearch.common.io.Streams; | ||
import org.elasticsearch.search.fetch.subphase.FetchSourceContext; | ||
import org.elasticsearch.search.lookup.Source; | ||
import org.elasticsearch.search.lookup.SourceFilter; | ||
import org.openjdk.jmh.annotations.Benchmark; | ||
import org.openjdk.jmh.annotations.BenchmarkMode; | ||
import org.openjdk.jmh.annotations.Fork; | ||
import org.openjdk.jmh.annotations.Measurement; | ||
import org.openjdk.jmh.annotations.Mode; | ||
import org.openjdk.jmh.annotations.OutputTimeUnit; | ||
import org.openjdk.jmh.annotations.Param; | ||
import org.openjdk.jmh.annotations.Scope; | ||
import org.openjdk.jmh.annotations.Setup; | ||
import org.openjdk.jmh.annotations.State; | ||
import org.openjdk.jmh.annotations.Warmup; | ||
|
||
import java.io.IOException; | ||
import java.util.concurrent.TimeUnit; | ||
|
||
@Fork(1) | ||
@Warmup(iterations = 5) | ||
@Measurement(iterations = 5) | ||
@BenchmarkMode(Mode.AverageTime) | ||
@OutputTimeUnit(TimeUnit.NANOSECONDS) | ||
@State(Scope.Benchmark) | ||
public class SourceFilteringBenchmark { | ||
|
||
private BytesReference sourceBytes; | ||
private SourceFilter filter; | ||
|
||
@Param({ "tiny", "short", "one_4k_field", "one_4m_field" }) | ||
private String source; | ||
@Param({ "message" }) | ||
private String includes; | ||
@Param({ "" }) | ||
private String excludes; | ||
|
||
@Setup | ||
public void setup() throws IOException { | ||
sourceBytes = switch (source) { | ||
case "tiny" -> new BytesArray("{\"message\": \"short\"}"); | ||
case "short" -> read300BytesExample(); | ||
case "one_4k_field" -> buildBigExample("huge".repeat(1024)); | ||
case "one_4m_field" -> buildBigExample("huge".repeat(1024 * 1024)); | ||
default -> throw new IllegalArgumentException("Unknown source [" + source + "]"); | ||
}; | ||
FetchSourceContext fetchContext = FetchSourceContext.of( | ||
true, | ||
Strings.splitStringByCommaToArray(includes), | ||
Strings.splitStringByCommaToArray(excludes) | ||
); | ||
filter = fetchContext.filter(); | ||
} | ||
|
||
private BytesReference read300BytesExample() throws IOException { | ||
return Streams.readFully(FetchSourcePhaseBenchmark.class.getResourceAsStream("300b_example.json")); | ||
} | ||
|
||
private BytesReference buildBigExample(String extraText) throws IOException { | ||
String bigger = read300BytesExample().utf8ToString(); | ||
bigger = "{\"huge\": \"" + extraText + "\"," + bigger.substring(1); | ||
return new BytesArray(bigger); | ||
} | ||
|
||
// We want to compare map filtering with bytes filtering when the map has already | ||
// been parsed. | ||
|
||
@Benchmark | ||
public Source filterMap() { | ||
Source source = Source.fromBytes(sourceBytes); | ||
source.source(); // build map | ||
return filter.filterMap(source); | ||
} | ||
|
||
@Benchmark | ||
public Source filterBytes() { | ||
Source source = Source.fromBytes(sourceBytes); | ||
source.source(); // build map | ||
return filter.filterBytes(source); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
101 changes: 0 additions & 101 deletions
101
server/src/main/java/org/elasticsearch/common/xcontent/XContentFieldFilter.java
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.