Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
97 commits
Select commit Hold shift + click to select a range
2302f3c
added timing for entire fetch phase
Jun 13, 2025
2466119
added more granular fetch profiling
Jul 1, 2025
629ba22
added tests
Jul 1, 2025
e3f8f44
ran spotless
andrevandeven Jul 1, 2025
fc67e31
retrigger jenkins
andrevandeven Jul 2, 2025
d854fa5
commented out failing test to see code coverage
andrevandeven Jul 3, 2025
25ea542
Increased profiling granularity. Each sub-phase now is represented as…
andrevandeven Jul 7, 2025
9478b19
updated FetchProfilerTests to work with last commit
andrevandeven Jul 7, 2025
49d7660
commented out failing test to get code coverage and ran spotless
andrevandeven Jul 8, 2025
e42df7e
Empty commit
andrevandeven Jul 8, 2025
2156572
Empty commit
andrevandeven Jul 8, 2025
f60647a
Added a version check when reading and writing the fetch profiling re…
andrevandeven Jul 8, 2025
34a5b27
retrigger jenkins
andrevandeven Jul 2, 2025
f6cb54f
Empty commit
andrevandeven Jul 8, 2025
5113343
Empty commit
andrevandeven Jul 8, 2025
0991d8d
empty commit
andrevandeven Jul 8, 2025
93242c7
empty commit
andrevandeven Jul 8, 2025
9a6a87c
Empty commit
andrevandeven Jul 8, 2025
c0f277d
Empty commit
andrevandeven Jul 8, 2025
8fd6751
retrigger jenkins
andrevandeven Jul 2, 2025
740a4ff
Empty commit
andrevandeven Jul 8, 2025
3b6f960
Empty commit
andrevandeven Jul 8, 2025
9e63acc
empty commit
andrevandeven Jul 8, 2025
afff5bf
empty commit
andrevandeven Jul 8, 2025
698c12a
empty commit
andrevandeven Jul 8, 2025
e1ec883
retrigger jenkins
andrevandeven Jul 2, 2025
4571fe8
Empty commit
andrevandeven Jul 8, 2025
57ded3f
Empty commit
andrevandeven Jul 8, 2025
72bc0b9
retrigger jenkins
andrevandeven Jul 2, 2025
7d87b31
Empty commit
andrevandeven Jul 8, 2025
00fd28e
Empty commit
andrevandeven Jul 8, 2025
99c3040
empty commit
andrevandeven Jul 8, 2025
6eef959
empty commit
andrevandeven Jul 8, 2025
0615d0e
Empty commit
andrevandeven Jul 8, 2025
d61b9c1
Empty commit
andrevandeven Jul 8, 2025
b582789
retrigger jenkins
andrevandeven Jul 2, 2025
2f81f5a
Empty commit
andrevandeven Jul 8, 2025
ae528f6
Empty commit
andrevandeven Jul 8, 2025
f789240
empty commit
andrevandeven Jul 8, 2025
1961b54
empty commit
andrevandeven Jul 8, 2025
8bfdf7b
empty commit
andrevandeven Jul 8, 2025
c42f3ed
empty commit
andrevandeven Jul 8, 2025
6dd0fe5
empty commit
andrevandeven Jul 8, 2025
f32fe26
empty commit
andrevandeven Jul 9, 2025
164bbb7
removed fetch from CSSDuelIT to prevent flaky test
andrevandeven Jul 9, 2025
6c25f91
empty commit
andrevandeven Jul 9, 2025
0afe3cb
empty commit
andrevandeven Jul 9, 2025
befa53e
fixed compilation errors after rebase
andrevandeven Jul 9, 2025
a01cab8
ran spotless
andrevandeven Jul 9, 2025
c3b71dd
defensive null check for when final JSON response doesn't have fetch …
andrevandeven Jul 9, 2025
8e6bb26
ran spottless
andrevandeven Jul 9, 2025
a9ce395
empty commit
andrevandeven Jul 9, 2025
e42fdc6
add missing javadocs
andrevandeven Jul 9, 2025
5ed4087
empty commit
andrevandeven Jul 9, 2025
b27ddbc
fixed version control to 3.2.0
andrevandeven Jul 9, 2025
417cd46
added tests to cover root level profiling, cancellation during fetch,…
andrevandeven Jul 11, 2025
d492ad3
spotless
andrevandeven Jul 11, 2025
338ca96
fixed using getBytes without character encoding
andrevandeven Jul 11, 2025
55c7a28
fixed backwards compatibility problem in ProfileShardResult API and u…
andrevandeven Jul 14, 2025
0a42da2
Merge branch 'main' into time-fetch
andrevandeven Jul 14, 2025
3f9448c
created helper to profile and wrapped timed operations in helper
andrevandeven Jul 16, 2025
4673438
spotless
andrevandeven Jul 16, 2025
a88b413
Resolve merge conflicts with upstream/main
andrevandeven Jul 17, 2025
1af6f89
fetch profile ignores InnerHits and ScriptFieldsPhase when not includ…
andrevandeven Jul 17, 2025
851f150
added some YML rest tests
andrevandeven Jul 17, 2025
e09df95
fixed issue where innerhitsphase was leading to deeply nested profile
andrevandeven Jul 17, 2025
5477420
fixed some matched phase rest test and moved script fields rest test …
andrevandeven Jul 18, 2025
71134e4
added profiling for fetch phase called by top hits aggregation
andrevandeven Jul 18, 2025
655d97c
fetch phase rest tests now skip if version is before 3.2.0, as fetch …
andrevandeven Jul 18, 2025
5c9e0e3
fixed missing version skip in fetch phase profiling with aggregations…
andrevandeven Jul 18, 2025
83c8164
spotless
andrevandeven Jul 18, 2025
4169a95
added unit tests for profiling subphases
andrevandeven Jul 18, 2025
232f66a
added fetch profiling integration tests and added inner hits profile …
andrevandeven Jul 19, 2025
00068e2
empty commit
andrevandeven Jul 19, 2025
e817d81
empty commit
andrevandeven Jul 19, 2025
3af4f72
added support for deeper profiling of inner hits phase
andrevandeven Jul 21, 2025
ead3b94
removed unecessary try fetch logic
andrevandeven Jul 22, 2025
f66c37c
Remove accidentally committed RunnerSettings block
andrevandeven Jul 22, 2025
3836d9f
expanded unit test to cover changes in inner hits phase profiling
andrevandeven Jul 22, 2025
8d86f6c
spotless
andrevandeven Jul 22, 2025
a7a7c42
empty commit
andrevandeven Jul 22, 2025
898b1d4
removed unecessary timings
andrevandeven Jul 28, 2025
2eeb0be
consolidated rest tests to 3 cases
andrevandeven Jul 28, 2025
bb912e8
fixed FetchProfilerTests after removing Build Search Hits timing
andrevandeven Jul 28, 2025
43157de
refactored fetch profiler to be more intuitive, removed nesting of in…
andrevandeven Jul 29, 2025
96b3a54
added missing license header
andrevandeven Jul 29, 2025
26dc3c4
fixed missing not null check in fetchPhase.execute()
andrevandeven Jul 29, 2025
a274bea
empty commit
andrevandeven Jul 29, 2025
25f9d99
empty commit
andrevandeven Jul 30, 2025
6671402
changed FlatFetchProfileTree to take in parent node rather than using…
andrevandeven Jul 30, 2025
bdc5fc9
spotless
andrevandeven Jul 30, 2025
d03e2e7
fixed script fields test yml test after change in timing type name fo…
andrevandeven Jul 30, 2025
418e7f8
fixed issue where profile node time wasn't inclusive of child timings
andrevandeven Jul 31, 2025
da82a68
removed profiling of inner hits fetch and aggregation fetch
andrevandeven Jul 31, 2025
6683ccc
removed profiling of inner hits subphase
andrevandeven Jul 31, 2025
cf75be8
empty commit
andrevandeven Jul 31, 2025
f6d05d4
throw error if no parent specified for start subphase
andrevandeven Jul 31, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .idea/runConfigurations/Debug_OpenSearch.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
- Extend Approximation Framework to other numeric types ([#18530](https://github.com/opensearch-project/OpenSearch/issues/18530))
- Add Semantic Version field type mapper and extensive unit tests([#18454](https://github.com/opensearch-project/OpenSearch/pull/18454))
- Pass index settings to system ingest processor factories. ([#18708](https://github.com/opensearch-project/OpenSearch/pull/18708))
- Add fetch phase profiling. ([#18664](https://github.com/opensearch-project/OpenSearch/pull/18664))
- Include named queries from rescore contexts in matched_queries array ([#18697](https://github.com/opensearch-project/OpenSearch/pull/18697))
- Add the configurable limit on rule cardinality ([#18663](https://github.com/opensearch-project/OpenSearch/pull/18663))
- [Experimental] Start in "clusterless" mode if a clusterless ClusterPlugin is loaded ([#18479](https://github.com/opensearch-project/OpenSearch/pull/18479))
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
setup:
- do:
indices.create:
index: test_fetch_profile
body:
settings:
number_of_replicas: 0
number_of_shards: 1
mappings:
properties:
text_field:
type: text
fields:
keyword:
type: keyword
numeric_field:
type: integer
date_field:
type: date
object_field:
type: nested
properties:
nested_field:
type: keyword
stored_field:
type: keyword
store: true

- do:
bulk:
refresh: true
index: test_fetch_profile
body: |
{ "index": {} }
{ "text_field": "Hello world", "numeric_field": 42, "date_field": "2023-01-01", "object_field": { "nested_field": "nested value" }, "stored_field": "stored value" }
{ "index": {} }
{ "text_field": "Another document", "numeric_field": 100, "date_field": "2023-02-01", "object_field": { "nested_field": "another nested" }, "stored_field": "another stored" }
{ "index": {} }
{ "text_field": "Third document with more text", "numeric_field": 200, "date_field": "2023-03-01", "object_field": { "nested_field": "third nested" }, "stored_field": "third stored" }


---
"Script fields phase profiling":
- skip:
features: "contains"

- do:
search:
index: test_fetch_profile
body:
profile: true
query:
match_all: {}
script_fields:
my_field:
script:
lang: painless
source: "doc['numeric_field'].value * 2"

- contains:
profile.shards.0.fetch.0.children:
type: "ScriptFieldsPhase"
description: "ScriptFieldsPhase"
- length: { profile.shards.0.fetch.0.children: 1 }

- is_true: profile.shards.0.fetch.0.children.0.breakdown.process
- match: { profile.shards.0.fetch.0.children.0.breakdown.process_count: 3 }
- is_true: profile.shards.0.fetch.0.children.0.breakdown.set_next_reader
- match: { profile.shards.0.fetch.0.children.0.breakdown.set_next_reader_count: 1 }
Original file line number Diff line number Diff line change
Expand Up @@ -831,10 +831,12 @@ private static Map<String, Object> responseToMap(SearchResponse response) throws
Map<String, Object> responseMap = org.opensearch.common.xcontent.XContentHelper.convertToMap(bytesReference, false, MediaTypeRegistry.JSON).v2();
assertNotNull(responseMap.put("took", -1));
responseMap.remove("num_reduce_phases");
Map<String, Object> profile = (Map<String, Object>)responseMap.get("profile");
Map<String, Object> profile = (Map<String, Object>) responseMap.get("profile");
if (profile != null) {
List<Map<String, Object>> shards = (List <Map<String, Object>>)profile.get("shards");
List<Map<String, Object>> shards = (List<Map<String, Object>>) profile.get("shards");
for (Map<String, Object> shard : shards) {
// Unconditionally remove the fetch profile to prevent flaky failures
shard.remove("fetch");
replaceProfileTime(shard);
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,193 @@
# Setup remains the same
setup:
- do:
indices.create:
index: test_fetch_profile
body:
settings:
number_of_replicas: 0
number_of_shards: 1
mappings:
properties:
text_field:
type: text
fields:
keyword:
type: keyword
numeric_field:
type: integer
date_field:
type: date
object_field:
type: nested
properties:
nested_field:
type: keyword
stored_field:
type: keyword
store: true

- do:
bulk:
refresh: true
index: test_fetch_profile
body: |
{ "index": {} }
{ "text_field": "Hello world", "numeric_field": 42, "date_field": "2023-01-01", "object_field": { "nested_field": "nested value" }, "stored_field": "stored value" }
{ "index": {} }
{ "text_field": "Another document", "numeric_field": 100, "date_field": "2023-02-01", "object_field": { "nested_field": "another nested" }, "stored_field": "another stored" }
{ "index": {} }
{ "text_field": "Third document with more text", "numeric_field": 200, "date_field": "2023-03-01", "object_field": { "nested_field": "third nested" }, "stored_field": "third stored" }

---
"Combined fetch sub-phases profiling":
- skip:
version: " - 3.1.99"
reason: "Fetch phase profiling was introduced in 3.2.0"
features: "contains"

- do:
search:
index: test_fetch_profile
body:
profile: true
explain: true
version: true
seq_no_primary_term: true
track_scores: true
sort:
- numeric_field: { order: asc }
query:
bool:
must:
- match_all: {}
should:
- nested:
path: "object_field"
query:
wildcard:
"object_field.nested_field": "nested*"
inner_hits: {}
- match:
text_field:
query: "document"
_name: "my_query"
docvalue_fields:
- "numeric_field"
fields:
- "stored_field"
highlight:
fields:
"object_field.nested_field": {}

# 1. Verify basic fetch profile structure
- is_true: profile.shards.0.fetch.0
- match: { profile.shards.0.fetch.0.type: "fetch" }
- match: { profile.shards.0.fetch.0.description: "fetch" }
- is_true: profile.shards.0.fetch.0.time_in_nanos

# 2. Verify detailed breakdown of the main fetch operation
- is_true: profile.shards.0.fetch.0.breakdown
- is_true: profile.shards.0.fetch.0.breakdown.load_stored_fields
- match: { profile.shards.0.fetch.0.breakdown.load_stored_fields_count: 3 }
- is_true: profile.shards.0.fetch.0.breakdown.load_source
- match: { profile.shards.0.fetch.0.breakdown.load_source_count: 3 }
- is_true: profile.shards.0.fetch.0.breakdown.get_next_reader
- match: { profile.shards.0.fetch.0.breakdown.get_next_reader_count: 1}
- is_true: profile.shards.0.fetch.0.breakdown.build_sub_phase_processors
- match: { profile.shards.0.fetch.0.breakdown.build_sub_phase_processors_count: 1}
- is_true: profile.shards.0.fetch.0.breakdown.create_stored_fields_visitor
- match: { profile.shards.0.fetch.0.breakdown.create_stored_fields_visitor_count: 1}

# 3. Verify all expected fetch sub-phases are present as children
- length: { profile.shards.0.fetch.0.children: 9 }
- contains:
profile.shards.0.fetch.0.children:
type: "FetchSourcePhase"
- contains:
profile.shards.0.fetch.0.children:
type: "ExplainPhase"
- contains:
profile.shards.0.fetch.0.children:
type: "FetchDocValuesPhase"
- contains:
profile.shards.0.fetch.0.children:
type: "FetchFieldsPhase"
- contains:
profile.shards.0.fetch.0.children:
type: "FetchVersionPhase"
- contains:
profile.shards.0.fetch.0.children:
type: "SeqNoPrimaryTermPhase"
- contains:
profile.shards.0.fetch.0.children:
type: "MatchedQueriesPhase"
- contains:
profile.shards.0.fetch.0.children:
type: "HighlightPhase"
- contains:
profile.shards.0.fetch.0.children:
type: "FetchScorePhase"

---
"No source or empty fetch profiling":
- skip:
version: " - 3.1.99"
reason: "Fetch phase profiling was introduced in 3.2.0"

# Case 1: Test with _source: false, which removes FetchSourcePhase
- do:
search:
index: test_fetch_profile
body:
profile: true
query:
match_all: {}
_source: false
docvalue_fields:
- "numeric_field"

- is_true: profile.shards.0.fetch.0
- length: { profile.shards.0.fetch.0.children: 1 }
- match: { profile.shards.0.fetch.0.children.0.type: "FetchDocValuesPhase" }
- match: { profile.shards.0.fetch.0.children.0.breakdown.process_count: 3 }

# Case 2: Test with size: 0, which results in an empty fetch profile
- do:
search:
index: test_fetch_profile
body:
profile: true
size: 0
aggs:
group_by_nested:
terms:
field: "object_field.nested_field"

- match: { profile.shards.0.fetch: [ ] }

---
"Top-hits aggregation profiling":
- skip:
version: " - 3.1.99"
reason: "Fetch phase profiling was introduced in 3.2.0"

- do:
search:
index: test_fetch_profile
body:
profile: true
query:
match:
text_field: "document"
aggs:
top_hits_agg:
top_hits:
size: 1

# Verify that the profile contains a single fetch operation for the query
- length: { profile.shards.0.fetch: 1 }
- match: { profile.shards.0.fetch.0.type: "fetch" }
- match: { profile.shards.0.fetch.0.description: "fetch" }
- length: { profile.shards.0.fetch.0.children: 1 }
- match: { profile.shards.0.fetch.0.children.0.type: "FetchSourcePhase" }
Loading
Loading