Solr中的通配符查询错误

11

我使用Solr搜索文档,当尝试使用此查询"id:*"搜索文档时,我会收到查询解析器异常,告诉我它无法解析以*或?作为第一个字符的查询。

HTTP Status 400 - org.apache.lucene.queryParser.ParseException: Cannot parse 'id:*': '*' or '?' not allowed as first character in WildcardQuery

type Status report

message org.apache.lucene.queryParser.ParseException: Cannot parse 'id:*': '*' or '?' not allowed as first character in WildcardQuery

description The request sent by the client was syntactically incorrect (org.apache.lucene.queryParser.ParseException: Cannot parse 'id:*': '*' or '?' not allowed as first character in WildcardQuery).

有没有针对只使用 * 就能使其运行的补丁?或者这样的查询非常昂贵吗?

7个回答

15

如果您想获取所有文档,请在*:*上执行查询:

如果您想获取所有带有特定字段(例如id)的文档,请尝试id:[* TO *]


10

默认情况下,Lucene不允许您使用星号作为通配符在WildcardQueries语句的开头,因为这些查询非常昂贵,在大型索引上速度非常慢。

如果您使用的是Lucene QueryParser,则可以调用setAllowLeadingWildcard(true)来启用它。

如果您想要设置了某个特定字段的所有文档,最好通过编程查询或遍历索引,而不是使用QueryParser。您真正需要使用QueryParser来解析用户输入。


5
id:[a* TO z*] id:[0* TO 9*] etc.

我刚刚在我的索引上使用了lukeall,它有效了,因此应该也适用于使用标准查询解析器的Solr。我实际上并没有使用Solr。
在基本的Lucene中,你永远不会查询每个文档,这是有充分理由的,因为要查询一个文档,你必须使用new indexReader("DirectoryName")并将查询应用于它。因此,你完全可以跳过将查询应用于它,并使用indexReader方法numDocs()来获取所有文档的计数,以及document(int n)来检索任何文档。

4
如果您只是想获取所有文档,Solr支持*:*查询。这是我所知道的Solr允许您以*开头开始查询的唯一时间。我相信您可能已经在Solr管理页面中看到了默认查询。

如果您尝试使用*作为第一个字符进行更具体的查询,比如说id:*456,那么我见过的最好方法之一是将该字段索引两次。一次正常索引(字段名称:id),一次反转所有字符的索引(字段名称:reverse_id)。然后,您可以通过发送查询reverse_id:654来实现查询id:456。希望这样能让您理解。

您还可以在Solr用户组邮件列表中搜索,网址为http://www.mail-archive.com/solr-user@lucene.apache.org/,这样的问题经常出现。


2
以下是Solr的一个问题,请求能够配置默认的Lucene查询解析器。 https://issues.apache.org/jira/browse/SOLR-218 在这个问题中,您可以找到如何“修补”Solr的描述。此修改将允许您以*开头启动查询。

乔纳斯·索尔克:我基本上只更新了一个Java文件:SolrQueryParser.java。

public SolrQueryParser(IndexSchema schema, String defaultField) { 
    ... 
    setAllowLeadingWildcard(true); 
    setLowercaseExpandedTerms(true); 
    ... 
}

 ...

public SolrQueryParser(QParser parser, String defaultField, Analyzer analyzer) {
    ... 
    setAllowLeadingWildcard(true); 
    setLowercaseExpandedTerms(true);
    ... 
}

我不确定是否需要设置setLowercaseExpandedTerms...

1

我猜你用id:*只是想匹配所有文档,对吧?

我以前从未使用过solr,但在我的Lucene经验中,在摄取数据时,我们为每个文档添加了一个隐藏字段,然后当我们需要返回每条记录时,我们搜索该字段中的字符串常量,该常量对于每个记录都相同。

如果您无法在您的情况下添加这样的字段,则可以使用RegexQuery和正则表达式来匹配id字段中可以找到的任何内容。

编辑:实际上回答问题。我从未听说过修补程序可以使其正常工作,但如果可以使其正常工作,我会感到惊讶。请参见this question,了解无约束PrefixQuery可能会导致问题的原因。


1

实际上,我一直在使用一个解决方法。我会在ID后面添加一个字符,例如:A1、A2等。

有了这样的值在字段中,就可以使用查询id:A*进行搜索。

但是我很想找到是否存在真正的解决方案。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接