LUCENE-10190: Ensure changes are visible before advancing seqno (#640)
DocumentWriter#anyChanges() can return false after we process and
generate a sequence number for an update operation; but before we adjust
the numDocsInRAM. In this window of time, refreshes are noop, although
the maxCompletedSequenceNumber has advanced.
diff --git a/lucene/core/src/java/org/apache/lucene/index/DocumentsWriter.java b/lucene/core/src/java/org/apache/lucene/index/DocumentsWriter.java
index 97b014f..5c21622 100644
--- a/lucene/core/src/java/org/apache/lucene/index/DocumentsWriter.java
+++ b/lucene/core/src/java/org/apache/lucene/index/DocumentsWriter.java
@@ -427,17 +427,13 @@
// This must happen after we've pulled the DWPT because IW.close
// waits for all DWPT to be released:
ensureOpen();
- final int dwptNumDocs = dwpt.getNumDocsInRAM();
try {
- seqNo = dwpt.updateDocuments(docs, delNode, flushNotifications);
+ seqNo =
+ dwpt.updateDocuments(docs, delNode, flushNotifications, numDocsInRAM::incrementAndGet);
} finally {
if (dwpt.isAborted()) {
flushControl.doOnAbort(dwpt);
}
- // We don't know how many documents were actually
- // counted as indexed, so we must subtract here to
- // accumulate our separate counter:
- numDocsInRAM.addAndGet(dwpt.getNumDocsInRAM() - dwptNumDocs);
}
final boolean isUpdate = delNode != null && delNode.isDelete();
flushingDWPT = flushControl.doAfterDocument(dwpt, isUpdate);
diff --git a/lucene/core/src/java/org/apache/lucene/index/DocumentsWriterPerThread.java b/lucene/core/src/java/org/apache/lucene/index/DocumentsWriterPerThread.java
index 451c2a7..4083e95 100644
--- a/lucene/core/src/java/org/apache/lucene/index/DocumentsWriterPerThread.java
+++ b/lucene/core/src/java/org/apache/lucene/index/DocumentsWriterPerThread.java
@@ -209,7 +209,8 @@
long updateDocuments(
Iterable<? extends Iterable<? extends IndexableField>> docs,
DocumentsWriterDeleteQueue.Node<?> deleteNode,
- DocumentsWriter.FlushNotifications flushNotifications)
+ DocumentsWriter.FlushNotifications flushNotifications,
+ Runnable onNewDocOnRAM)
throws IOException {
try {
testPoint("DocumentsWriterPerThread addDocuments start");
@@ -236,7 +237,11 @@
// it's very hard to fix (we can't easily distinguish aborting
// vs non-aborting exceptions):
reserveOneDoc();
- indexingChain.processDocument(numDocsInRAM++, doc);
+ try {
+ indexingChain.processDocument(numDocsInRAM++, doc);
+ } finally {
+ onNewDocOnRAM.run();
+ }
}
allDocsIndexed = true;
return finishDocuments(deleteNode, docsInRamBefore);