|  | @@ -48,6 +48,7 @@ import org.elasticsearch.index.cache.bitset.BitsetFilterCache;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.cache.bitset.BitsetFilterCache.Listener;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.cache.query.DisabledQueryCache;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.engine.Engine;
 | 
	
		
			
				|  |  | +import org.elasticsearch.index.fielddata.IndexFieldData;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.fielddata.IndexFieldDataCache;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.fielddata.IndexFieldDataService;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.mapper.ContentPath;
 | 
	
	
		
			
				|  | @@ -58,7 +59,6 @@ import org.elasticsearch.index.mapper.MapperService;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.mapper.ObjectMapper;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.mapper.ObjectMapper.Nested;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.query.QueryShardContext;
 | 
	
		
			
				|  |  | -import org.elasticsearch.index.query.support.NestedScope;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.shard.IndexShard;
 | 
	
		
			
				|  |  |  import org.elasticsearch.index.shard.ShardId;
 | 
	
		
			
				|  |  |  import org.elasticsearch.indices.breaker.CircuitBreakerService;
 | 
	
	
		
			
				|  | @@ -83,10 +83,10 @@ import java.util.ArrayList;
 | 
	
		
			
				|  |  |  import java.util.Arrays;
 | 
	
		
			
				|  |  |  import java.util.Collections;
 | 
	
		
			
				|  |  |  import java.util.HashMap;
 | 
	
		
			
				|  |  | -import java.util.HashSet;
 | 
	
		
			
				|  |  |  import java.util.List;
 | 
	
		
			
				|  |  |  import java.util.Map;
 | 
	
		
			
				|  |  |  import java.util.Objects;
 | 
	
		
			
				|  |  | +import java.util.function.BiFunction;
 | 
	
		
			
				|  |  |  import java.util.function.Function;
 | 
	
		
			
				|  |  |  import java.util.stream.Collectors;
 | 
	
		
			
				|  |  |  
 | 
	
	
		
			
				|  | @@ -157,8 +157,8 @@ public abstract class AggregatorTestCase extends ESTestCase {
 | 
	
		
			
				|  |  |          SearchLookup searchLookup = new SearchLookup(mapperService, ifds::getForField);
 | 
	
		
			
				|  |  |          when(searchContext.lookup()).thenReturn(searchLookup);
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -        QueryShardContext queryShardContext = queryShardContextMock(mapperService);
 | 
	
		
			
				|  |  | -        when(queryShardContext.getIndexSettings()).thenReturn(indexSettings);
 | 
	
		
			
				|  |  | +        QueryShardContext queryShardContext = queryShardContextMock(mapperService, indexSettings, circuitBreakerService);
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |          when(searchContext.getQueryShardContext()).thenReturn(queryShardContext);
 | 
	
		
			
				|  |  |          Map<String, MappedFieldType> fieldNameToType = new HashMap<>();
 | 
	
		
			
				|  |  |          fieldNameToType.putAll(Arrays.stream(fieldTypes)
 | 
	
	
		
			
				|  | @@ -189,16 +189,11 @@ public abstract class AggregatorTestCase extends ESTestCase {
 | 
	
		
			
				|  |  |              String fieldName = entry.getKey();
 | 
	
		
			
				|  |  |              MappedFieldType fieldType = entry.getValue();
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -            when(queryShardContext.fieldMapper(fieldName)).thenReturn(fieldType);
 | 
	
		
			
				|  |  | +            when(mapperService.fullName(fieldName)).thenReturn(fieldType);
 | 
	
		
			
				|  |  |              when(searchContext.smartNameFieldType(fieldName)).thenReturn(fieldType);
 | 
	
		
			
				|  |  |          }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -        for (MappedFieldType fieldType : new HashSet<>(fieldNameToType.values())) {
 | 
	
		
			
				|  |  | -            when(queryShardContext.getForField(fieldType)).then(invocation ->
 | 
	
		
			
				|  |  | -                fieldType.fielddataBuilder(mapperService.getIndexSettings().getIndex().getName())
 | 
	
		
			
				|  |  | -                    .build(mapperService.getIndexSettings(), fieldType,
 | 
	
		
			
				|  |  | -                        new IndexFieldDataCache.None(), circuitBreakerService, mapperService));
 | 
	
		
			
				|  |  | -        }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |      }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |      protected <A extends Aggregator> A createAggregator(AggregationBuilder aggregationBuilder,
 | 
	
	
		
			
				|  | @@ -304,12 +299,31 @@ public abstract class AggregatorTestCase extends ESTestCase {
 | 
	
		
			
				|  |  |      /**
 | 
	
		
			
				|  |  |       * sub-tests that need a more complex mock can overwrite this
 | 
	
		
			
				|  |  |       */
 | 
	
		
			
				|  |  | -    protected QueryShardContext queryShardContextMock(MapperService mapperService) {
 | 
	
		
			
				|  |  | -        QueryShardContext queryShardContext = mock(QueryShardContext.class);
 | 
	
		
			
				|  |  | -        when(queryShardContext.getMapperService()).thenReturn(mapperService);
 | 
	
		
			
				|  |  | -        NestedScope nestedScope = new NestedScope();
 | 
	
		
			
				|  |  | -        when(queryShardContext.nestedScope()).thenReturn(nestedScope);
 | 
	
		
			
				|  |  | -        return queryShardContext;
 | 
	
		
			
				|  |  | +    protected QueryShardContext queryShardContextMock(MapperService mapperService, IndexSettings indexSettings,
 | 
	
		
			
				|  |  | +                                                      CircuitBreakerService circuitBreakerService) {
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +        return new QueryShardContext(0, indexSettings, null, null,
 | 
	
		
			
				|  |  | +            getIndexFieldDataLookup(mapperService, circuitBreakerService),
 | 
	
		
			
				|  |  | +            mapperService, null, getMockScriptService(), xContentRegistry(),
 | 
	
		
			
				|  |  | +            writableRegistry(), null, null, System::currentTimeMillis, null);
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    /**
 | 
	
		
			
				|  |  | +     * Sub-tests that need a more complex index field data provider can override this
 | 
	
		
			
				|  |  | +     */
 | 
	
		
			
				|  |  | +    protected BiFunction<MappedFieldType, String, IndexFieldData<?>> getIndexFieldDataLookup(MapperService mapperService,
 | 
	
		
			
				|  |  | +                                                                                             CircuitBreakerService circuitBreakerService) {
 | 
	
		
			
				|  |  | +        return (fieldType, s) -> fieldType.fielddataBuilder(mapperService.getIndexSettings().getIndex().getName())
 | 
	
		
			
				|  |  | +            .build(mapperService.getIndexSettings(), fieldType,
 | 
	
		
			
				|  |  | +                new IndexFieldDataCache.None(), circuitBreakerService, mapperService);
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    /**
 | 
	
		
			
				|  |  | +     * Sub-tests that need scripting can override this method to provide a script service and pre-baked scripts
 | 
	
		
			
				|  |  | +     */
 | 
	
		
			
				|  |  | +    protected ScriptService getMockScriptService() {
 | 
	
		
			
				|  |  | +        return null;
 | 
	
		
			
				|  |  |      }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |      protected <A extends InternalAggregation, C extends Aggregator> A search(IndexSearcher searcher,
 |