throw new QueryPhaseExecutionException(searchContext, "Failed to refresh id cache for child queries", e);
}
// process scoped queries (from the last to the first, working with the parsing option here)
for (int i = searchContext.scopePhases().size() - 1; i >= 0; i--) {
ScopePhase scopePhase = searchContext.scopePhases().get(i);
if (scopePhase instanceof ScopePhase.TopDocsPhase) {
ScopePhase.TopDocsPhase topDocsPhase = (ScopePhase.TopDocsPhase) scopePhase;
topDocsPhase.clear();
int numDocs = (searchContext.from() + searchContext.size());
if (numDocs == 0) {
numDocs = 1;
}
try {
numDocs *= topDocsPhase.factor();
while (true) {
if (topDocsPhase.scope() != null) {
searchContext.searcher().processingScope(topDocsPhase.scope());
}
TopDocs topDocs = searchContext.searcher().search(topDocsPhase.query(), numDocs);
if (topDocsPhase.scope() != null) {
// we mark the scope as processed, so we don't process it again, even if we need to rerun the query...
searchContext.searcher().processedScope();
}
topDocsPhase.processResults(topDocs, searchContext);
// check if we found enough docs, if so, break
if (topDocsPhase.numHits() >= (searchContext.from() + searchContext.size())) {
break;
}
// if we did not find enough docs, check if it make sense to search further
if (topDocs.totalHits <= numDocs) {
break;
}
// if not, update numDocs, and search again
numDocs *= topDocsPhase.incrementalFactor();
if (numDocs > topDocs.totalHits) {
numDocs = topDocs.totalHits;
}
}
} catch (Exception e) {
throw new QueryPhaseExecutionException(searchContext, "Failed to execute child query [" + scopePhase.query() + "]", e);
}
} else if (scopePhase instanceof ScopePhase.CollectorPhase) {
try {
ScopePhase.CollectorPhase collectorPhase = (ScopePhase.CollectorPhase) scopePhase;
// collector phase might not require extra processing, for example, when scrolling
if (!collectorPhase.requiresProcessing()) {
continue;
}
if (scopePhase.scope() != null) {
searchContext.searcher().processingScope(scopePhase.scope());
}
Collector collector = collectorPhase.collector();
searchContext.searcher().search(collectorPhase.query(), collector);
collectorPhase.processCollector(collector);
if (collectorPhase.scope() != null) {
// we mark the scope as processed, so we don't process it again, even if we need to rerun the query...
searchContext.searcher().processedScope();
}
} catch (Exception e) {
throw new QueryPhaseExecutionException(searchContext, "Failed to execute child query [" + scopePhase.query() + "]", e);
}
}
}
}