From 09ebcf0dac6e38cde0ac5cda18fcca230d2787d3 Mon Sep 17 00:00:00 2001 From: Armin Braun Date: Sat, 22 Feb 2025 19:57:19 +0100 Subject: [PATCH] Speedup SearchResponse serialization No need to have a nested concat here. There's obviously lots and lots of room for optimization on this one, but just flattening out one obvious step here outright halves the number of method calls required when serializing a search response. Given that method calls can consume up to half the serialization cost this change might massively speed up some usecases. --- .../action/search/SearchResponse.java | 22 +++++++++---------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/server/src/main/java/org/elasticsearch/action/search/SearchResponse.java b/server/src/main/java/org/elasticsearch/action/search/SearchResponse.java index 787dc14f6cd96..2a9acd465f727 100644 --- a/server/src/main/java/org/elasticsearch/action/search/SearchResponse.java +++ b/server/src/main/java/org/elasticsearch/action/search/SearchResponse.java @@ -382,23 +382,23 @@ public Clusters getClusters() { @Override public Iterator toXContentChunked(ToXContent.Params params) { assert hasReferences(); - return Iterators.concat( - ChunkedToXContentHelper.startObject(), - this.innerToXContentChunked(params), - ChunkedToXContentHelper.endObject() - ); + return getToXContentIterator(true, params); } public Iterator innerToXContentChunked(ToXContent.Params params) { + return getToXContentIterator(false, params); + } + + private Iterator getToXContentIterator(boolean wrapInObject, ToXContent.Params params) { return Iterators.concat( + wrapInObject ? ChunkedToXContentHelper.startObject() : Collections.emptyIterator(), ChunkedToXContentHelper.chunk(SearchResponse.this::headerToXContent), Iterators.single(clusters), - Iterators.concat( - hits.toXContentChunked(params), - aggregations == null ? Collections.emptyIterator() : ChunkedToXContentHelper.chunk(aggregations), - suggest == null ? Collections.emptyIterator() : ChunkedToXContentHelper.chunk(suggest), - profileResults == null ? Collections.emptyIterator() : ChunkedToXContentHelper.chunk(profileResults) - ) + hits.toXContentChunked(params), + aggregations == null ? Collections.emptyIterator() : ChunkedToXContentHelper.chunk(aggregations), + suggest == null ? Collections.emptyIterator() : ChunkedToXContentHelper.chunk(suggest), + profileResults == null ? Collections.emptyIterator() : ChunkedToXContentHelper.chunk(profileResults), + wrapInObject ? ChunkedToXContentHelper.endObject() : Collections.emptyIterator() ); }