diff --git a/lucene/CHANGES.txt b/lucene/CHANGES.txt index 622dce800460..0787724aac7f 100644 --- a/lucene/CHANGES.txt +++ b/lucene/CHANGES.txt @@ -106,6 +106,8 @@ Optimizations * GITHUB#15597: Reduce memory usage of NeighborArray (Viliam Durina) +* GITHUB#15683: Reuse reader's fieldinfos. (Vliam Durina) + Bug Fixes --------------------- * GITHUB#14049: Randomize KNN codec params in RandomCodec. Fixes scalar quantization div-by-zero diff --git a/lucene/core/src/java/org/apache/lucene/index/IndexWriter.java b/lucene/core/src/java/org/apache/lucene/index/IndexWriter.java index bd166b71e473..e4c68e6f3df2 100644 --- a/lucene/core/src/java/org/apache/lucene/index/IndexWriter.java +++ b/lucene/core/src/java/org/apache/lucene/index/IndexWriter.java @@ -1119,7 +1119,7 @@ public IndexWriter(Directory d, IndexWriterConfig conf) throws IOException { // start with previous field numbers, but new FieldInfos // NOTE: this is correct even for an NRT reader because we'll pull FieldInfos even for the // un-committed segments: - globalFieldNumberMap = getFieldNumberMap(); + globalFieldNumberMap = getFieldNumberMap(reader); if (create == false && conf.getParentField() != null && globalFieldNumberMap.getFieldNames().isEmpty() == false @@ -1258,17 +1258,28 @@ static FieldInfos readFieldInfos(SegmentCommitInfo si) throws IOException { } /** - * Loads or returns the already loaded global field number map for this {@link SegmentInfos}. If - * this {@link SegmentInfos} has no global field number map, the returned instance is empty. + * Loads the global field number map for this {@link SegmentInfos}. If this {@link SegmentInfos} + * has no global field number map the returned instance is empty. + * + *

If the a {@code reader} is given, then instead of reading the field info file (.fnm), the + * field infos from its leaves are used. */ - private FieldNumbers getFieldNumberMap() throws IOException { + private FieldNumbers getFieldNumberMap(StandardDirectoryReader reader) throws IOException { final FieldNumbers map = new FieldNumbers(config.getSoftDeletesField(), config.getParentField()); - for (SegmentCommitInfo info : segmentInfos) { - FieldInfos fis = readFieldInfos(info); - for (FieldInfo fi : fis) { - map.addOrGet(fi); + if (reader == null) { + for (SegmentCommitInfo info : segmentInfos) { + FieldInfos fis = readFieldInfos(info); + for (FieldInfo fi : fis) { + map.addOrGet(fi); + } + } + } else { + for (LeafReaderContext leafContext : reader.leaves()) { + for (FieldInfo fi : leafContext.reader().getFieldInfos()) { + map.addOrGet(fi); + } } } return map;