Skip to main content
The query parser module translates human-readable query strings into Lucene Query objects. It supports a rich syntax for boolean logic, phrase search, field targeting, wildcards, fuzzy matching, and more.

Dependency

<dependency>
  <groupId>org.apache.lucene</groupId>
  <artifactId>lucene-queryparser</artifactId>
  <version>${lucene.version}</version>
</dependency>

Classic QueryParser syntax

QueryParser accepts queries with the following syntax:
SyntaxExampleMeaning
Field targetingtitle:luceneSearch the title field
Boolean ANDlucene AND searchBoth terms required
Boolean ORlucene OR searchEither term
Boolean NOTlucene NOT javaExclude term
Required/prohibited+lucene -javaRequire/exclude terms
Phrase"apache lucene"Exact phrase
Wildcardluce* or luc?neGlob-style wildcard
Fuzzylucene~ or lucene~1Edit-distance fuzzy
Boostlucene^2 searchBoost a term’s relevance
Rangedate:[2020-01-01 TO 2024-01-01]Inclusive range
Grouping(lucene OR solr) AND searchGrouped sub-query
QueryParser is not thread-safe. Create a new instance per thread or use StandardQueryParser, which is thread-safe.

QueryParser constructor and parse()

import org.apache.lucene.queryparser.classic.QueryParser;
import org.apache.lucene.analysis.standard.StandardAnalyzer;
import org.apache.lucene.search.Query;

// First argument is the default field; second is the analyzer.
QueryParser parser = new QueryParser("content", new StandardAnalyzer());

// Parse returns a Query ready to pass to IndexSearcher.search().
Query q = parser.parse("title:lucene AND \"full text search\"^2");
Key configuration methods on QueryParser / QueryParserBase:
  • setDefaultOperator(QueryParser.Operator.AND) — change the implicit operator from OR to AND
  • setAllowLeadingWildcard(true) — allow *term and ?term patterns (expensive)
  • setFuzzyMinSim(float) — set the minimum similarity for fuzzy queries
  • setDateResolution(DateTools.Resolution) — configure date-range parsing resolution

StandardQueryParser

StandardQueryParser is the flexible query framework alternative. It parses the same syntax as QueryParser but is built on a configurable processor pipeline and is thread-safe.
import org.apache.lucene.queryparser.flexible.standard.StandardQueryParser;

StandardQueryParser parser = new StandardQueryParser(new StandardAnalyzer());
Query q = parser.parse("title:lucene AND released:[2020 TO 2024]", "content");

SimpleQueryParser

SimpleQueryParser is designed for user-facing search boxes. It is lenient — malformed input never throws an exception — and supports a reduced but intuitive syntax.
import org.apache.lucene.queryparser.simple.SimpleQueryParser;
import org.apache.lucene.analysis.standard.StandardAnalyzer;
import java.util.HashMap;
import java.util.Map;

// Map of field name -> boost weight
Map<String, Float> fields = new HashMap<>();
fields.put("title", 2.0f);
fields.put("body", 1.0f);

SimpleQueryParser parser = new SimpleQueryParser(new StandardAnalyzer(), fields);
Query q = parser.parse("apache lucene +search");
SimpleQueryParser supports + (required), - (prohibited), "phrases", * prefix wildcard, ~ fuzzy, and | OR.

Escaping special characters

The following characters have special meaning in the classic query syntax and must be escaped with a backslash when used as literals:
+ - && || ! ( ) { } [ ] ^ " ~ * ? : \ /
To escape programmatically, use QueryParser.escape():
String userInput = "price: $100 (USD)";
String escaped = QueryParser.escape(userInput);
// escaped -> "price\:\ \$100\ \(USD\)"
Query q = parser.parse(escaped);
1

Open the index

Directory dir = FSDirectory.open(Paths.get("/path/to/index"));
DirectoryReader reader = DirectoryReader.open(dir);
IndexSearcher searcher = new IndexSearcher(reader);
2

Parse the query string

Analyzer analyzer = new StandardAnalyzer();
QueryParser parser = new QueryParser("body", analyzer);
parser.setDefaultOperator(QueryParser.Operator.AND);
Query query = parser.parse("apache lucene search");
3

Execute and display results

TopDocs hits = searcher.search(query, 10);
StoredFields storedFields = searcher.storedFields();
for (ScoreDoc sd : hits.scoreDocs) {
  Document doc = storedFields.document(sd.doc);
  System.out.println(sd.score + " " + doc.get("title"));
}
reader.close();
For programmatically constructed queries—such as those built by your application rather than typed by a user—prefer the query API directly (TermQuery, BooleanQuery, etc.) over parsing a string. Parsing has overhead and the string format is not a stable API.

Build docs developers (and LLMs) love