@Override
    public void fill(Result result, String summaryClass, Execution execution) {
        UniqueExecutionsToResults uniqueExecutionsToResults = new UniqueExecutionsToResults();
        addResultsToFill(result.hits(), result, summaryClass, uniqueExecutionsToResults);
        var resultsForAllChains = uniqueExecutionsToResults.resultsToFill.entrySet();
        int numberOfCallsToFillNeeded = 0;

        for (Entry<Chain<Searcher>, Map<Query, Result>> resultsToFillForAChain : resultsForAllChains) {
            numberOfCallsToFillNeeded += resultsToFillForAChain.getValue().size();
        }

        List<Pair<Result, FutureResult>> futureFilledResults = new ArrayList<>();
        for (Entry<Chain<Searcher>, Map<Query, Result>> resultsToFillForAChain : resultsForAllChains) {
            Chain<Searcher> chain = resultsToFillForAChain.getKey();
            Execution chainExecution = (chain == null) ? execution : new Execution(chain, execution.context());

            for (Entry<Query, Result> resultsToFillForAChainAndQuery : resultsToFillForAChain.getValue().entrySet()) {
                Result resultToFill = resultsToFillForAChainAndQuery.getValue();
                if (numberOfCallsToFillNeeded == 1) {
                    chainExecution.fill(resultToFill, summaryClass);
                    propagateErrors(resultToFill, result);
                } else {
                    AsyncExecution asyncFill = new AsyncExecution(chainExecution);
                    futureFilledResults.add(new Pair<>(resultToFill, asyncFill.fill(resultToFill, summaryClass)));
                }
            }
        }
        for (Pair<Result, FutureResult> futureFilledResult : futureFilledResults) {
            // futureFilledResult is a pair of a result to be filled and the future in which that same result is filled
            Optional<Result> filledResult = futureFilledResult.getSecond().getIfAvailable(result.getQuery().getTimeLeft(), TimeUnit.MILLISECONDS);
            if (filledResult.isPresent()) { // fill completed
                propagateErrors(filledResult.get(), result);
            }
            else { // fill timed out: Remove these hits as they are incomplete and may cause a race when accessed later
                result.hits().addError(futureFilledResult.getSecond().createTimeoutError());
                for (Iterator<Hit> i = futureFilledResult.getFirst().hits().unorderedDeepIterator(); i.hasNext(); ) {
                    // Note that some of these hits may be filled, but as the fill thread may still be working on them,
                    // and we do not synchronize with it, we need to discard all.
                    result.hits().remove(i.next().getId());
                }
            }
        }
    }
The name of the query property containing the source name added to the query to each source by this
container-search/src/main/java/com/yahoo/search/federation/FederationSearcher.java