Skip to content

Commit dd70ed5

Browse files
authored
#14607: Index open performs version check on each segment, ignores indexCreatedVersionMajor
1 parent 3bc67d6 commit dd70ed5

File tree

4 files changed

+50
-23
lines changed

4 files changed

+50
-23
lines changed

lucene/CHANGES.txt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -131,6 +131,8 @@ Other
131131
* GITHUB#14761: Use more Comparators for PriorityQueue implementations. (Simon Cooper)
132132
* GITHUB#14817: Refactor some complex uses of PriorityQueue to use Comparators. (Simon Cooper)
133133

134+
* GITHUB#14607: Index open performs version check on each segment, ignores indexCreatedVersionMajor (Rahul Goswami)
135+
134136
======================= Lucene 10.4.0 =======================
135137

136138
API Changes

lucene/backward-codecs/src/test/org/apache/lucene/backward_index/TestAncientIndicesCompatibility.java

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@
4545
import org.apache.lucene.tests.util.LuceneTestCase;
4646
import org.apache.lucene.tests.util.TestUtil;
4747
import org.apache.lucene.util.IOUtils;
48+
import org.apache.lucene.util.Version;
4849

4950
public class TestAncientIndicesCompatibility extends LuceneTestCase {
5051
static final Set<String> UNSUPPORTED_INDEXES;
@@ -199,7 +200,7 @@ public void testUnsupportedOldIndexes() throws Exception {
199200
checker.setInfoStream(new PrintStream(bos, false, UTF_8));
200201
checker.setLevel(CheckIndex.Level.MIN_LEVEL_FOR_INTEGRITY_CHECKS);
201202
CheckIndex.Status indexStatus = checker.checkIndex();
202-
if (version.startsWith("8.") || version.startsWith("9.")) {
203+
if (getVersion(version).onOrAfter(Version.fromBits(8, 6, 0))) {
203204
assertTrue(indexStatus.clean);
204205
} else {
205206
assertFalse(indexStatus.clean);
@@ -217,6 +218,18 @@ public void testUnsupportedOldIndexes() throws Exception {
217218
}
218219
}
219220

221+
private Version getVersion(String version) {
222+
if (version.startsWith("5x")) {
223+
// couple of indices in unsupported_indices.txt start with "5x'
224+
return Version.fromBits(5, 0, 0);
225+
}
226+
String[] versionBitsStr = version.split("[.\\-]");
227+
return Version.fromBits(
228+
Integer.parseInt(versionBitsStr[0]),
229+
Integer.parseInt(versionBitsStr[1]),
230+
Integer.parseInt(versionBitsStr[2]));
231+
}
232+
220233
// #12895: test on a carefully crafted 9.8.0 index (from a small contiguous subset
221234
// of wikibigall unique terms) that shows the read-time exception of
222235
// IntersectTermsEnum (used by WildcardQuery)

lucene/backward-codecs/src/test/org/apache/lucene/backward_index/TestBasicBackwardsCompatibility.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -864,7 +864,7 @@ public void testFailOpenOldIndex() throws IOException {
864864
assertTrue(
865865
ex.getMessage()
866866
.contains(
867-
"This Lucene version only supports indexes created with major version "
867+
"This Lucene version only supports indexes with major version "
868868
+ Version.LATEST.major
869869
+ " or later"));
870870
// now open with allowed min version

lucene/core/src/java/org/apache/lucene/index/SegmentInfos.java

Lines changed: 33 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -328,7 +328,7 @@ public static final SegmentInfos readCommit(
328328
throw new IndexFormatTooOldException(
329329
input, magic, CodecUtil.CODEC_MAGIC, CodecUtil.CODEC_MAGIC);
330330
}
331-
format = CodecUtil.checkHeaderNoMagic(input, "segments", VERSION_74, VERSION_CURRENT);
331+
format = CodecUtil.checkHeaderNoMagic(input, "segments", VERSION_86, VERSION_CURRENT);
332332
byte[] id = new byte[StringHelper.ID_LENGTH];
333333
input.readBytes(id, 0, id.length);
334334
CodecUtil.checkIndexHeaderSuffix(input, Long.toString(generation, Character.MAX_RADIX));
@@ -346,30 +346,12 @@ public static final SegmentInfos readCommit(
346346
input);
347347
}
348348

349-
if (indexCreatedVersion < minSupportedMajorVersion) {
350-
throw new IndexFormatTooOldException(
351-
input,
352-
"Index created with Lucene "
353-
+ indexCreatedVersion
354-
+ ".x is not supported by Lucene "
355-
+ Version.LATEST
356-
+ ". This Lucene version only supports indexes created with major version "
357-
+ minSupportedMajorVersion
358-
+ " or later (found: "
359-
+ indexCreatedVersion
360-
+ ", minimum: "
361-
+ minSupportedMajorVersion
362-
+ "). To resolve this issue: (1) Re-index your data using Lucene "
363-
+ Version.LATEST.major
364-
+ ".x, or (2) Use an older Lucene version that supports your index format.");
365-
}
366-
367349
SegmentInfos infos = new SegmentInfos(indexCreatedVersion);
368350
infos.id = id;
369351
infos.generation = generation;
370352
infos.lastGeneration = generation;
371353
infos.luceneVersion = luceneVersion;
372-
parseSegmentInfos(directory, input, infos, format);
354+
parseSegmentInfos(directory, input, infos, format, minSupportedMajorVersion);
373355
return infos;
374356

375357
} catch (Throwable t) {
@@ -385,7 +367,12 @@ public static final SegmentInfos readCommit(
385367
}
386368

387369
private static void parseSegmentInfos(
388-
Directory directory, DataInput input, SegmentInfos infos, int format) throws IOException {
370+
Directory directory,
371+
DataInput input,
372+
SegmentInfos infos,
373+
int format,
374+
int minSupportedMajorVersion)
375+
throws IOException {
389376
infos.version = CodecUtil.readBELong(input);
390377
// System.out.println("READ sis version=" + infos.version);
391378
infos.counter = input.readVLong();
@@ -402,6 +389,7 @@ private static void parseSegmentInfos(
402389
}
403390

404391
long totalDocs = 0;
392+
405393
for (int seg = 0; seg < numSegments; seg++) {
406394
String segName = input.readString();
407395
byte[] segmentID = new byte[StringHelper.ID_LENGTH];
@@ -495,6 +483,30 @@ private static void parseSegmentInfos(
495483
+ infos.indexCreatedVersionMajor,
496484
input);
497485
}
486+
487+
int createdOrSegmentMinVersion =
488+
info.getMinVersion() == null
489+
? infos.indexCreatedVersionMajor
490+
: info.getMinVersion().major;
491+
492+
// version >=7 are expected to record minVersion
493+
if (info.getMinVersion() == null || info.getMinVersion().major < minSupportedMajorVersion) {
494+
throw new IndexFormatTooOldException(
495+
input,
496+
"Index has segments derived from Lucene version "
497+
+ createdOrSegmentMinVersion
498+
+ ".x and is not supported by Lucene "
499+
+ Version.LATEST
500+
+ ". This Lucene version only supports indexes with major version "
501+
+ minSupportedMajorVersion
502+
+ " or later (found: "
503+
+ createdOrSegmentMinVersion
504+
+ ", minimum supported: "
505+
+ minSupportedMajorVersion
506+
+ "). To resolve this issue re-index your data using Lucene "
507+
+ minSupportedMajorVersion
508+
+ ".x or later.");
509+
}
498510
}
499511

500512
infos.userData = input.readMapOfStrings();

0 commit comments

Comments
 (0)