Do not warm up searcher in engine constructor (#48605)
With this change, we won't warm up searchers until we externally refresh an engine. We explicitly refresh before allowing reading from a shard (i.e., move to post_recovery state) and during resetting. These guarantees that we have warmed up the engine before exposing the external searcher. Another prerequisite for #47186.
This commit is contained in:
parent
c9ead80c31
commit
f8ef402027
|
@ -670,6 +670,7 @@ public abstract class Engine implements Closeable {
|
||||||
}
|
}
|
||||||
Releasable releasable = store::decRef;
|
Releasable releasable = store::decRef;
|
||||||
try {
|
try {
|
||||||
|
assert assertSearcherIsWarmedUp(source, scope);
|
||||||
ReferenceManager<ElasticsearchDirectoryReader> referenceManager = getReferenceManager(scope);
|
ReferenceManager<ElasticsearchDirectoryReader> referenceManager = getReferenceManager(scope);
|
||||||
final ElasticsearchDirectoryReader acquire = referenceManager.acquire();
|
final ElasticsearchDirectoryReader acquire = referenceManager.acquire();
|
||||||
AtomicBoolean released = new AtomicBoolean(false);
|
AtomicBoolean released = new AtomicBoolean(false);
|
||||||
|
@ -705,6 +706,10 @@ public abstract class Engine implements Closeable {
|
||||||
|
|
||||||
protected abstract ReferenceManager<ElasticsearchDirectoryReader> getReferenceManager(SearcherScope scope);
|
protected abstract ReferenceManager<ElasticsearchDirectoryReader> getReferenceManager(SearcherScope scope);
|
||||||
|
|
||||||
|
boolean assertSearcherIsWarmedUp(String source, SearcherScope scope) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
public enum SearcherScope {
|
public enum SearcherScope {
|
||||||
EXTERNAL, INTERNAL
|
EXTERNAL, INTERNAL
|
||||||
}
|
}
|
||||||
|
|
|
@ -322,18 +322,13 @@ public class InternalEngine extends Engine {
|
||||||
private static final class ExternalReaderManager extends ReferenceManager<ElasticsearchDirectoryReader> {
|
private static final class ExternalReaderManager extends ReferenceManager<ElasticsearchDirectoryReader> {
|
||||||
private final BiConsumer<ElasticsearchDirectoryReader, ElasticsearchDirectoryReader> refreshListener;
|
private final BiConsumer<ElasticsearchDirectoryReader, ElasticsearchDirectoryReader> refreshListener;
|
||||||
private final ElasticsearchReaderManager internalReaderManager;
|
private final ElasticsearchReaderManager internalReaderManager;
|
||||||
|
private boolean isWarmedUp; //guarded by refreshLock
|
||||||
|
|
||||||
ExternalReaderManager(ElasticsearchReaderManager internalReaderManager,
|
ExternalReaderManager(ElasticsearchReaderManager internalReaderManager,
|
||||||
BiConsumer<ElasticsearchDirectoryReader, ElasticsearchDirectoryReader> refreshListener) throws IOException {
|
BiConsumer<ElasticsearchDirectoryReader, ElasticsearchDirectoryReader> refreshListener) throws IOException {
|
||||||
this.refreshListener = refreshListener;
|
this.refreshListener = refreshListener;
|
||||||
this.internalReaderManager = internalReaderManager;
|
this.internalReaderManager = internalReaderManager;
|
||||||
ElasticsearchDirectoryReader acquire = internalReaderManager.acquire();
|
this.current = internalReaderManager.acquire(); // steal the reference without warming up
|
||||||
try {
|
|
||||||
incrementAndNotify(acquire, null);
|
|
||||||
current = acquire;
|
|
||||||
} finally {
|
|
||||||
internalReaderManager.release(acquire);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -342,26 +337,25 @@ public class InternalEngine extends Engine {
|
||||||
// it's a save operation since we acquire the reader which incs it's reference but then down the road
|
// it's a save operation since we acquire the reader which incs it's reference but then down the road
|
||||||
// steal it by calling incRef on the "stolen" reader
|
// steal it by calling incRef on the "stolen" reader
|
||||||
internalReaderManager.maybeRefreshBlocking();
|
internalReaderManager.maybeRefreshBlocking();
|
||||||
ElasticsearchDirectoryReader acquire = internalReaderManager.acquire();
|
final ElasticsearchDirectoryReader newReader = internalReaderManager.acquire();
|
||||||
try {
|
if (isWarmedUp == false || newReader != referenceToRefresh) {
|
||||||
if (acquire == referenceToRefresh) {
|
boolean success = false;
|
||||||
// nothing has changed - both ref managers share the same instance so we can use reference equality
|
try {
|
||||||
return null;
|
refreshListener.accept(newReader, isWarmedUp ? referenceToRefresh : null);
|
||||||
} else {
|
isWarmedUp = true;
|
||||||
incrementAndNotify(acquire, referenceToRefresh);
|
success = true;
|
||||||
return acquire;
|
} finally {
|
||||||
|
if (success == false) {
|
||||||
|
internalReaderManager.release(newReader);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} finally {
|
|
||||||
internalReaderManager.release(acquire);
|
|
||||||
}
|
}
|
||||||
}
|
// nothing has changed - both ref managers share the same instance so we can use reference equality
|
||||||
|
if (referenceToRefresh == newReader) {
|
||||||
private void incrementAndNotify(ElasticsearchDirectoryReader reader,
|
internalReaderManager.release(newReader);
|
||||||
ElasticsearchDirectoryReader previousReader) throws IOException {
|
return null;
|
||||||
reader.incRef(); // steal the reference
|
} else {
|
||||||
try (Closeable c = reader::decRef) {
|
return newReader; // steal the reference
|
||||||
refreshListener.accept(reader, previousReader);
|
|
||||||
reader.incRef(); // double inc-ref if we were successful
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -376,7 +370,24 @@ public class InternalEngine extends Engine {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void decRef(ElasticsearchDirectoryReader reference) throws IOException { reference.decRef(); }
|
protected void decRef(ElasticsearchDirectoryReader reference) throws IOException {
|
||||||
|
reference.decRef();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
final boolean assertSearcherIsWarmedUp(String source, SearcherScope scope) {
|
||||||
|
if (scope == SearcherScope.EXTERNAL) {
|
||||||
|
switch (source) {
|
||||||
|
// we can access segment_stats while a shard is still in the recovering state.
|
||||||
|
case "segments":
|
||||||
|
case "segments_stats":
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
assert externalReaderManager.isWarmedUp : "searcher was not warmed up yet for source[" + source + "]";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -2702,6 +2702,7 @@ public class IndexShard extends AbstractIndexShardComponent implements IndicesCl
|
||||||
final Sort indexSort = indexSortSupplier.get();
|
final Sort indexSort = indexSortSupplier.get();
|
||||||
final Engine.Warmer warmer = reader -> {
|
final Engine.Warmer warmer = reader -> {
|
||||||
assert Thread.holdsLock(mutex) == false : "warming engine under mutex";
|
assert Thread.holdsLock(mutex) == false : "warming engine under mutex";
|
||||||
|
assert reader != null;
|
||||||
if (this.warmer != null) {
|
if (this.warmer != null) {
|
||||||
this.warmer.warm(reader);
|
this.warmer.warm(reader);
|
||||||
}
|
}
|
||||||
|
@ -3413,6 +3414,7 @@ public class IndexShard extends AbstractIndexShardComponent implements IndicesCl
|
||||||
// TODO: add a dedicate recovery stats for the reset translog
|
// TODO: add a dedicate recovery stats for the reset translog
|
||||||
});
|
});
|
||||||
newEngineReference.get().recoverFromTranslog(translogRunner, globalCheckpoint);
|
newEngineReference.get().recoverFromTranslog(translogRunner, globalCheckpoint);
|
||||||
|
newEngineReference.get().refresh("reset_engine");
|
||||||
synchronized (mutex) {
|
synchronized (mutex) {
|
||||||
verifyNotClosed();
|
verifyNotClosed();
|
||||||
IOUtils.close(currentEngineReference.getAndSet(newEngineReference.get()));
|
IOUtils.close(currentEngineReference.getAndSet(newEngineReference.get()));
|
||||||
|
|
|
@ -204,6 +204,7 @@ import static org.hamcrest.Matchers.greaterThanOrEqualTo;
|
||||||
import static org.hamcrest.Matchers.hasItem;
|
import static org.hamcrest.Matchers.hasItem;
|
||||||
import static org.hamcrest.Matchers.hasKey;
|
import static org.hamcrest.Matchers.hasKey;
|
||||||
import static org.hamcrest.Matchers.hasSize;
|
import static org.hamcrest.Matchers.hasSize;
|
||||||
|
import static org.hamcrest.Matchers.in;
|
||||||
import static org.hamcrest.Matchers.isIn;
|
import static org.hamcrest.Matchers.isIn;
|
||||||
import static org.hamcrest.Matchers.lessThanOrEqualTo;
|
import static org.hamcrest.Matchers.lessThanOrEqualTo;
|
||||||
import static org.hamcrest.Matchers.not;
|
import static org.hamcrest.Matchers.not;
|
||||||
|
@ -215,6 +216,7 @@ import static org.mockito.Mockito.when;
|
||||||
public class InternalEngineTests extends EngineTestCase {
|
public class InternalEngineTests extends EngineTestCase {
|
||||||
|
|
||||||
public void testVersionMapAfterAutoIDDocument() throws IOException {
|
public void testVersionMapAfterAutoIDDocument() throws IOException {
|
||||||
|
engine.refresh("warm_up");
|
||||||
ParsedDocument doc = testParsedDocument("1", null, testDocumentWithTextField("test"),
|
ParsedDocument doc = testParsedDocument("1", null, testDocumentWithTextField("test"),
|
||||||
new BytesArray("{}".getBytes(Charset.defaultCharset())), null);
|
new BytesArray("{}".getBytes(Charset.defaultCharset())), null);
|
||||||
Engine.Index operation = randomBoolean() ?
|
Engine.Index operation = randomBoolean() ?
|
||||||
|
@ -926,6 +928,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testSimpleOperations() throws Exception {
|
public void testSimpleOperations() throws Exception {
|
||||||
|
engine.refresh("warm_up");
|
||||||
Engine.Searcher searchResult = engine.acquireSearcher("test");
|
Engine.Searcher searchResult = engine.acquireSearcher("test");
|
||||||
MatcherAssert.assertThat(searchResult, EngineSearcherTotalHitsMatcher.engineSearcherTotalHits(0));
|
MatcherAssert.assertThat(searchResult, EngineSearcherTotalHitsMatcher.engineSearcherTotalHits(0));
|
||||||
searchResult.close();
|
searchResult.close();
|
||||||
|
@ -1103,6 +1106,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testSearchResultRelease() throws Exception {
|
public void testSearchResultRelease() throws Exception {
|
||||||
|
engine.refresh("warm_up");
|
||||||
Engine.Searcher searchResult = engine.acquireSearcher("test");
|
Engine.Searcher searchResult = engine.acquireSearcher("test");
|
||||||
MatcherAssert.assertThat(searchResult, EngineSearcherTotalHitsMatcher.engineSearcherTotalHits(0));
|
MatcherAssert.assertThat(searchResult, EngineSearcherTotalHitsMatcher.engineSearcherTotalHits(0));
|
||||||
searchResult.close();
|
searchResult.close();
|
||||||
|
@ -2175,7 +2179,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
final int opsOnPrimary = assertOpsOnPrimary(primaryOps, finalReplicaVersion, deletedOnReplica, replicaEngine);
|
final int opsOnPrimary = assertOpsOnPrimary(primaryOps, finalReplicaVersion, deletedOnReplica, replicaEngine);
|
||||||
final long currentSeqNo = getSequenceID(replicaEngine,
|
final long currentSeqNo = getSequenceID(replicaEngine,
|
||||||
new Engine.Get(false, false, "type", lastReplicaOp.uid().text(), lastReplicaOp.uid())).v1();
|
new Engine.Get(false, false, "type", lastReplicaOp.uid().text(), lastReplicaOp.uid())).v1();
|
||||||
try (Engine.Searcher searcher = engine.acquireSearcher("test")) {
|
try (Engine.Searcher searcher = engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL)) {
|
||||||
final TotalHitCountCollector collector = new TotalHitCountCollector();
|
final TotalHitCountCollector collector = new TotalHitCountCollector();
|
||||||
searcher.search(new MatchAllDocsQuery(), collector);
|
searcher.search(new MatchAllDocsQuery(), collector);
|
||||||
if (collector.getTotalHits() > 0) {
|
if (collector.getTotalHits() > 0) {
|
||||||
|
@ -2740,7 +2744,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testExtractShardId() {
|
public void testExtractShardId() {
|
||||||
try (Engine.Searcher test = this.engine.acquireSearcher("test")) {
|
try (Engine.Searcher test = this.engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL)) {
|
||||||
ShardId shardId = ShardUtils.extractShardId(test.getDirectoryReader());
|
ShardId shardId = ShardUtils.extractShardId(test.getDirectoryReader());
|
||||||
assertNotNull(shardId);
|
assertNotNull(shardId);
|
||||||
assertEquals(shardId, engine.config().getShardId());
|
assertEquals(shardId, engine.config().getShardId());
|
||||||
|
@ -3015,7 +3019,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
engine.close();
|
engine.close();
|
||||||
try (InternalEngine engine = new InternalEngine(config)) {
|
try (InternalEngine engine = new InternalEngine(config)) {
|
||||||
engine.skipTranslogRecovery();
|
engine.skipTranslogRecovery();
|
||||||
try (Engine.Searcher searcher = engine.acquireSearcher("test")) {
|
try (Engine.Searcher searcher = engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL)) {
|
||||||
TopDocs topDocs = searcher.search(new MatchAllDocsQuery(), randomIntBetween(numDocs, numDocs + 10));
|
TopDocs topDocs = searcher.search(new MatchAllDocsQuery(), randomIntBetween(numDocs, numDocs + 10));
|
||||||
assertThat(topDocs.totalHits.value, equalTo(0L));
|
assertThat(topDocs.totalHits.value, equalTo(0L));
|
||||||
}
|
}
|
||||||
|
@ -3058,6 +3062,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
// we need to reuse the engine config unless the parser.mappingModified won't work
|
// we need to reuse the engine config unless the parser.mappingModified won't work
|
||||||
engine = new InternalEngine(copy(engine.config(), inSyncGlobalCheckpointSupplier));
|
engine = new InternalEngine(copy(engine.config(), inSyncGlobalCheckpointSupplier));
|
||||||
engine.recoverFromTranslog(translogHandler, Long.MAX_VALUE);
|
engine.recoverFromTranslog(translogHandler, Long.MAX_VALUE);
|
||||||
|
engine.refresh("warm_up");
|
||||||
|
|
||||||
assertVisibleCount(engine, numDocs, false);
|
assertVisibleCount(engine, numDocs, false);
|
||||||
assertEquals(numDocs, translogHandler.appliedOperations());
|
assertEquals(numDocs, translogHandler.appliedOperations());
|
||||||
|
@ -3071,6 +3076,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
engine.close();
|
engine.close();
|
||||||
translogHandler = createTranslogHandler(engine.engineConfig.getIndexSettings());
|
translogHandler = createTranslogHandler(engine.engineConfig.getIndexSettings());
|
||||||
engine = createEngine(store, primaryTranslogDir, inSyncGlobalCheckpointSupplier);
|
engine = createEngine(store, primaryTranslogDir, inSyncGlobalCheckpointSupplier);
|
||||||
|
engine.refresh("warm_up");
|
||||||
assertVisibleCount(engine, numDocs, false);
|
assertVisibleCount(engine, numDocs, false);
|
||||||
assertEquals(0, translogHandler.appliedOperations());
|
assertEquals(0, translogHandler.appliedOperations());
|
||||||
|
|
||||||
|
@ -3100,6 +3106,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
engine.close();
|
engine.close();
|
||||||
translogHandler = createTranslogHandler(engine.engineConfig.getIndexSettings());
|
translogHandler = createTranslogHandler(engine.engineConfig.getIndexSettings());
|
||||||
engine = createEngine(store, primaryTranslogDir, inSyncGlobalCheckpointSupplier);
|
engine = createEngine(store, primaryTranslogDir, inSyncGlobalCheckpointSupplier);
|
||||||
|
engine.refresh("warm_up");
|
||||||
try (Engine.Searcher searcher = engine.acquireSearcher("test")) {
|
try (Engine.Searcher searcher = engine.acquireSearcher("test")) {
|
||||||
TopDocs topDocs = searcher.search(new MatchAllDocsQuery(), numDocs + 1);
|
TopDocs topDocs = searcher.search(new MatchAllDocsQuery(), numDocs + 1);
|
||||||
assertThat(topDocs.totalHits.value, equalTo(numDocs + 1L));
|
assertThat(topDocs.totalHits.value, equalTo(numDocs + 1L));
|
||||||
|
@ -4491,7 +4498,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
* second is the primary term.
|
* second is the primary term.
|
||||||
*/
|
*/
|
||||||
private Tuple<Long, Long> getSequenceID(Engine engine, Engine.Get get) throws EngineException {
|
private Tuple<Long, Long> getSequenceID(Engine engine, Engine.Get get) throws EngineException {
|
||||||
try (Engine.Searcher searcher = engine.acquireSearcher("get")) {
|
try (Engine.Searcher searcher = engine.acquireSearcher("get", Engine.SearcherScope.INTERNAL)) {
|
||||||
final long primaryTerm;
|
final long primaryTerm;
|
||||||
final long seqNo;
|
final long seqNo;
|
||||||
DocIdAndSeqNo docIdAndSeqNo = VersionsAndSeqNoResolver.loadDocIdAndSeqNo(searcher.getIndexReader(), get.uid());
|
DocIdAndSeqNo docIdAndSeqNo = VersionsAndSeqNoResolver.loadDocIdAndSeqNo(searcher.getIndexReader(), get.uid());
|
||||||
|
@ -4673,7 +4680,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
InternalEngine engine =
|
InternalEngine engine =
|
||||||
// disable merges to make sure that the reader doesn't change unexpectedly during the test
|
// disable merges to make sure that the reader doesn't change unexpectedly during the test
|
||||||
createEngine(defaultSettings, store, createTempDir(), NoMergePolicy.INSTANCE)) {
|
createEngine(defaultSettings, store, createTempDir(), NoMergePolicy.INSTANCE)) {
|
||||||
|
engine.refresh("warm_up");
|
||||||
try (Engine.Searcher getSearcher = engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL);
|
try (Engine.Searcher getSearcher = engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL);
|
||||||
Engine.Searcher searchSearcher = engine.acquireSearcher("test", Engine.SearcherScope.EXTERNAL)) {
|
Engine.Searcher searchSearcher = engine.acquireSearcher("test", Engine.SearcherScope.EXTERNAL)) {
|
||||||
assertSameReader(getSearcher, searchSearcher);
|
assertSameReader(getSearcher, searchSearcher);
|
||||||
|
@ -5536,7 +5543,7 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
|
|
||||||
public void testAcquireSearcherOnClosingEngine() throws Exception {
|
public void testAcquireSearcherOnClosingEngine() throws Exception {
|
||||||
engine.close();
|
engine.close();
|
||||||
expectThrows(AlreadyClosedException.class, () -> engine.acquireSearcher("test"));
|
expectThrows(AlreadyClosedException.class, () -> engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void testNoOpOnClosingEngine() throws Exception {
|
public void testNoOpOnClosingEngine() throws Exception {
|
||||||
|
@ -6195,4 +6202,59 @@ public class InternalEngineTests extends EngineTestCase {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testNotWarmUpSearcherInEngineCtor() throws Exception {
|
||||||
|
try (Store store = createStore()) {
|
||||||
|
List<ElasticsearchDirectoryReader> warmedUpReaders = new ArrayList<>();
|
||||||
|
Engine.Warmer warmer = reader -> {
|
||||||
|
assertNotNull(reader);
|
||||||
|
assertThat(reader, not(in(warmedUpReaders)));
|
||||||
|
warmedUpReaders.add(reader);
|
||||||
|
};
|
||||||
|
EngineConfig config = engine.config();
|
||||||
|
final TranslogConfig translogConfig = new TranslogConfig(config.getTranslogConfig().getShardId(),
|
||||||
|
createTempDir(), config.getTranslogConfig().getIndexSettings(), config.getTranslogConfig().getBigArrays());
|
||||||
|
EngineConfig configWithWarmer = new EngineConfig(config.getShardId(), config.getAllocationId(), config.getThreadPool(),
|
||||||
|
config.getIndexSettings(), warmer, store, config.getMergePolicy(), config.getAnalyzer(),
|
||||||
|
config.getSimilarity(), new CodecService(null, logger), config.getEventListener(), config.getQueryCache(),
|
||||||
|
config.getQueryCachingPolicy(), translogConfig, config.getFlushMergesAfter(),
|
||||||
|
config.getExternalRefreshListener(), config.getInternalRefreshListener(), config.getIndexSort(),
|
||||||
|
config.getCircuitBreakerService(), config.getGlobalCheckpointSupplier(), config.retentionLeasesSupplier(),
|
||||||
|
config.getPrimaryTermSupplier(), config.getTombstoneDocSupplier());
|
||||||
|
try (InternalEngine engine = createEngine(configWithWarmer)) {
|
||||||
|
assertThat(warmedUpReaders, empty());
|
||||||
|
assertThat(expectThrows(Throwable.class, () -> engine.acquireSearcher("test")).getMessage(),
|
||||||
|
equalTo("searcher was not warmed up yet for source[test]"));
|
||||||
|
int times = randomIntBetween(1, 10);
|
||||||
|
for (int i = 0; i < times; i++) {
|
||||||
|
engine.refresh("test");
|
||||||
|
}
|
||||||
|
assertThat(warmedUpReaders, hasSize(1));
|
||||||
|
try (Engine.Searcher internalSearcher = engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL)) {
|
||||||
|
try (Engine.Searcher externalSearcher = engine.acquireSearcher("test", Engine.SearcherScope.EXTERNAL)) {
|
||||||
|
assertSame(internalSearcher.getDirectoryReader(), externalSearcher.getDirectoryReader());
|
||||||
|
assertSame(warmedUpReaders.get(0), externalSearcher.getDirectoryReader());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
index(engine, randomInt());
|
||||||
|
if (randomBoolean()) {
|
||||||
|
engine.refresh("test", Engine.SearcherScope.INTERNAL, true);
|
||||||
|
assertThat(warmedUpReaders, hasSize(1));
|
||||||
|
try (Engine.Searcher internalSearcher = engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL)) {
|
||||||
|
try (Engine.Searcher externalSearcher = engine.acquireSearcher("test", Engine.SearcherScope.EXTERNAL)) {
|
||||||
|
assertNotSame(internalSearcher.getDirectoryReader(), externalSearcher.getDirectoryReader());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
engine.refresh("test");
|
||||||
|
assertThat(warmedUpReaders, hasSize(2));
|
||||||
|
try (Engine.Searcher internalSearcher = engine.acquireSearcher("test", Engine.SearcherScope.INTERNAL)) {
|
||||||
|
try (Engine.Searcher externalSearcher = engine.acquireSearcher("test", Engine.SearcherScope.EXTERNAL)) {
|
||||||
|
assertSame(internalSearcher.getDirectoryReader(), externalSearcher.getDirectoryReader());
|
||||||
|
assertSame(warmedUpReaders.get(1), externalSearcher.getDirectoryReader());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue