|
123 | 123 | import org.elasticsearch.index.translog.Translog;
|
124 | 124 | import org.elasticsearch.index.translog.TranslogConfig;
|
125 | 125 | import org.elasticsearch.indices.breaker.NoneCircuitBreakerService;
|
| 126 | +import org.elasticsearch.test.IndexSettingsModule; |
126 | 127 | import org.hamcrest.MatcherAssert;
|
127 | 128 | import org.hamcrest.Matchers;
|
128 | 129 |
|
|
178 | 179 | import static org.hamcrest.Matchers.hasItem;
|
179 | 180 | import static org.hamcrest.Matchers.hasKey;
|
180 | 181 | import static org.hamcrest.Matchers.hasSize;
|
| 182 | +import static org.hamcrest.Matchers.isIn; |
181 | 183 | import static org.hamcrest.Matchers.lessThanOrEqualTo;
|
182 | 184 | import static org.hamcrest.Matchers.not;
|
183 | 185 | import static org.hamcrest.Matchers.notNullValue;
|
@@ -251,8 +253,9 @@ public void testVersionMapAfterAutoIDDocument() throws IOException {
|
251 | 253 | }
|
252 | 254 |
|
253 | 255 | public void testSegments() throws Exception {
|
| 256 | + final AtomicLong globalCheckpoint = new AtomicLong(SequenceNumbers.NO_OPS_PERFORMED); |
254 | 257 | try (Store store = createStore();
|
255 |
| - InternalEngine engine = createEngine(defaultSettings, store, createTempDir(), NoMergePolicy.INSTANCE)) { |
| 258 | + InternalEngine engine = createEngine(config(defaultSettings, store, createTempDir(), NoMergePolicy.INSTANCE, null, null, globalCheckpoint::get))) { |
256 | 259 | List<Segment> segments = engine.segments(false);
|
257 | 260 | assertThat(segments.isEmpty(), equalTo(true));
|
258 | 261 | assertThat(engine.segmentsStats(false).getCount(), equalTo(0L));
|
@@ -324,6 +327,8 @@ public void testSegments() throws Exception {
|
324 | 327 |
|
325 | 328 |
|
326 | 329 | engine.delete(new Engine.Delete("test", "1", newUid(doc), primaryTerm.get()));
|
| 330 | + globalCheckpoint.set(engine.getLocalCheckpointTracker().getCheckpoint()); |
| 331 | + engine.getTranslog().sync(); |
327 | 332 | engine.refresh("test");
|
328 | 333 |
|
329 | 334 | segments = engine.segments(false);
|
@@ -1279,9 +1284,13 @@ public void testVersioningNewIndex() throws IOException {
|
1279 | 1284 | assertThat(indexResult.getVersion(), equalTo(1L));
|
1280 | 1285 | }
|
1281 | 1286 |
|
1282 |
| - public void testForceMerge() throws IOException { |
| 1287 | + public void testForceMergeWithoutSoftDeletes() throws IOException { |
| 1288 | + Settings settings = Settings.builder() |
| 1289 | + .put(defaultSettings.getSettings()) |
| 1290 | + .put(IndexSettings.INDEX_SOFT_DELETES_SETTING.getKey(), false).build(); |
| 1291 | + IndexMetaData indexMetaData = IndexMetaData.builder(defaultSettings.getIndexMetaData()).settings(settings).build(); |
1283 | 1292 | try (Store store = createStore();
|
1284 |
| - Engine engine = createEngine(config(defaultSettings, store, createTempDir(), |
| 1293 | + Engine engine = createEngine(config(IndexSettingsModule.newIndexSettings(indexMetaData), store, createTempDir(), |
1285 | 1294 | new LogByteSizeMergePolicy(), null))) { // use log MP here we test some behavior in ESMP
|
1286 | 1295 | int numDocs = randomIntBetween(10, 100);
|
1287 | 1296 | for (int i = 0; i < numDocs; i++) {
|
@@ -1322,6 +1331,66 @@ public void testForceMerge() throws IOException {
|
1322 | 1331 | }
|
1323 | 1332 | }
|
1324 | 1333 |
|
| 1334 | + public void testForceMergeWithSoftDeletesRetention() throws Exception { |
| 1335 | + final long retainedExtraOps = randomLongBetween(0, 10); |
| 1336 | + Settings.Builder settings = Settings.builder() |
| 1337 | + .put(defaultSettings.getSettings()) |
| 1338 | + .put(IndexSettings.INDEX_SOFT_DELETES_SETTING.getKey(), true) |
| 1339 | + .put(IndexSettings.INDEX_SOFT_DELETES_RETENTION_OPERATIONS_SETTING.getKey(), retainedExtraOps); |
| 1340 | + final IndexMetaData indexMetaData = IndexMetaData.builder(defaultSettings.getIndexMetaData()).settings(settings).build(); |
| 1341 | + final IndexSettings indexSettings = IndexSettingsModule.newIndexSettings(indexMetaData); |
| 1342 | + final AtomicLong globalCheckpoint = new AtomicLong(SequenceNumbers.NO_OPS_PERFORMED); |
| 1343 | + final MapperService mapperService = createMapperService("test"); |
| 1344 | + final Set<String> liveDocs = new HashSet<>(); |
| 1345 | + try (Store store = createStore(); |
| 1346 | + Engine engine = createEngine(config(indexSettings, store, createTempDir(), newMergePolicy(), null, null, globalCheckpoint::get))) { |
| 1347 | + int numDocs = scaledRandomIntBetween(10, 100); |
| 1348 | + for (int i = 0; i < numDocs; i++) { |
| 1349 | + ParsedDocument doc = testParsedDocument(Integer.toString(i), null, testDocument(), B_1, null); |
| 1350 | + engine.index(indexForDoc(doc)); |
| 1351 | + liveDocs.add(doc.id()); |
| 1352 | + } |
| 1353 | + for (int i = 0; i < numDocs; i++) { |
| 1354 | + ParsedDocument doc = testParsedDocument(Integer.toString(i), null, testDocument(), B_1, null); |
| 1355 | + if (randomBoolean()) { |
| 1356 | + engine.delete(new Engine.Delete(doc.type(), doc.id(), newUid(doc.id()), primaryTerm.get())); |
| 1357 | + liveDocs.remove(doc.id()); |
| 1358 | + } |
| 1359 | + if (randomBoolean()) { |
| 1360 | + engine.index(indexForDoc(doc)); |
| 1361 | + liveDocs.add(doc.id()); |
| 1362 | + } |
| 1363 | + } |
| 1364 | + long localCheckpoint = engine.getLocalCheckpointTracker().getCheckpoint(); |
| 1365 | + globalCheckpoint.set(randomLongBetween(0, localCheckpoint)); |
| 1366 | + engine.getTranslog().sync(); |
| 1367 | + engine.forceMerge(true, 1, false, false, false); |
| 1368 | + assertConsistentHistoryBetweenTranslogAndLuceneIndex(engine, mapperService); |
| 1369 | + Map<Long, Translog.Operation> ops = readAllOperationsInLucene(engine, mapperService) |
| 1370 | + .stream().collect(Collectors.toMap(Translog.Operation::seqNo, Function.identity())); |
| 1371 | + for (long seqno = 0; seqno <= localCheckpoint; seqno++) { |
| 1372 | + long keptIndex = globalCheckpoint.get() + 1 - retainedExtraOps; |
| 1373 | + String msg = "seq# [" + seqno + "], global checkpoint [" + globalCheckpoint + "], retained-ops [" + retainedExtraOps + "]"; |
| 1374 | + if (seqno < keptIndex) { |
| 1375 | + Translog.Operation op = ops.get(seqno); |
| 1376 | + if (op != null) { |
| 1377 | + assertThat(op, instanceOf(Translog.Index.class)); |
| 1378 | + assertThat(msg, ((Translog.Index) op).id(), isIn(liveDocs)); |
| 1379 | + } |
| 1380 | + } else { |
| 1381 | + assertThat(msg, ops.get(seqno), notNullValue()); |
| 1382 | + } |
| 1383 | + } |
| 1384 | + settings.put(IndexSettings.INDEX_SOFT_DELETES_RETENTION_OPERATIONS_SETTING.getKey(), 0); |
| 1385 | + indexSettings.updateIndexMetaData(IndexMetaData.builder(defaultSettings.getIndexMetaData()).settings(settings).build()); |
| 1386 | + globalCheckpoint.set(localCheckpoint); |
| 1387 | + engine.getTranslog().sync(); |
| 1388 | + engine.forceMerge(true, 1, false, false, false); |
| 1389 | + assertConsistentHistoryBetweenTranslogAndLuceneIndex(engine, mapperService); |
| 1390 | + assertThat(readAllOperationsInLucene(engine, mapperService), hasSize(liveDocs.size())); |
| 1391 | + } |
| 1392 | + } |
| 1393 | + |
1325 | 1394 | public void testForceMergeAndClose() throws IOException, InterruptedException {
|
1326 | 1395 | int numIters = randomIntBetween(2, 10);
|
1327 | 1396 | for (int j = 0; j < numIters; j++) {
|
@@ -2525,14 +2594,16 @@ public void testSkipTranslogReplay() throws IOException {
|
2525 | 2594 | Engine.IndexResult indexResult = engine.index(firstIndexRequest);
|
2526 | 2595 | assertThat(indexResult.getVersion(), equalTo(1L));
|
2527 | 2596 | }
|
| 2597 | + EngineConfig config = engine.config(); |
2528 | 2598 | assertVisibleCount(engine, numDocs);
|
2529 | 2599 | engine.close();
|
2530 |
| - trimUnsafeCommits(engine.config()); |
2531 |
| - engine = new InternalEngine(engine.config()); |
2532 |
| - engine.skipTranslogRecovery(); |
2533 |
| - try (Engine.Searcher searcher = engine.acquireSearcher("test")) { |
2534 |
| - TopDocs topDocs = searcher.searcher().search(new MatchAllDocsQuery(), randomIntBetween(numDocs, numDocs + 10)); |
2535 |
| - assertThat(topDocs.totalHits, equalTo(0L)); |
| 2600 | + trimUnsafeCommits(config); |
| 2601 | + try (InternalEngine engine = new InternalEngine(config)) { |
| 2602 | + engine.skipTranslogRecovery(); |
| 2603 | + try (Engine.Searcher searcher = engine.acquireSearcher("test")) { |
| 2604 | + TopDocs topDocs = searcher.searcher().search(new MatchAllDocsQuery(), randomIntBetween(numDocs, numDocs + 10)); |
| 2605 | + assertThat(topDocs.totalHits, equalTo(0L)); |
| 2606 | + } |
2536 | 2607 | }
|
2537 | 2608 | }
|
2538 | 2609 |
|
|
0 commit comments