All findings · Lucene finding · LFV-1032 · memoryindex-javadoc-example-uses-removed-version-constructors

MemoryIndex's javadoc example calls new SimpleAnalyzer(version) and new QueryParser(version, ...), constructors removed in 5.0.0, so it does not compile

The only usage example in the MemoryIndex javadoc builds its analyzer with new SimpleAnalyzer(version) and its parser with new QueryParser(version, "content", analyzer). Both constructors were removed in 5.0.0, so the example has not compiled on any release since; dropping the two version arguments fixes it.

Summary

Priority
Low, rank 1248The only end-to-end example for the widely used, non-experimental MemoryIndex has failed to compile since 5.0.0 with no runtime effect.
Impact
minor
Since
5.0.0 (LUCENE-5859, 2014)introduced 2014-08-08 · over 12 years
Affected
every release 5.0.0-10.6.0 and main (javadoc only)
Status
documented
Found by
compiling javadoc examples against the jars (non-formal)

AI-assisted page: this finding was first signalled by code reading or testing and then checked with AI tools; the checks it went through, and what each found, are under Prior reports, history and checks. Not yet triaged by a human. Snapshot of 2026-11-06.

The finding in 30 seconds

One javadoc example names two constructors that no longer exist.

What you need to know first

  1. MemoryIndex (lucene-memory) holds exactly one document in memory. You add fields with an Analyzer and call search(query), which returns a score above 0 when the document matches. The highlighter and monitor modules build on it.
  2. Before 5.0, Lucene analyzers and the classic QueryParser took a Version ("matchVersion") argument. LUCENE-5859 removed those constructors: today it is new SimpleAnalyzer() and new QueryParser(field, analyzer).
Diagram of the bug. The MemoryIndex javadoc "Example Usage" program calls new SimpleAnalyzer(version) in line 1 and new QueryParser(version, "content", analyzer) in line 5. LUCENE-5859 removed both Version constructors in 5.0.0, leaving only SimpleAnalyzer() and QueryParser(String, Analyzer), so javac reports two errors on every release since 5.0.0 (4.10.4 still compiles it). Without the two version arguments the example compiles and prints "it's a match".
Line 1 and line 5 of the javadoc example call constructors that 5.0.0 removed; today only SimpleAnalyzer() and QueryParser(String, Analyzer) exist, so javac rejects both lines. Select the still to open it at full size. Generated with AI, checked against the code.

The finding, step by step

  1. You copy the 12-line "Example Usage" program from the MemoryIndex javadoc. It indexes two fields, parses +author:james +salmon~ +fish* manual~ and prints "it's a match".
  2. You add the 5 imports, declare version (the block never does) and compile against 10.6.0 or main. You expect it to compile and print "it's a match".
  3. Instead javac stops with 2 errors: in line 1, SimpleAnalyzer takes no arguments; in line 5, there is no QueryParser(Version, String, Analyzer). Both errors are about the number of arguments, so no type for version helps.
  4. Why: LUCENE-5859 removed both Version constructors in 5.0.0 and updated the module's test, but not this example. 4.10.4 still compiles it; 5.0.0 through 10.6.0 and main do not.
  5. Remove the two version arguments and the same 12 lines compile and print "it's a match" (score 1.3487055). Nothing wrong ever runs: it is a documentation fix.

Who is affected

Anyone who learns MemoryIndex from its javadoc and copies its only usage example, on every release since 5.0.0: two compile errors, with no configuration or special input involved. Nothing wrong ever runs, and javac lists the right constructors, so it is a Low documentation fix.

Mechanism, terms and numbers431 words

MemoryIndex is Lucene's one-document, in-memory index, often used to check whether a single text matches a query. Its class javadoc has one end-to-end "Example Usage" program: build a SimpleAnalyzer, add a "content" and an "author" field, parse +author:james +salmon~ +fish* manual~ with the classic QueryParser and print "it's a match". The program's first line is new SimpleAnalyzer(version) and its fifth is new QueryParser(version, "content", analyzer). LUCENE-5859 removed both Version-taking constructors (trunk 2014; released in 5.0.0 through the branch_5x backport) and left this example, so it has not compiled on any release since 5.0.0: with the Lucene imports, both calls pass the wrong number of arguments, whatever version is declared as. With the two version arguments dropped it compiles and prints "it's a match" on main and 10.5.2. Documentation only: no code is wrong and nothing wrong ever runs.

The example and the API on main 645d4fe14a20

MemoryIndex.java:144 opens "Example Usage"; the program is :147-158 inside <pre><code> (:146, :159):

Analyzer analyzer = new SimpleAnalyzer(version);                       // MemoryIndex.java:147
MemoryIndex index = new MemoryIndex();
index.addField("content", "Readings about Salmons and other select Alaska fishing Manuals", analyzer);
index.addField("author", "Tales of James", analyzer);
QueryParser parser = new QueryParser(version, "content", analyzer);    // MemoryIndex.java:151
float score = index.search(parser.parse("+author:james +salmon~ +fish* manual~"));
if (score > 0.0f) {
    System.out.println("it's a match");
} else {
    System.out.println("no match found");
}
System.out.println("indexData=" + index.toString());
  • SimpleAnalyzer.java:32: public SimpleAnalyzer() {} is the only constructor.
  • QueryParser.java:91 (classic): public QueryParser(String f, Analyzer a); the other two constructors are protected and take one argument (QueryParser(CharStream) :921, QueryParser(QueryParserTokenManager) :943).
  • The two errors are about the number of arguments, so with the Lucene imports no declaration of version makes the calls compile.
  • Nothing in the build checks it: code inside javadoc <pre> blocks is not compiled, and no {@snippet} is used anywhere under lucene/.

How it went stale

  1. 2012-09-12: Robert Muir's "code snippet improvements: fix out of date api usage and add syntax highlighting" (647b5091697 trunk, d8d5bf5e07d branch_4x) wrote both calls in their current form. They were valid; first release 4.0.0.
  2. 2014-08-08: LUCENE-5859 (9938a39a872, Ryan Ernst, "Remove Version from Analyzer constructors") removed SimpleAnalyzer(Version) and QueryParser(Version, String, Analyzer). In the memory module it changed only MemoryIndexTest.java (new QueryParser(TEST_VERSION_CURRENT, "foo", analyzer) became new QueryParser("foo", analyzer)), not MemoryIndex.java.
  3. On branch_4x (cb9beac7079, 4.10.0) the two constructors were only deprecated, so 4.10.x still compiles the example. The branch_5x backport 55594bad9b0 (LUCENE-5944, 2014-09-18) carried the removal into 5.0.0.
  4. Later commits (2014-2015 doclint fixes, LUCENE-9570 reformatting in 2021, #15573 in 2026) changed only the markup around the block.
Exposure and likelihood113 words
  • Who. Readers of the MemoryIndex class javadoc, the class's only end-to-end usage example. MemoryIndex is public and not marked @lucene.experimental; the highlighter (WeightedSpanTermExtractor, MemoryIndexOffsetStrategy) and the monitor (DocumentBatch) build on it. Users do quote this example: a 2016 java-user thread copies its addField lines.
  • What they get. Two javac errors, on every release from 5.0.0 to 10.6.0 and on main.
  • What they do not get. Any runtime effect: no wrong result, no exception at run time. javac names the valid constructors (SimpleAnalyzer(), QueryParser(String, Analyzer)), so the fix is quick once seen.
  • Priority. Low; likelihood "plausible" (anyone who copies the example hits it, every time).

Minimal repro

One JUnit class, one test, no randomness. It compiles the 12 example lines verbatim with the JDK's in-process compiler; the test wraps them in the five imports, a class and a method example(Version version) throws Exception (the throws because parse declares ParseException). Put it in the monitor module's tests, which have memory, analysis-common and queryparser, and run it with gradle.

TestMemoryIndexJavadocExample.java (one test, monitor module tests)79 lines
/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.apache.lucene.monitor;

import java.io.File;
import java.net.URI;
import java.util.List;
import javax.tools.DiagnosticCollector;
import javax.tools.JavaFileObject;
import javax.tools.SimpleJavaFileObject;
import javax.tools.ToolProvider;
import org.apache.lucene.tests.util.LuceneTestCase;

public class TestMemoryIndexJavadocExample extends LuceneTestCase {

  // Expected: the class-javadoc example compiles; actual: no SimpleAnalyzer(Version) /
  // QueryParser(Version, String, Analyzer).
  public void testClassJavadocExampleCompiles() throws Exception {
    String source =
        """
        import org.apache.lucene.analysis.Analyzer;
        import org.apache.lucene.analysis.core.SimpleAnalyzer;
        import org.apache.lucene.index.memory.MemoryIndex;
        import org.apache.lucene.queryparser.classic.QueryParser;
        import org.apache.lucene.util.Version;
        class Example {
          void example(Version version) throws Exception {
        Analyzer analyzer = new SimpleAnalyzer(version);
        MemoryIndex index = new MemoryIndex();
        index.addField("content", "Readings about Salmons and other select Alaska fishing Manuals", analyzer);
        index.addField("author", "Tales of James", analyzer);
        QueryParser parser = new QueryParser(version, "content", analyzer);
        float score = index.search(parser.parse("+author:james +salmon~ +fish* manual~"));
        if (score > 0.0f) {
            System.out.println("it's a match");
        } else {
            System.out.println("no match found");
        }
        System.out.println("indexData=" + index.toString());
          }
        }
        """;
    JavaFileObject unit =
        new SimpleJavaFileObject(URI.create("string:///Example.java"), JavaFileObject.Kind.SOURCE) {
          @Override
          public CharSequence getCharContent(boolean ignoreEncodingErrors) {
            return source;
          }
        };
    // Lucene modules sit on the module path under gradle and on the class path elsewhere: use both.
    String classPath = System.getProperty("java.class.path");
    String modulePath = System.getProperty("jdk.module.path");
    if (modulePath != null) {
      classPath = classPath + File.pathSeparator + modulePath;
    }
    DiagnosticCollector<JavaFileObject> diagnostics = new DiagnosticCollector<>();
    List<String> options =
        List.of("-classpath", classPath, "-d", createTempDir().toString(), "-proc:none");
    boolean compiled =
        ToolProvider.getSystemJavaCompiler()
            .getTask(null, null, diagnostics, options, null, List.of(unit))
            .call();
    assertTrue(diagnostics.getDiagnostics().toString(), compiled);
  }
}
Command
./gradlew :lucene:monitor:test --tests org.apache.lucene.monitor.TestMemoryIndexJavadocExample -Ptests.seed=DEADBEEF
Expected
With the imports and a declared version, the 12-line example compiles and, when run, prints "it's a match" (what a reader expects of an "Example Usage" block; Lucene does not compile javadoc code).
Observed
javac: SimpleAnalyzer "cannot be applied to given types" and "no suitable constructor found for QueryParser(Version,String,Analyzer)", with assertions on and off.

All files of this repro: repro/LFV-1032/

More files, environment, full output352 words

The test passes the example as a string to javax.tools and asserts that it compiles; on failure the message is javac's own diagnostics. The 12 lines are MemoryIndex.java:147-158 with &gt; decoded; a script checked them against the javadoc line for line. Single thread, public API only. The test shows that the two calls fail with the intended Lucene imports and this ordinary wrapper; it does not test the bare fragment, which needs some such wrapper on every version, 4.10.4 included.

It sits in lucene/monitor because the memory module's own tests have no analysis-common (for SimpleAnalyzer). The javac class path includes the module path, which gradle uses for Lucene's modules. The same file also fails against the 10.6.0, 10.5.2 and 9.12.3 release jars.

Regression test (optional): this same test with the two fixed lines. It guards the documented calls; it cannot notice a later edit of the javadoc itself, since Lucene does not compile javadoc code.

Environment

lucenemain 645d4fe14a20 (11.0.0-SNAPSHOT); 10.6.0, 10.5.2 and 9.12.3 fail the same way
jdkOpenJDK 25.0.3
osLinux aarch64 (the result does not depend on the platform)
Command (environment)
cp $REPRO/TestMemoryIndexJavadocExample.java $LUCENE/lucene/monitor/src/test/org/apache/lucene/monitor/
cd $LUCENE
./gradlew :lucene:monitor:test --tests org.apache.lucene.monitor.TestMemoryIndexJavadocExample -Ptests.seed=DEADBEEF
# assertions off: add -Ptests.asserts=false (same failure)

Observed output

# gradle, main 645d4fe14a20, seed DEADBEEF, assertions on (off: the same two errors)
TestMemoryIndexJavadocExample > testClassJavadocExampleCompiles FAILED
    java.lang.AssertionError: [/Example.java:8: error: constructor SimpleAnalyzer in class org.apache.lucene.analysis.core.SimpleAnalyzer cannot be applied to given types;
    Analyzer analyzer = new SimpleAnalyzer(version);
                        ^
      required: no arguments
      found:    org.apache.lucene.util.Version
      reason: actual and formal argument lists differ in length, /Example.java:12: error: no suitable constructor found for QueryParser(org.apache.lucene.util.Version,java.lang.String,org.apache.lucene.analysis.Analyzer)
    QueryParser parser = new QueryParser(version, "content", analyzer);
                         ^
        constructor org.apache.lucene.queryparser.classic.QueryParser.QueryParser(java.lang.String,org.apache.lucene.analysis.Analyzer) is not applicable
          (actual and formal argument lists differ in length)
        constructor org.apache.lucene.queryparser.classic.QueryParser.QueryParser(org.apache.lucene.queryparser.charstream.CharStream) is not applicable
          (actual and formal argument lists differ in length)
        constructor org.apache.lucene.queryparser.classic.QueryParser.QueryParser(org.apache.lucene.queryparser.classic.QueryParserTokenManager) is not applicable
          (actual and formal argument lists differ in length)]
        at __randomizedtesting.SeedInfo.seed([DEADBEEF:9A7EBD6A0F12FB11]:0)
1 test completed, 1 failed

# Example.java:8 and :12 are lines 1 and 5 of the block (MemoryIndex.java:147 and :151)
# with the fix and the fixed text in the test: BUILD SUCCESSFUL, 1 test (assertions on and off)

Why it looks unintended

  • The text comes from a 2012 commit titled "fix out of date api usage": it is meant to track the API, and it compiled on 4.0.0-4.10.4.
  • LUCENE-5859 removed the constructors and updated the module's test, not this file; its discussion never mentions the example.
  • Upstream fixes javadoc examples that do not work (#12666, fixed by #12693; LUCENE-9046).
The full argument165 words
  • Meant to track the API. 647b5091697 / d8d5bf5e07d (Robert Muir, 2012-09-12), "code snippet improvements: fix out of date api usage and add syntax highlighting", wrote today's text. 4.10.4 compiles it.
  • An oversight, not a decision. 9938a39a872 (LUCENE-5859) touched MemoryIndexTest.java but not MemoryIndex.java; the 55 comments of #6921 never mention MemoryIndex; MIGRATE.md and CHANGES.txt say nothing about keeping the example.
  • Precedent. #12666 (the Analyzer class-doc example "does not work") was closed by #12693, "chore: update the Javadoc example in Analyzer" (2023); CHANGES.txt: "LUCENE-9046: Fix wrong example in Javadoc of TermInSetQuery".
  • Not a placeholder. version is undeclared, which a reader can fill in; but with the Lucene imports no declaration of version fixes a call to a constructor that does not exist.
  • What a reader can expect. Lucene does not compile javadoc code, so nothing guarantees that this block compiles. The claim is what a reader reasonably expects of an "Example Usage" block: that, with the imports added and version declared, it calls API that exists.
The devil's-advocate check139 words

The case for "intended": the block is an uncompiled illustrative fragment (no imports, version never declared, no snippet tooling in the build) inside a class javadoc full of 2005-2006 prose (the Nux XQuery example, dead today.java.net links); the error is loud and names the right constructors; and a maintainer edited this exact block in January 2026 (#15573) without touching the calls.

Why it fails: #15573 ("Replace prettyprint with code tag for prism") changed 252 files mechanically, as the 2014-2015 doclint and 2021 reformatting commits also changed only the markup. With the Lucene imports no declaration of version makes the calls compile: they name API that does not exist. Every reviewer, including two from another model family (OpenAI GPT-5.6), and the adjudication rejected the argument. What remains true is that the impact is small, which is why it is Low.

Suggested fix

Recommended Drop the two Version arguments (validated)

Javadoc only: change line 1 of the example to new SimpleAnalyzer() and line 5 to new QueryParser("content", analyzer). Validated with gradle: the example then compiles, and the memory module's 51 tests and its javadoc build pass.

All options and trade-offs3 options ยท 415 words

One fix was validated with gradle in a scratch worktree of 645d4fe14a20; the alternatives were not run.

Drop the two Version arguments (validated) (recommended)

Exactly the change LUCENE-5859 made to the memory module's test. The example then uses the current constructors and no longer needs the undeclared version at all. 1 file, +2/-2, javadoc only.

--- a/lucene/memory/src/java/org/apache/lucene/index/memory/MemoryIndex.java
+++ b/lucene/memory/src/java/org/apache/lucene/index/memory/MemoryIndex.java
@@ -144,11 +144,11 @@
  * <p><b>Example Usage</b> <br>
  *
  * <pre><code class="language-java">
- * Analyzer analyzer = new SimpleAnalyzer(version);
+ * Analyzer analyzer = new SimpleAnalyzer();
  * MemoryIndex index = new MemoryIndex();
  * index.addField("content", "Readings about Salmons and other select Alaska fishing Manuals", analyzer);
  * index.addField("author", "Tales of James", analyzer);
- * QueryParser parser = new QueryParser(version, "content", analyzer);
+ * QueryParser parser = new QueryParser("content", analyzer);
  * float score = index.search(parser.parse("+author:james +salmon~ +fish* manual~"));
  * if (score &gt; 0.0f) {
  *     System.out.println("it's a match");

Trade-offs

  • No behaviour, API or test change; trivially reviewable.
  • Leaves the rest of the 2005-2006 prose (dead links, the XQuery block, JDK 1.5 profiling advice) alone.

What the checks validated

  • Scratch worktree of 645d4fe14a20, gradle --offline, OpenJDK 25.0.3, seed DEADBEEF; the test in the monitor module's tests.
  • Stock: the one-test repro fails with assertions on and off (both javac errors).
  • With the diff: a script confirmed the patched javadoc block equals the fixed text line for line; the test with that text passes with assertions on and off.
  • :lucene:memory:test, the whole module: 51 tests (TestMemoryIndex 30, TestMemoryIndexAgainstDirectory 16, TestSlicedIntBlockPool 5), 0 failures, 0 skipped.
  • :lucene:memory:renderJavadoc, checkGoogleJavaFormat and ecjLintMain pass; with the test file in place, :lucene:monitor:checkGoogleJavaFormat, ecjLintTest and forbiddenApisTest pass.
  • Earlier runs: the corrected example runs and prints "it's a match" (score 1.3487055) on main with -ea and -da and on 10.5.2; the cross-model reviewer ran 46 existing MemoryIndex tests against the patched source, all passing.
  • Not run: the whole :lucene:monitor:test or ./gradlew check.

Also add the imports (alternative, not run)

Add the five import lines so the block can be pasted as is. More text in a class javadoc, and other Lucene examples omit imports too; not needed to fix the defect.

Trade-offs

Longer example; same compile check as the recommended option.

What the checks validated

Not run.

Compile javadoc examples in the build (not recommended here) (not run)

Move examples to {@snippet} with compiled source files, or compile <pre> blocks in a build check. The only thing that would stop this class of drift.

Trade-offs

A build-tooling change far beyond a two-line docs fix; out of scope here.

What the checks validated

Not run.

How it was found

No formal method. A pass compiled the code examples in the javadocs of the memory, monitor, suggest, facet and join modules against the current jars, and this one failed. A scan of 158 builds' jars dated the two constructors; verifiers, reviewers from another model family (OpenAI GPT-5.6) and an adjudication confirmed it.

The method in full95 words
  • Lead. A first pass over javadoc examples compiled the block against the stock main jars and got both constructor errors.
  • Hunt. The finder re-ran the lead, extracted the block mechanically from the source, and checked with a java.lang.classfile scan in which of 158 builds (every cached release 1.9.1-10.5.2, the 10.6.0 release candidate and main) the example's API members exist; the boundaries were cross-checked by compiling each release's own javadoc text with javac. It then wrote the one-test repro.
  • Tier. Non-formal: compiling documentation code and scanning jars for API members, not a check against exact semantics.

Prior reports, history and checks

Prior reports

No prior report: GitHub issues, PRs and commits (with the migrated JIRA archive), four mailing lists, downstream repositories, Stack Exchange and the web were searched; none of the seven open PRs that touch MemoryIndex.java edits the example.

Searches5 searches

Closest hits, none this bug: #6586 (LUCENE-5523, 2014, closed Cannot Reproduce) quotes the example as the repro of a TokenStream-contract report on 4.7, when it still compiled; #6921 (LUCENE-5859) and #7006 (LUCENE-5944) made it stale without mentioning it; #5862, #10610 and #15573 edited only the markup around it; #8777 fixed an HTML entity above it; #16821 (open) is the same kind of defect in the highlight package docs; #15225, #14257, #4624 and #9527 are generic javadoc discussions; a 2016 java-user thread quotes the example's addField lines, not about compiling. Tracking issue #16937 does not name it.

What was searched, when, and what turned up
WhereWhenHowFound
Scripted searches2026-10-2916 GitHub issue/PR, 3 commit, 2 downstream, 20 mailing-list, 4 JIRA-archive and 6 web queries, with exact example phrases ("Readings about Salmons", SimpleAnalyzer(version), salmon~) and LUCENE-58591,098 distinct hits; the 3 high-overlap hits are all from before 5.0
GitHub, manual2026-10-2935 manual searches: 26 on apache/lucene (exact example phrases, API and issue names, author listings, and every issue/PR created or updated since 2026-10-27), 3 on downstream repositories, 6 on the old lucene-solr repository and GitHub-wideno report
Open PRs2026-10-29changed files of all 415 open apache/lucene PRs; patches of the seven that touch MemoryIndex.java (#16847, #14716, #14475, #13948, #13525, #13342, #486)none edits the example lines
Mailing lists, JIRA archive, Stack Exchange, web2026-10-2928 lists.apache.org queries (java-user@, dev@, issues@, general@), 5 JQL queries, 3 Stack Overflow threads, 7 web searchesa 2016 java-user thread quoting the addField lines; nothing about compiling
History and upstream main2026-11-01git log -S / -L on the block in the full-history clone; upstream main f815e679bf6cboth calls unchanged upstream; no commit since 645d4fe14a20 touched the file

History

Stale since 5.0.0: LUCENE-5859 (9938a39a872, 2014-08-08; released through the branch_5x backport 55594bad9b0) removed both constructors. 4.10.4 compiles the example; every release from 5.0.0 to 10.6.0 and main fail.

Versions tested7 rows
  • Example written by 647b5091697 / d8d5bf5e07d (2012-09-12, first released in 4.0.0); git blame on main still points there for both lines.
  • Introduced by 9938a39a872 (LUCENE-5859, Ryan Ernst, 2014-08-08, trunk; first released in 6.0.0). 5.0.0 got the removal through the branch_5x backport 55594bad9b0 (LUCENE-5944, Robert Muir, 2014-09-18), so 5.0.0 is the first affected release. On branch_4x, cb9beac7079 (4.10.0) only deprecated both constructors.
  • Same text everywhere: after stripping markup the example code is identical in all 121 release tags 4.0.0-10.5.2 of the history clone and on main; a bytecode scan of 158 builds finds both constructors in 4.0.0-4.10.4 and in no build from 5.0.0 to main.
  • Not fixed upstream: upstream main f815e679bf6c (2026-11-01) and branch_11x still have both calls at lines 147 and 151; branch_10_6 and the 10.6.0 tag at 115 and 119. Before 4.0.0 the example had an older, different form; not claimed.
Versions and branches executed, with results
Version or commitVerdictResult
main 645d4fe14a20; upstream main f815e679bf6c affectedrepro fails with -ea and -da (standalone and gradle); upstream read: same two lines
10.6.0 affectedfails 1/1 (release jars); the finder's earlier run used jars built at the same commit 4ae946e5a9b, labelled 10.6.0-SNAPSHOT: also fails
10.5.2, 9.12.3 affectedfail 1/1
5.0.0, 6.0.0, 8.11.4 affectedfail with the same two errors (port that only changes the LuceneTestCase import)
5.0.0 to 10.5.2 (all tags) affectedread: same example text; both constructors absent from every build
4.10.4 not affectedthe verbatim example compiles (constructors deprecated, not removed)
4.0.0 to 4.10.3 not affectedread: both constructors present; 4.0.0's text compiles with javac

Independent checks

Seven independent looks agree it is real and documentation-only: the finder, verifiers, reviewers from another model family (OpenAI GPT-5.6), the adjudication, and a credibility audit. This doc's brief re-ran the repro with gradle and validated the fix.

Checks and verdicts200 words

Each check ran separately; the intended-lens cross-model review could not run code, and a separate run re-ran the repro.

Each independent check and its verdict
CheckVerdictWhat it found
Finder reproduced (doc)Repro fails on main (-ea, -da), the 10.6.0 release candidate, 10.5.2 and 9.12.3; fix check passes.
Refute lens (OpenAI GPT-5.6) real, highOwn tests fail on main ea57360912ed (same javadoc text); with the fix the block compiles, runs and prints "it's a match"; 46 existing MemoryIndex tests pass.
Independent reproducer realOwn test, run with Version.LATEST: fails on main (-ea, -da), 10.5.2, 9.12.3; control without the two arguments prints "it's a match".
Intended lens (OpenAI GPT-5.6) real, medium (reading only)Could not execute; a separate run re-ran the repro on main (fails).
Devil's advocate real, LowArgued "illustrative fragment" and rejected it; runs on main and 10.5.2 fail.
Adjudication confirmed, highRe-ran the repro on main (fails); documentation defect, severity low.
Credibility audit confirmed, LowRe-runs on main fail; minor, not noise (removed-API call in the only example).
This doc's brief real; fix validatedGradle before and after in a scratch worktree; standalone on main, 10.6.0, 10.5.2, 9.12.3.

Diagram file

The diagram as a still image, generated with AI and checked against the code. It is under 10 MB, the limit for a GitHub attachment.

Sources and provenance

Finding record, Lucene and upstream sources, repro files and diagram notes1,207 words

Finding record

LFV-1032, snapshot of 2026-11-06

Registry title
MemoryIndex's class javadoc example calls new SimpleAnalyzer(version) and new QueryParser(version, "content", analyzer), constructors removed in 5.0.0 (LUCENE-5859), so the example does not compile on any release since 5.0.0 (documentation defect)
Area
memory / MemoryIndex (class javadoc example)
Priority
Low, rank 1248: The only end-to-end example for the widely used, non-experimental MemoryIndex has failed to compile since 5.0.0 with no runtime effect.
Impact class
minor
Impact note
Documentation only, with no runtime effect: a developer who starts from MemoryIndex's only end-to-end usage example (the class javadoc 'Example Usage') and copies it gets two compile errors on every release since 5.0.0, whatever they declare version as; dropping the two Version arguments fixes it, and no configuration, scale or special input is involved.
Summary
The MemoryIndex class javadoc shows an 'Example Usage' program that adds two fields to a MemoryIndex, parses '+author:james +salmon~ +fish* manual~' and prints "it's a match". Its first and fifth lines call new SimpleAnalyzer(version) and new QueryParser(version, "content", analyzer), but both Version-taking constructors were removed in 5.0.0 (LUCENE-5859), so the example has not compiled on any release since then, whatever type version is given. With new SimpleAnalyzer() and new QueryParser("content", analyzer) the same example compiles and prints "it's a match" on main and 10.5.2, so only the javadoc is wrong.
Introduced
9938a39a872 (trunk, svn r1616901; LUCENE-5859 'Remove Version from Analyzer constructors', migrated as #6921, by Ryan Ernst (rjernst), author date = commit date 2014-08-08): it removed SimpleAnalyzer(Version) (leaving SimpleAnalyzer()) and the classic QueryParser(Version, String, Analyzer) (leaving QueryParser(String, Analyzer)) and updated MemoryIndexTest.java, but not the MemoryIndex.java class javadoc example. The released 5.x line got the same removal through the branch_5x bulk backport 55594bad9b0 (LUCENE-5944, Robert Muir, 2014-09-18, svn r1626055); 9938a39a872 itself is first released in 6.0.0. On branch_4x, cb9beac7079 (LUCENE-5859, Ryan Ernst, 2014-08-21, first released in 4.10.0) only deprecated both constructors, so 4.10.x still compiles the example. The two calls were written by 647b5091697 (trunk) / d8d5bf5e07d (branch_4x) ('code snippet improvements: fix out of date api usage and add syntax highlighting', Robert Muir, 2012-09-12, first released in 4.0.0) and were valid then [read: git log, show, blame and tag --contains in the full-history clone and a Lucene clone; exec: release runs, see affected_versions] (2014-08-08 (9938a39a872, trunk, author date = commit date); released through the branch_5x backport 55594bad9b0 of 2014-09-18)
First affected version
5.0.0 [exec] (the verbatim example compiles on 4.10.4 [exec], where both constructors still exist as deprecated, and fails on 5.0.0 with identical example text)
Affected versions
every release from 5.0.0 to 10.6.0 (RC1 4ae946e5a9b), branch_10x 657014b3c579, branch_11x f85446cb1af1 and main 645d4fe14a20; not fixed upstream (recheck 2026-10-29: both calls are still at lines 147 and 151 on main and branch_11x and at lines 115 and 119 on branch_10x and branch_10_6; the latest commit touching the file on main, bfe5c847d3c4 (#16383, author date 2026-07-27), does not change them). [exec: 4.10.4 compiles; 5.0.0, 6.0.0, 8.11.4, 9.12.3, 10.5.2, the 10.6.0 RC1 jars and main (-ea and -da) fail with the same two javac errors; the pre-9.0 runs use an import-only port of the test (LuceneTestCase package) and the junitcore runner] [read: a bytecode scan of 158 builds (every cached release 1.9.1-10.5.2, the 10.6.0 RC1 and main) finds SimpleAnalyzer(Version) and QueryParser(Version, String, Analyzer) in 4.0.0-4.10.4 and in no build from 5.0.0 to main; the example code (markup stripped) is identical in all 121 release tags 4.0.0-10.5.2 of the history clone (the 8.9.0-8.11.x tags are not in it) and on main]. branch_10x and branch_11x: text only (that jar set has no memory or queryparser jar). Before 4.0.0 the example had an older, different form (not claimed). Not new in 10.6. Caveat: all runs used JDK 25 on Linux aarch64.
Status
documented (brief, checks and a per-finding doc exist)
Verification
Confirmed by AI-run checks: an independent repro, a cross-model review that agreed, an intended-behaviour check, a prior-report search and a skeptical audit; not yet triaged by a person.
Found by
non-formal
Upstream and prior reports
none found (searched 2026-10-29; the finder's, the independent reproduction's, the intended-behaviour check's and the adjudication's searches agree): 125 queries, among them scripted searches over GitHub issues, PRs and commits, downstream repositories, the dev@, java-user@, issues@ and general@ lists, the JIRA archive and the web, 35 manual GitHub search phrasings (apache/lucene, the old lucene-solr repository, three downstream search-engine repositories and GitHub-wide), the changed files of all 415 open apache/lucene PRs and the patches of the seven that touch MemoryIndex.java (#16847, #14716, #14475, #13948, #13525, #13342, #486; none edits the example lines), 28 direct lists.apache.org queries, 5 JIRA-archive queries, Stack Exchange, and git log -S / -L on the example in the full history. Read but not the same bug: #6586 (LUCENE-5523, 2014, closed Cannot Reproduce) quotes the example as the reproduction of a TokenStream-contract report on 4.7, when it still compiled; #6921 (LUCENE-5859) and #7006 (LUCENE-5944), the changes that made it stale, never mention MemoryIndex's example; #5862 (LUCENE-4797), #10610 (LUCENE-9570) and #15573 later edited the markup around the example and left the code; #8777 (LUCENE-7726) fixed an HTML entity above it; #16821 (open, by hidingmyname, 2026-10-12) is the same kind of defect in the highlight package docs; #15225, #14257, #4624 and #9527 are generic javadoc or snippet discussions that name no MemoryIndex example; a 2016 java-user thread quotes the example's addField lines without mentioning the constructors. Recheck: upstream main still 645d4fe14a20; both calls still present on main, branch_11x, branch_10x and branch_10_6; none of the 63 issues and PRs updated since 2026-10-27 (newest #16940) names MemoryIndex, SimpleAnalyzer(version) or QueryParser(version, and none of their 25 PRs changes MemoryIndex.java. Tracking issue #16937 does not name it.
Lucene commit tested
main 645d4fe14a20 (2026-10-28): the one-test repro fails with assertions on and off (standalone, and gradle with the file in the monitor module's tests); it fails against the 10.6.0, 10.5.2 and 9.12.3 release jars; the version-history runs ran 4.10.4 (compiles) and 5.0.0, 6.0.0 and 8.11.4 (the same two errors); the fix was validated with gradle in a scratch worktree of 645d4fe14a20. Upstream main f815e679bf6c (2026-11-01) was read, not run: both calls are unchanged and no commit since 645d4fe14a20 touched the file.

Lucene and upstream sources

Finding record
  • lucene/memory/src/java/org/apache/lucene/index/memory/MemoryIndex.java:144-159 (class javadoc 'Example Usage', the stale calls at :147 and :151; the class carries no @lucene.experimental tag); lucene/analysis/common/src/java/org/apache/lucene/analysis/core/SimpleAnalyzer.java:32 (the only constructor, SimpleAnalyzer()); lucene/queryparser/src/java/org/apache/lucene/queryparser/classic/QueryParser.java:91 (QueryParser(String f, Analyzer a))
The finding in 30 seconds
  • lucene/memory/src/java/org/apache/lucene/index/memory/MemoryIndex.java (lines 144-159, 147, 151, 201)
  • lucene/analysis/common/src/java/org/apache/lucene/analysis/core/SimpleAnalyzer.java:32
  • lucene/queryparser/src/java/org/apache/lucene/queryparser/classic/QueryParser.java:91, :921, :943
Who is affected
  • lucene/memory/src/java/org/apache/lucene/index/memory/MemoryIndex.java:201 (public class, no class-level @lucene.experimental)
  • lucene/highlighter/src/java/org/apache/lucene/search/highlight/WeightedSpanTermExtractor.java (new MemoryIndex)
  • lucene/highlighter/src/java/org/apache/lucene/search/uhighlight/MemoryIndexOffsetStrategy.java (new MemoryIndex)
  • lucene/monitor/src/java/org/apache/lucene/monitor/DocumentBatch.java (new MemoryIndex)
Minimal repro
  • lucene/queryparser/src/java/org/apache/lucene/queryparser/classic/QueryParserBase.java:129 (parse(String) throws ParseException)
Why it looks unintended
  • lucene/CHANGES.txt:6147 (LUCENE-9046)
History
  • a Lucene clone: git tag --contains 55594bad9b0 (first release tag 5.0.0), 9938a39a872 (first release tag 6.0.0); releases/lucene-solr/5.0.0 MemoryIndex.java:129, :133; releases/lucene/10.6.0 MemoryIndex.java:115, :119; origin/branch_11x :147, :151; origin/branch_10_6 :115, :119

Other statements trace to the hunt's working files (models, logs, reviews and briefs), which are not published.

Repro files

About the diagrams

Made in parallel with this doc from the mechanism in the brief; the PNG is the summary frame.

Built 2026-11-06 from the hunt's record of this finding and its doc file. Lucene main under test in this hunt: ea57360912ed. Every listed finding was re-run on Lucene main e1faeba08bde on 2026-11-02.