如何通过solrj分词并查询进行查询

Solr 学习(5) —- Solr查询语法和参数 - 奔跑的面包 - ITeye技术网站
博客分类:
1、查询地址
建立好solr的索引后,可以通过管理界面进行查询。
要尝试多个查询方法的话,可以进入full interface模式,并勾选debug选项,像下面这样
随便进行一个查询,如输入 hi ,通过返回的页面的debug项中,就可以看到solr进行查询的很多相关信息
&lst name="debug"&
&str name="rawquerystring"&hi&/str&
&str name="querystring"&hi&/str&
&str name="parsedquery"&text:hi&/str&
&str name="parsedquery_toString"&text:hi&/str&
&lst name="explain"&
&str name="1474002"&
8.481748 = (MATCH) fieldWeight(text:hi in 207626), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=207626)
&str name="556830"&
8.481748 = (MATCH) fieldWeight(text:hi in 794169), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=794169)
&str name="735197"&
8.481748 = (MATCH) fieldWeight(text:hi in 901810), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=901810)
&str name="2142779"&
8.481748 = (MATCH) fieldWeight(text:hi in 1584789), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=1584789)
&str name="182950"&
8.481748 = (MATCH) fieldWeight(text:hi in 1862408), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=1862408)
&str name="155112"&
8.481748 = (MATCH) fieldWeight(text:hi in 1967709), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=1967709)
&str name="2223440"&
8.481748 = (MATCH) fieldWeight(text:hi in 2181479), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=2181479)
&str name="2236992"&
8.481748 = (MATCH) fieldWeight(text:hi in 2199957), product of: 1.0 = tf(termFreq(text:hi)=1) 8.481748 = idf(docFreq=1336, maxDocs=.0 = fieldNorm(field=text, doc=2199957)
&str name="2231513"&
7.4968767 = (MATCH) fieldWeight(text:hi in 2179538), product of: 1.4142135 = tf(termFreq(text:hi)=2) 8.481748 = idf(docFreq=1336, maxDocs=.625 = fieldNorm(field=text, doc=2179538)
&str name="17885"&
5.9975014 = (MATCH) fieldWeight(text:hi in 2009670), product of: 1.4142135 = tf(termFreq(text:hi)=2) 8.481748 = idf(docFreq=1336, maxDocs=.5 = fieldNorm(field=text, doc=2009670)
&str name="QParser"&LuceneQParser&/str&
&lst name="timing"&
&double name="time"&8.0&/double&
&lst name="prepare"&
&double name="time"&1.0&/double&
&lst name="org.apache.ponent.QueryComponent"&
&double name="time"&1.0&/double&
&lst name="org.apache.ponent.FacetComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.MoreLikeThisComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.HighlightComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.StatsComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.DebugComponent"&
&double name="time"&0.0&/double&
&lst name="process"&
&double name="time"&7.0&/double&
&lst name="org.apache.ponent.QueryComponent"&
&double name="time"&5.0&/double&
&lst name="org.apache.ponent.FacetComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.MoreLikeThisComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.HighlightComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.StatsComponent"&
&double name="time"&0.0&/double&
&lst name="org.apache.ponent.DebugComponent"&
&double name="time"&2.0&/double&
同时 在查询的头部信息中,也可以看到查询语法和参数是否被正确解析
&lst name="responseHeader"&
&int name="status"&0&/int&
&int name="QTime"&8&/int&
&lst name="params"&
&str name="explainOther"/&
&str name="fl"&*,score&/str&
&str name="debugQuery"&on&/str&
&str name="indent"&on&/str&
&str name="start"&0&/str&
&str name="q"&hi&/str&
&str name="hl.fl"/&
&str name="qt"/&
&str name="wt"/&
&str name="fq"/&
&str name="rows"&10&/str&
&str name="version"&2.2&/str&
具体命中的文档数可以在respose标签里找到,如下说明找到1328个包含查询词的文档
&result name="response" numFound="1328" start="0" maxScore="8.481748"&
以上这些地方对分析解决查询中出现的问题都很有帮助
2、查询语法
solr的一些查询语法
1.1. 首先假设我的数据里fields有:name, tel, address 预设的搜寻是name这个字段, 如果要搜寻的数据刚好就是 name 这个字段,就不需要指定搜寻字段名称.
1.2. 查询规则:
如欲查询特定字段(非预设字段),请在查询词前加上该字段名称加 “:” (不包含”号) 符号,
例如: address:北京市海淀区上地软件园 tel:88xxxxx1
1&. q代表query input
2&. version代表solr版本(建议不要变动此变量)
3&. start代表显示结果从哪一笔结果资料开始,预设为0代表第一笔, rows是说要显示几笔数据,预设为10笔
(因为有时查询结果可能有几百笔,但不需要显示所有结果,所以预设是从第一笔开始到第十笔)
所以若要显示第10到30笔就改为:
http: //localhost:8080/solr/select/?indent=on&version=2.2&q=address:北京 市海淀区上地软件园+tel:88xxxxx1&version=2.2&start=10&rows= 20&indent=on
(indent代表输出的xml要不要缩行.预设为开启 on)
1.3. 另外,要限定输出结果的内容可用 “fl=” 加上你要的字段名称,如以下这个范例:
http: //localhost:8080/solr/select/?indent=on&version=2.2&q=text:北京+ OR+text:亿度&start=0&rows=10&fl=name,address,tel
在fl=之后加上了name,adress,tel
所以结果会如下:
3、查询参数
q - 查询字符串,必须的。
fl - 指定返回那些字段内容,用逗号或空格分隔多个。
start - 返回第一条记录在完整找到结果中的偏移位置,0开始,一般分页用。
rows - 指定返回结果最多有多少条记录,配合start来实现分页。
sort - 排序,格式:sort=&field name&+&desc|asc&[,&field name&+&desc|asc&]… 。示例:(inStock desc, price asc)表示先 “inStock” 降序, 再 “price” 升序,默认是相关性降序。
wt - (writer type)指定输出格式,可以有 xml, json, php, phps, 后面 solr 1.3增加的,要用通知我们,因为默认没有打开。
fq - (filter query)过虑查询,作用:在q查询符合结果中同时是fq查询符合的,例如:q=mm&fq=date_time:[ TO ],找关键字mm,并且date_time是091031之间的。官方文档:
q.op - 覆盖schema.xml的defaultOperator(有空格时用"AND"还是用"OR"操作逻辑),一般默认指定
df - 默认的查询字段,一般默认指定
qt - (query type)指定那个类型来处理查询请求,一般不用指定,默认是standard。
indent - 返回的结果是否缩进,默认关闭,用 indent=true|on 开启,一般调试json,php,phps,ruby输出才有必要用这个参数。
version - 查询语法的版本,建议不使用它,由服务器指定默认值。
[Solr的检索运算符] “:” 指定字段查指定值,如返回所有值*:*? “?”?表示单个任意字符的通配 “*”
表示多个任意字符的通配(不能在检索的项开始使用*或者?符号)? “~”?表示模糊检索,如检索拼写类似于”roam”的项这样写:roam~将找到形如foam和roams的单词;roam~0.8,检索返回相似度在0.8以上的记录。?邻近检索,如检索相隔10个单词的”apache”和”jakarta”,”jakarta
apache”~10 “^”?控制相关度检索,如检索jakarta
apache,同时希望去让”jakarta”的相关度更加好,那么在其后加上”^”符号和增量值,即jakarta^4
apache 布尔操作符AND、||? 布尔操作符OR、?&& 布尔操作符NOT、!、-?(排除操作符不能单独与项使用构成查询) “+”
存在操作符,要求符号”+”后的项必须在文档相应的域中存在? ( ) 用于构成子查询?? [] 包含范围检索,如检索某时间段记录,包含头尾,date:[200707 TO
200710] {}?不包含范围检索,如检索某时间段记录,不包含头尾date:{200707
TO 200710} " 转义操作符,特殊字符包括+ -? && || ! ( ) { } [ ] ^ ” ~ * ?
浏览 49660
martin3000
浏览: 125318 次
来自: 武汉
requestHandler 是配置在solrconfig.x ...&&国之画&&&& &&&&&&
&& &&&&&&&&&&&&&&&&&&&&
鲁ICP备号-4
打开技术之扣,分享程序人生!Solr的内容还是比较多的,一篇文章只能讲解一部分。
全面介绍,没兴趣,没时间,也没能力,回报还不大。
本文只写点我认为比较重要的知识点,独特的个人想法。
仅供参考哦,更多细节需要自己去琢磨。
Solr是一个高性能,采用Java5开发,基于Lucene的全文搜索服务器。同时对其进行了扩展,提供了比Lucene更为丰富的查询语言,
同时实现了可配置、可扩展并对查询性能进行了优化,并且提供了一个完善的功能管理界面,是一款非常优秀的全文搜索引擎。
文档通过Http利用XML 加到一个搜索集合中。
查询该集合也是通过http收到一个XML/JSON响应来实现。
它的主要特性包括:高效、灵活的缓存功能,垂直搜索功能,高亮显示搜索结果,通过索引复制来提高可用性,
提供一套强大Data Schema来定义字段,类型和设置文本分析,提供基于Web的管理界面等。
& 查询和搜索,我们直接查询数据库MySQL。查询数据库主要有一些局限性:
比如多表查询效率低,大文本字段不好建立索引和搜索,复杂的条件查询和搜索功能不够强大,或者说不够简单。
& 使用Solr的话,就很简单地解决了以上问题。
& 以上需求,或者说关系型数据库mysql的问题,只是目前的一点理解。
& 虽说能够使用MySQL和Sorl解决实际中的问题,但毕竟都是中低难度的问题(自认为如此哦)。
& 非要说深入理解,剖析Solr的好处,MySQL是否“干的过”Solr,真心不懂。
& 单独搞MySQL,够你研究5年以上,DBA毕竟是个传说。
& Solr,想搞懂,也得好多年。
& 个人同时学习Java服务端、Android、iOS、Web前端,目标是能够解决工作中最常见的问题,并不想要
深入学习有限的几种技术,比如MySQL,达到那种“再难的问题,也可以搞定”的程度。
我对Solr的8点理解1.定义数据源接口,获得数据。
& 比如定义MySQL查询语句,把一个表或多个表的数据,导入到Solr中。
& 这个地方我觉得特别“不公平”,数据都是从别的地方搞过来的。外界的数据如果会变化,意味着,必须处理“数据同步”。
& 实时性要求不高的情况下,可以每天“全量更新”。要求高的情况下,单条数据的变化,需要“实时更新-单条”。
& 因此,Solr和Mysql并不是“直接竞争”关系,而是“互补”的关系。
2.把Mysql等数据源的数据,导入到Solr中去。
& Solr定义数据,可以理解成一张很大的表,包含了很多字段,比如可以包含mysql中3个表的所有字段。
& 这样,查询就不存在“多表”的问题。
& 既然是一张表,建立索引,查询就很快了。
3.自带缓存功能。
& Mysql,Solr,Redis等数据源或者有能力获得数据和管理数据的组件,只要需要,就可以提供“缓存”功能。
& Solr简化了查询,缓存就更容易了。
4.索引和全文搜索。
& Solr底层采用Lucene建立索引,全文索引,这样可以实现更多的“搜索功能”,可以说增强了Mysql的查询。
5.站内搜索的另外一种形式。
& 百度等搜索引擎,可以为网站提供“站内搜索”功能,他们爬去数据可以是公开的URL的形式。
& 如果需要和百度等合作,可以申请使用百度的搜索API,将站内数据,更友好,更快速地告诉百度。
& 而Solr和百度提供的搜索相关接口就基本一样,只不过是处在我们的管理之下。
6.简洁使用的管理界面。
& 后台有Web界面,导入数据,更新,可以通过可视化的操作来管理,比较方便。
7.功能服务化。
& Solr提供的查询等功能,有Java等多种语言的实现。
& 建立数据结构,导入数据,维护缓存和实时性,最重要的就是“查询”和“搜索”了。
8.最大的“隐患”。
& 只用Mysql管理数据和查询的时候,我们必须并且只需要保障mysql的“高可用性”。
& 不能出任何问题,如果只用1个Mysql,意味着我们需要实时监控Mysql是否可用,如果出了问题,我们需要立即修复它。
& 如果是多台Mysql,我们需要用主从,或者更复杂的主从。
& 现在用了Solr,意味着,我们很多查询和搜索,优先使用Solr,不再使用Mysql。
& 这个时候,为了“高可靠性”,我们也必须保障Solr是靠谱的。
& 单台Solr服务器,可靠性怎么样,我不太清楚。
& 无论单台Solr是否靠谱,多台Solr更加靠谱,这都意味着
& “我们程序中必须可靠的基础服务更多了”。
& 常见的必须“高可用性”的服务有
& 高可用性的服务越多,意味着我们的程序越复杂。
& 大部分的公司,都是中小型企业。
& 大部分的应用,都是为了快速推出,看看是否有效果。
& 真正需要保障“高可靠性”的项目,是很少的,如果遇到了,是很幸运的。
官方网站:http://lucene.apache.org/solr/
&本地环境:Windows-5.3.1版本
&运行和建立工程
&启动:solr.cmd start(类似这样)
&建立工程:
name=raikou
config=solrconfig.xml
schema=schema.xml
dataDir=J\:\\SoftData\\Solr\\raikou\\data
指定config、schema等多种参数。
(图文并茂的入门指引,可以参考其它博主的文章,本人觉得这种“图文并茂”的太尼玛费事了。
方便了读者,但是“技术含量”不够高,博主表示不过瘾o(︶︿︶)o )
简要介绍下几个配置,附带源文件内容
core.properties
name=raikou(项目名称)
config=solrconfig.xml(Solr配置)
schema=schema.xml(模式定义)
dataDir=J\:\\SoftData\\Solr\\raikou\\data (存储索引等数据)
Web界面输入的内容,保存在这了,入口配置,可以这么说。
schema.xml
&field name=&id& type=&long& indexed=&true& stored=&true& required=&true& multiValued=&false& /&
&field name=&title& type=&string& indexed=&true& stored=&true& required=&true& /&
&field name=&content& type=&string& indexed=&true& stored=&true& /&
&field name=&summary& type=&string& indexed=&true& stored=&true& /&
& &定义了几个字段
& &uniqueKey&id&/uniqueKey&
&&defaultSearchField&title&/defaultSearchField&
& 唯一字段,默认查询字段
& schemal.xml还配置了若干其它配置文件,比如“stopwords_en.txt”、“protwords.txt”、“stopwords.txt”等。
& 如果Solr启动报错,可能是缺少了这些字段。
data-config.xml&
&?xml version=&1.0& encoding=&UTF-8&?&
&dataConfig&
&dataSource type=&JdbcDataSource& driver=&com.mysql.jdbc.Driver&
url=&jdbc:mysql://localhost:3306/raikou?useUnicode=true&characterEncoding=UTF-8&
user=&root&
password=&mypassword&/&
&document name=&raikou_article&&
&entity name=&raikou_article&
query=&select * from raikou_article&
deltaImportQuery=&select * from raikou_article where id='${dih.delta.id}'&
deltaQuery=&select * from raikou_article where update_time & '${dataimporter.last_index_time}'&&
&field column=&id&
&field column=&title&
name=&title&
&field column=&content&
name=&content&
&field column=&summary&
name=&summary&
&/document&
&/dataConfig&
& 定义了数据导入、增量更新的查询语句。
&web.xml 这段配置,可能有用
& E:\Mongodb-Redis-Nginx\solr-5.3.1\server\solr-webapp\webapp\WEB-INF\web.xml
&!-- People who want to hardcode their &Solr Home& directly into the
WAR File can set the JNDI property here...
&env-entry&
&env-entry-name&solr/home&/env-entry-name&
&env-entry-value&J:\SoftData\Solr\&/env-entry-value&
&env-entry-type&java.lang.String&/env-entry-type&
&/env-entry&
Java程序访问
& maven配置
&dependency&
&groupId&org.apache.solr&/groupId&
&artifactId&solr-solrj&/artifactId&
&version&5.3.1&/version&
&/dependency&
包名:org.apache.solr.client.solrj
SolrHelper.java 查询(查询语句构造和执行查询,分页查询),更新,重建索引
import java.beans.PropertyD
import java.io.IOE
import java.lang.reflect.F
import java.lang.reflect.M
import java.text.SimpleDateF
import java.util.A
import java.util.D
import java.util.L
import mons.lang3.StringU
import org.apache.solr.client.solrj.SolrQ
import org.apache.solr.client.solrj.SolrServerE
import org.apache.solr.client.solrj.impl.HttpSolrC
import org.apache.solr.client.solrj.response.QueryR
import org.mon.SolrInputD
import org.slf4j.L
import org.slf4j.LoggerF
import com.github.pagehelper.P
/**查询(查询语句构造),更新,重建索引*/
public class SolrHelper&T& {
protected final Logger logger = LoggerFactory.getLogger(SolrHelper.class);
private HttpSolrC
private StringBuffer queryS
public SolrHelper(String reqUrl) {
server = new HttpSolrClient(reqUrl);
queryString = new StringBuffer();
public void andEquals(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:&).append(val);
public void orEquals(String fieldName, String val) {
queryString.append(& || &).append(fieldName).append(&:&).append(val);
public void andNotEquals(String fieldName, String val) {
queryString.append(& && &).append(&-&).append(fieldName).append(&:&)
.append(val);
public void orNotEquals(String fieldName, String val) {
queryString.append(& || &).append(&-&).append(fieldName).append(&:&)
.append(val);
public void andGreaterThan(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(val)
.append(& TO &).append(&*]&);
public void orGreaterThan(String fieldName, String val) {
queryString.append(& || &).append(fieldName).append(&:[&).append(val)
.append(& TO &).append(&*]&);
public void andGreaterThanOrEqualTo(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(val)
.append(& TO &).append(&*]&);
public void orGreaterThanOrEqualTo(String fieldName, String val) {
queryString.append(& || &).append(fieldName).append(&:[&).append(val)
.append(& TO &).append(&*]&);
public void andDateGreaterThan(String fieldName, Date val) {
queryString.append(& && &).append(fieldName).append(&:[&)
.append(formatUTCString(val)).append(& TO &).append(&*]&);
public void orDateGreaterThan(String fieldName, Date val) {
queryString.append(& || &).append(fieldName).append(&:[&)
.append(formatUTCString(val)).append(& TO &).append(&*]&);
public void andDateGreaterThanOrEqualTo(String fieldName, Date val) {
queryString.append(& && &).append(fieldName).append(&:[&)
.append(formatUTCString(val)).append(& TO &).append(&*]&);
public void orDateGreaterThanOrEqualTo(String fieldName, Date val) {
queryString.append(& || &).append(fieldName).append(&:[&)
.append(formatUTCString(val)).append(& TO &).append(&*]&);
public void andLessThan(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(val).append(&]&);
public void orLessThan(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(val).append(&]&);
public void andLessThanOrEqualTo(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(val).append(&]&);
public void orLessThanOrEqualTo(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(val).append(&]&);
public void andDateLessThan(String fieldName, Date val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(formatUTCString(val)).append(&]&);
public void orDateLessThan(String fieldName, Date val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(formatUTCString(val)).append(&]&);
public void andDateLessThanOrEqualTo(String fieldName, Date val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(formatUTCString(val)).append(&]&);
public void orDateLessThanOrEqualTo(String fieldName, Date val) {
queryString.append(& && &).append(fieldName).append(&:[&).append(&*&)
.append(& TO &).append(formatUTCString(val)).append(&]&);
public void andLike(String fieldName, String val) {
queryString.append(& && &).append(fieldName).append(&:*&).append(val)
.append(&*&);
public void orLike(String fieldName, String val) {
queryString.append(& || &).append(fieldName).append(&:*&).append(val)
.append(&*&);
public void andNotLike(String fieldName, String val) {
queryString.append(& && &).append(&-&).append(fieldName).append(&:*&)
.append(val).append(&*&);
public void orNotLike(String fieldName, String val) {
queryString.append(& || &).append(&-&).append(fieldName).append(&:*&)
.append(val).append(&*&);
public void andIn(String fieldName, String[] vals) {
queryString.append(& && &);
in(fieldName, vals);
private void in(String fieldName, String[] vals) {
List&String& list=Arrays.asList(vals);
in(queryString,fieldName,list);
public void orIn(String fieldName, List&String& vals) {
queryString.append(& || &);
in(queryString,fieldName,vals);
private static void in(StringBuffer queryString,String fieldName, List&String& vals) {
queryString.append(&(&);
inStr(queryString, fieldName, vals);
queryString.append(&)&);
private static void inStr(StringBuffer queryString, String fieldName,
List&String& vals) {
int index = 0;
for (String val : vals) {
if (0 != index) {
queryString.append(& || &);
queryString.append(fieldName).append(&:&).append(val);
// /questions/634765/using-or-and-not-in-solr-query
//instead of &NOT [condition]& use &(*:* NOT [condition])&
public void andNotIn(String fieldName, String[] vals) {
List&String& list=Arrays.asList(vals);
queryString.append(&&&(&);
queryString.append(&*:* NOT &);
inStr(queryString, fieldName, list);
queryString.append(&)&);
public void andDateBetween(String fieldName, Date startDate, Date endDate) {
queryString.append(& && &).append(fieldName).append(&:[&)
.append(formatUTCString(startDate)).append(& TO &)
.append(formatUTCString(endDate)).append(&]&);
public void orDateBetween(String fieldName, Date startDate, Date endDate) {
queryString.append(& || &).append(fieldName).append(&:[&)
.append(formatUTCString(startDate)).append(& TO &)
.append(formatUTCString(endDate)).append(&]&);
public void andDateNotBetween(String fieldName, Date startDate, Date endDate) {
queryString.append(& && &).append(&-&).append(fieldName).append(&:[&)
.append(formatUTCString(startDate)).append(& TO &)
.append(formatUTCString(endDate)).append(&]&);
public void orDateNotBetween(String fieldName, Date startDate, Date endDate) {
queryString.append(& && &).append(&-&).append(fieldName).append(&:[&)
.append(formatUTCString(startDate)).append(& TO &)
.append(formatUTCString(endDate)).append(&]&);
public void andBetween(String fieldName, String start, String end) {
queryString.append(& && &).append(fieldName).append(&:[&).append(start)
.append(& TO &).append(end).append(&]&);
public void orBetween(String fieldName, String start, String end) {
queryString.append(& || &).append(fieldName).append(&:[&).append(start)
.append(& TO &).append(end).append(&]&);
public void andNotBetween(String fieldName, String start, String end) {
queryString.append(& && &).append(&-&).append(fieldName).append(&:[&)
.append(start).append(& TO &).append(end).append(&]&);
public void orNotBetween(String fieldName, String start, String end) {
queryString.append(& || &).append(&-&).append(fieldName).append(&:[&)
.append(start).append(& TO &).append(end).append(&]&);
public void andStartSub() {
queryString.append(& && (&);
public void orStartSub() {
queryString.append(& || (&);
public void endSub() {
queryString.append(&)&);
private String formatUTCString(Date d) {
SimpleDateFormat sdf = new SimpleDateFormat(&yyyy-MM-dd'T'HH:mm:ss'Z'&);
String s = sdf.format(d);
public int execQueryTotalCount() {
SolrQuery params = handleQuery();
params.set(&start&, 0);
params.set(&rows&, Integer.MAX_VALUE);
QueryResponse response =
response = server.query(params);
return response.getResults().size();
} catch (SolrServerException e) {
logger.error(&&, e);
} catch (IOException e) {
logger.error(&&, e);
public List&T& query(String sort, Class&T& beanClass) {
SolrQuery params = handleQuery();
QueryResponse response =
List&T& list =
(&SolyQuery:& + params.toString());
response = server.query(params);
list = (List&T&) response.getBeans(beanClass);
} catch (SolrServerException e) {
logger.error(&SolrServerException&, e);
} catch (IOException e) {
logger.error(&IOException&, e);
public Page&T& execQuery(Integer pageNo, Integer rows, String sort,
Class&T& beanClass) {
List&T& results =
Page&T& page =
SolrQuery params = handleQuery();
if (pageNo != null && rows != null && pageNo & 0 && rows & 0) {
params.set(&start&, (pageNo - 1) * rows);
params.set(&rows&, rows);
if (null != sort && !&&.equals(sort)) {
params.set(&sort&, sort);
QueryResponse response =
(&SolyQuery WithPage:& + params.toString());
response = server.query(params);
results = (List&T&) response.getBeans(beanClass);
page = new Page&T&(pageNo, rows, execQueryTotalCount());
page.addAll(results);
} catch (SolrServerException e) {
logger.error(&SolrServerException&, e);
} catch (IOException e) {
logger.error(&IOException&, e);
private SolrQuery handleQuery() {
SolrQuery params = new SolrQuery();
String qryFinalStr = queryString.toString();
if (qryFinalStr.startsWith(& && &)) {
qryFinalStr = qryFinalStr.replaceFirst(& && &, &&);
} else if (qryFinalStr.startsWith(& || &)) {
qryFinalStr = qryFinalStr.replaceFirst(& || &, &&);
// 子查询开头的关联符号
if (-1 != qryFinalStr.indexOf(&( && &)) {
qryFinalStr = qryFinalStr.replaceAll(&\\( \\&\\& &, &(&);
if (-1 != qryFinalStr.indexOf(&( || &)) {
qryFinalStr = qryFinalStr.replaceAll(&\\( \\|\\| &, &(&);
if (StringUtils.isBlank(qryFinalStr)) {
qryFinalStr = &*:*&;
params.set(&q&, qryFinalStr);
public void execDelete(String keyName, String keyVal) {
server.deleteByQuery(keyName + &:& + keyVal);
} catch (SolrServerException | IOException e) {
logger.error(&&, e);
public void execUpdate(T model) {
Field[] fields = model.getClass().getDeclaredFields();
SolrInputDocument solrDoc = new SolrInputDocument();
for (Field f : fields) {
pd = new PropertyDescriptor(f.getName(), model.getClass());
String fieldName = f.getName();
Method rM = pd.getReadMethod();// 获得读方法
solrDoc.addField(fieldName, rM.invoke(model));
server.add(solrDoc);
} catch (Exception e) {
logger.error(&&, e);
public void execUpdate(SolrInputDocument solrDoc) {
server.add(solrDoc);
} catch (SolrServerException e) {
logger.error(&&, e);
} catch (IOException e) {
logger.error(&&, e);
* 重建索引和增量索引的接口
* @param delta
public void buildIndex(boolean delta) {
SolrQuery query = new SolrQuery();
// 指定RequestHandler,默认使用/select
query.setRequestHandler(&/dataimport&);
String command = delta ? &delta-import& : &full-import&;
String clean = delta ? &false& : &true&;
String optimize = delta ? &false& : &true&;
query.setParam(&command&, command).setParam(&clean&, clean)
.setParam(&commit&, &true&).setParam(&optimize&, optimize);
server.query(query);
} catch (SolrServerException e) {
logger.error(&建立索引时遇到错误,delta:& + delta, e);
} catch (IOException e) {
logger.error(&建立索引时遇到错误,delta:& + delta, e);
代码使用示例:
& & 1.常见的分页查询,更新单条数据
public static void main(String[] args) {
SolrHelper&Project& sh = new SolrHelper&Project&(
&http://host/solr/project&);
sh.andEquals(&id&, &32404&);
List&Project& page = sh.execQuery(1, 10, &id desc&,
Project.class);
Project ps = page.get(0);
ps.setTotal(3.1415);
sh.execUpdate(ps);
2.不修改,直接同步
public void synProject(long id) {
ProjectSolrDto solrDto = projectMapper.selectSolrProjectSimple(id);
SolrHelper&ProjectSolrDto& solrHelper = new SolrHelper&ProjectSolrDto&(
solrProjectUrl);
solrHelper.execUpdate(solrDto);
3.同步某几个字段
public void synIntention(Long id) {
Intention intention = intentionMapper.selectByPrimaryKey(id);
SolrHelper&Intention& solrHelper = new SolrHelper&Intention&(
solrIntentionUrl);
SolrInputDocument solrDoc = new SolrInputDocument();
solrDoc.addField(&id&, intention.getId());
solrDoc.addField(&intro&, intention.getIntro());
solrDoc.addField(&industry&, intention.getIndustry());
solrHelper.execUpdate(solrDoc);
& & 4.删除
public void delFund(Long id) {
SolrHelper&Intention& solrHelper = new SolrHelper&Intention&(
solrFundUrl);
solrHelper.execDelete(&id&, id.toString());
1.需要有“定时器”,定时“全量更新”和“重建索引”,防止数据不一致,或者查询效率低。
2.SolrHelper中的代码,或者说Solr的相关代码,无非就是“增删改查CRUD”,比较特殊的
“重建索引”和为了执行查询,拼接查询条件的“And,Or”等工具方法。
3.分页有个实体类,用到了Github上的1个工具,个人觉得一般般,Page类的定义比较糟糕。
如有需要,自己引入,或者自行改造。
IT互联网技术很多,更新很快,问题也很多,深入需要实践,深入需要时间。
技术方面的博学和专注,自己去平衡吧~
技术和技术之外的平衡,自己看着办哦~
Solr 搭建搜索服务器
http://my.oschina.net/u/1757458/blog/389109?fromerr=HUEucn9b
Solr调研总结
/guozk/p/3498831.html
http://www.solr.cc/blog/
solr对跨服务器表联合查询的配置
http://blog.csdn.net/awj3584/article/details/

我要回帖

更多关于 solrj 查询 的文章

 

随机推荐