Repository navigation
Conversation
When no phrase qualifies for the pf boost (single-term queries, q=*:*), the pf sub-parser returns an empty BooleanQuery that was added to the main query as a SHOULD clause, defeating the single-clause MatchAllDocsQuery optimization. Omit it, and return early when there are no clauses to build a phrase from. Likewise skip a bq that parses to an empty query, e.g. one consisting only of stopwords. Co-Authored-By: Claude <svc-devxp-claude@slack-corp.com>
|
🤖 AI text below 🤖 (reviewed by Nick Shanin) @ispringer I prepared an optional test-only follow-up for your current version. It adds plain-token and fielded-only checks in both Selected suites passed on your head If useful, the test-only diff is one commit directly above your current head and can be taken without rewriting history: git switch SOLR-18625
git fetch https://github.com/nick-boss-tech/solr.git pr-5303-phrase-coverage-round-2
git merge --ff-only 07328d6973c4bb3385ca6d50bfe871f8808c1550 |
https://issues.apache.org/jira/browse/SOLR-18625
Description
When
pfis set and no phrase qualifies for the boost (single-term queries,q=*:*), eDisMax's pf sub-parser discards every phrase viaminClauseSizeand returns an emptyBooleanQueryrather thannull. That passed thephrase != nullguard and was added to the main query as an emptySHOULDclause (visible as()in the parsed query, e.g.+(subject:wireless) ()).It did not affect scoring, but it defeated the single-clause
MatchAllDocsQueryunwrapping inExtendedDismaxQParser.parse(), soq=*:*withpfset scored aBooleanQueryover every doc instead of reaching Solr'sMatchAllDocsQueryfast paths.The same happens with
bq: a boost query consisting only of stopwords (e.g.bq=text:a) parses to an emptyBooleanQueryand was added unchecked, with the same effect onq=*:*.Split out from #4652 (closed), where the pf part was agreed to be safe on its own; the bq part is the same fix applied to the other path that can add an empty clause.
Solution
In
addShingledPhraseQueries:q=subject:foo), avoiding creating a sub-parser and analyzing an empty phrase per pf slop group.In
getBoostQueries, skip a boost query that parses to an empty query.No ranking change.
Co-authored with Claude Code (Opus 5.5).
Tests
TestExtendedDismaxParser.testNoEmptyPhraseBoostClause(new):q=wireless→ no pf boost and no empty()clause (fails without the fix).q=wi-fi(WordDelimiter splits into two tokens) → phrase boost retained.TestExtendedDismaxParser.testMatchAllDocs(extended): now setspf,pf2,pf3and a stopword-onlybq, acrossq=*:*/q=*and bothsowvalues, and still expectsMatchAllDocsQuery(fails without the bq fix).Ran
TestExtendedDismaxParser,QueryEqualityTest,DisMaxRequestHandlerTest(all green), plus./gradlew tidyand./gradlew check -x test.Checklist
mainbranch../gradlew check.🤖 Generated with Claude Code